Supply Chain Reference Ontology のサンプルデータを data.world でクエリする方法

<!--

ChatGPT では下記のプロンプトで調査
- [RDF供給チェーンオントロジー](https://chatgpt.com/c/67e0f090-3bcc-8004-be81-f4f0986b679a)
-->

## 概要

本記事では、Supply Chain Reference Ontology (SCRO) のサンプルデータとして公開されている `SCRO_Ford.ttl` に対し、data.world 上で SPARQL クエリを実行する方法を紹介します。SCRO はサプライチェーン管理におけるオントロジーであり、サンプルデータである `SCRO_Ford.ttl` ファイルが下記のように公開されています。本記事では、このデータに対して SPARQL を用いてどのようにクエリを実行できるかを解説します。なお、紹介している SPARQL は動作確認済みですが、最適なクエリである保証はない点に注意してください。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/8b76b359-403a-4bc7-9876-ff4a94f80fb4.png)

出所：[ontology/supplychain/data/SCRO_Ford.ttl at master · iofoundry/ontology](https://github.com/iofoundry/ontology/blob/master/supplychain/data/SCRO_Ford.ttl)

応用的なクエリとしては、「MODELING A SUPPLY CHAIN REFERENCE ONTOLOGY BASED ON A TOP-LEVEL ONTOLOGY」に記載されている、ビジネス上重要な質問に対応するクエリを例示します。ただし、サンプルデータがこれらの質問すべてに答えられる構造にはなっていないため、実行方法が確立できたクエリのみを紹介しています。

> - What are the outputs of this supplier in this supply network?
> - What types of information does this supplier receive?
> - What is the most connected supplier in this supply network?
> - What are the first-tier/second-tier suppliers in this network?
> - Which supplier provides raw materials in this network?
> - What is the path followed by a certain component in this network?

出所：[MODELING A SUPPLY CHAIN REFERENCE ONTOLOGY BASED ON A TOP-LEVEL ONTOLOGY](https://tsapps.nist.gov/publication/get_pdf.cfm?pub_id=928051)

なお、data.world については下記の記事でも紹介しています。

- [クラウド型データカタログサービス data.world の無償版で学ぶ SPARQL 実践ガイド #SPARQL - Qiita](https://qiita.com/manabian/items/b18ffe9914056d9d3f82)

## サンプルデータである`SCRO_Ford.ttl`ファイルについて

Supply Chain Reference Ontology (SCRO) の README で、サンプルデータとして紹介されています。

> ## Example RDF Dataset
> This dataset represents a hypothetical supply chain as depicted in [this image](https://github.com/iofoundry/ontology/blob/master/supplychain/Documentation & Resources/Terms-Patterns-Modules/Ford Supply Chain.md). The RDF dataset demonstrates how the class "Supply Chain Relationship' is used to represent the strucrue of a supply chain.
> - [RDF Dataset](https://github.com/iofoundry/ontology/blob/master/supplychain/data/SCRO_Ford.tt) ======= Additional class diagrams can be found [here](https://oagiscore.atlassian.net/wiki/spaces/IOF/pages/4554031140/SCRO+Class+Diagrams).

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/7a14a0ec-c581-4698-a92f-7a9a5c6defb0.png)

出所：[ontology/supplychain/README.md at master · iofoundry/ontology](https://github.com/iofoundry/ontology/blob/master/supplychain/README.md)

上記のリンクには誤字があるため、正確には下記 URL からアクセスしてください。

- [ontology/supplychain/data/SCRO_Ford.ttl at master · iofoundry/ontology](https://github.com/iofoundry/ontology/blob/master/supplychain/data/SCRO_Ford.ttl)

データ構造の概要は画像として公開されています。Ford Motor Company を中心としたサプライチェーンが表現されており、素材メーカーから部品メーカー、システムサプライヤーを経て最終組立の Ford へ部品やモジュールが集約されます。企業名と部品が矢印で結ばれており、矢印の上には納入部材や供給関係の番号が記載されています。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/b2ed169e-22a1-4811-9290-8f8c2937c708.png)

出所：[FORD-SupplyChain.png](https://github.com/iofoundry/ontology/blob/master/supplychain/Documentation%20%26%20Resources/images/FORD-SupplyChain.png)

## 事前準備

### data.world にてプロジェクトを作成

下記の記事を参考にプロジェクトを作成してください。

- [クラウド型データカタログサービス data.world の無償版で学ぶ SPARQL 実践ガイド #SPARQL - Qiita](https://qiita.com/manabian/items/b18ffe9914056d9d3f82)

### data.world に SCRO のサンプルデータである`SCRO_Ford.ttl`ファイルをアップロード

左上にある `+ Add` -> `Project file` を選択します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/49363417-27c4-432b-b873-4962ce934881.png)

`Sync from URL` を選択します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/911200cd-c5ce-44d7-96cf-16a0ffb0eb48.png)

`Source URL` に `SCRO_Ford.ttl` ファイルの GitHub URL を入力し、`Continue` を選択します。

```url
https://github.com/iofoundry/ontology/blob/master/supplychain/data/SCRO_Ford.ttl
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/c4c5cfc2-5dea-41b9-bfb6-e2789207454e.png)

`File name` が `SCRO_Ford.ttl` になっていることを確認し、`Done` を選択します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/7915d6ac-9c21-4d1f-9c6a-d4091ded4c86.png)

サンプルデータがアップロードされていることを確認します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/e754c3e5-a2bf-4dc7-bee8-92c93495e6e7.png)

### SPARQL Query の追加

`+ Add` -> `SPARQL Query` を選択します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/72edd1b8-c3d6-4467-9be0-a43c31dfc662.png)

SPARQL Query が表示されることを確認します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/3f25a1a8-7bc5-4054-bb31-2ee882b6131e.png)

## 1. 基本的なクエリ

### 1-1. 組織の一覧を表示

```sparql
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>
PREFIX obo: <http://purl.obolibrary.org/obo/>

SELECT ?org ?label ?properName ?naicsCode ?address
WHERE {
  ?org a iof-core:BusinessOrganization ;
       rdfs:label ?label .  
  OPTIONAL {
    ?org iof-core:designatedBy ?nameResource .
    ?nameResource a iof-scro:ProperName ;
                  iof-scro:hasTextValue ?properName .
  }
  OPTIONAL {
    ?org iof-core:designatedBy ?naicsResource .
    ?naicsResource a iof-scro:NAICSCode ;
                   iof-scro:hasTextValue ?naicsCode .
  }
  OPTIONAL {
    ?org obo:BFO_0000082 ?location .
    ?location iof-core:designatedBy ?addrResource .
    ?addrResource iof-scro:hasTextValue ?address .
  }
}
ORDER BY ?org
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/26510305-4bf3-4ba2-a1a5-a4da0ae58c7a.png)

### 1-2. 部材の一覧を表示

```sparql
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX obo: <http://purl.obolibrary.org/obo/>

SELECT ?contract ?partNumber ?modelName  
WHERE {
  ?contract a iof-scro:Contract ;
            obo:BFO_0000110 ?prodPart, ?prodModel .
  
  ?prodPart a iof-scro:PartNumber ;
            iof-scro:hasTextValue ?partNumber .
  
  ?prodModel a iof-scro:MaterialArtifactModelName ;
             iof-scro:hasTextValue ?modelName .
}
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/902f437a-b329-4dfe-bbb0-15f5efd8bfc7.png)

### 1-3. 契約（Contract）関連のデータを表示

```sparql
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX obo: <http://purl.obolibrary.org/obo/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>

SELECT 
  ?contract
  ?relationship 
  ?prodTextModel 
  ?supplierName ?buyerName
WHERE {
  ?contract a iof-scro:Contract ;
            iof-core:prescribes ?relationship .
  
  OPTIONAL {
    ?contract obo:BFO_0000110 ?part .
    ?part a iof-scro:PartNumber ;
          iof-scro:hasTextValue ?prodTextPart .
  }
  OPTIONAL {
    ?contract obo:BFO_0000110 ?model .
    ?model a iof-scro:MaterialArtifactModelName ;
           iof-scro:hasTextValue ?prodTextModel .
  }
  OPTIONAL {
    ?relationship obo:BFO_0000195 ?supplierRole .
    ?supplierRole a iof-core:SupplierRole ;
                  iof-core:roleOf ?supplier .
    ?supplier iof-core:designatedBy ?supplierNameNode .
    ?supplierNameNode a iof-scro:ProperName ;
                      iof-scro:hasTextValue ?supplierName .
  }
  OPTIONAL {
    ?relationship obo:BFO_0000195 ?buyerRole .
    ?buyerRole a iof-core:BuyerRole ;
               iof-core:roleOf ?buyer .
    ?buyer iof-core:designatedBy ?buyerNameNode .
    ?buyerNameNode a iof-scro:ProperName ;
                   iof-scro:hasTextValue ?buyerName .
  }
}
ORDER BY ?contract
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/8b9bca8d-69e9-4ae8-89fd-6f5f5b3b888a.png)

### 1-4. 供給関係（SupplyRelationship）のデータを表示

```sparql
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX obo: <http://purl.obolibrary.org/obo/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>

SELECT ?supplyRel ?buyer ?buyerName ?supplier ?supplierName 
WHERE {
  ?supplyRel a iof-scro:SupplyRelationship ;
             rdfs:label ?relLabel .
  
  # 供給者の役割から対象組織と正式名称を取得
  ?supplyRel obo:BFO_0000195 ?supplierRole .
  ?supplierRole a iof-core:SupplierRole ;
                iof-core:roleOf ?supplier .
  ?supplier iof-core:designatedBy ?supplierNameNode .
  ?supplierNameNode a iof-scro:ProperName ;
                    iof-scro:hasTextValue ?supplierName .
  
  # 購入者の役割から対象組織と正式名称を取得
  ?supplyRel obo:BFO_0000195 ?buyerRole .
  ?buyerRole a iof-core:BuyerRole ;
             iof-core:roleOf ?buyer .
  ?buyer iof-core:designatedBy ?buyerNameNode .
  ?buyerNameNode a iof-scro:ProperName ;
                 iof-scro:hasTextValue ?buyerName .
}
ORDER BY ?supplyRel
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/645a7fb4-3765-4a16-985b-c44e2908b2c4.png)

## 2. 応用的なクエリ

### 2-1. What are the outputs of this supplier in this supply network?

サプライチェーン上であるサプライヤーが提供する製品（部材）を抽出するクエリが考えられます。たとえば `ZF North America`（ `iof-scro:org-0006` ）が提供している部品を調べると、`Transmission` を特定できれば目的を達成できます。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/f19308f3-6b33-4202-9d27-c7229dbca34e.png)

出所：[FORD-SupplyChain.png](https://github.com/iofoundry/ontology/blob/master/supplychain/Documentation%20%26%20Resources/images/FORD-SupplyChain.png)

下記のクエリを実行すると、`ZF North America` が提供している `Transmission T4` を含む情報を取得できます。

```sparql
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX obo: <http://purl.obolibrary.org/obo/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>

SELECT ?supplierName ?modelName  ?buyerName
WHERE {
  # 指定したサプライヤー（例: iof-scro:org-0006）に関連するサプライヤーロールを取得
  ?supplierRole a iof-core:SupplierRole ;
                iof-core:roleOf iof-scro:org-0006 .
  
  # 同一の供給関係内で、サプライヤーロールとバイヤーロールを取得
  ?supplyRel obo:BFO_0000195 ?supplierRole ;
             obo:BFO_0000195 ?buyerRole .
  
  # 供給関係を規定する契約から、製品情報（部品番号、モデル名）を取得
  ?contract a iof-scro:Contract ;
            iof-core:prescribes ?supplyRel ;
            obo:BFO_0000110 ?prodPart, ?prodModel .
  
  # 部品番号の抽出
  ?prodPart a iof-scro:PartNumber ;
            iof-scro:hasTextValue ?partNumber .
  
  # 製品モデル名（製品名）の抽出
  ?prodModel a iof-scro:MaterialArtifactModelName ;
             iof-scro:hasTextValue ?modelName .
  
  # サプライヤー組織の名称を取得
  ?supplierRole iof-core:roleOf ?supplierOrg .
  ?supplierOrg iof-core:designatedBy ?supplierNameRes .
  ?supplierNameRes iof-scro:hasTextValue ?supplierName .
  ?supplierNameRes a iof-scro:ProperName .
  
  # バイヤー組織の名称を取得
  ?buyerRole a iof-core:BuyerRole ;
             iof-core:roleOf ?buyerOrg .
  ?buyerOrg iof-core:designatedBy ?buyerNameRes .
  ?buyerNameRes iof-scro:hasTextValue ?buyerName .
  ?buyerNameRes a iof-scro:ProperName .
}
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/b96c72ad-f430-4e6a-b4e9-2bfe0f111ee3.png)

### 2-2. What are the first-tier/second-tier suppliers in this network?

ある組織に直接納品しているサプライヤーを first-tier とし、そのサプライヤーにさらに納品している組織を second-tier と定義できます。Ford を基準とすると、3 社が first-tier、4 社が second-tier にあたります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/68d9af78-4ae7-4f0b-a2ff-33964577ead2.png)

出所：[FORD-SupplyChain.png](https://github.com/iofoundry/ontology/blob/master/supplychain/Documentation%20%26%20Resources/images/FORD-SupplyChain.png)

下記のクエリで、Ford の first-tier および second-tier サプライヤーを抽出できます。

```sparql
PREFIX iof-scro: <https://spec.industrialontologies.org/ontology/supplychain/SupplyChain/>
PREFIX iof-core: <https://spec.industrialontologies.org/ontology/core/Core/>
PREFIX obo: <http://purl.obolibrary.org/obo/>
PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#>

SELECT DISTINCT ?baseOrgName ?supplier ?supplierName ?tier
WHERE {
  # ベース組織 (Ford Motor Company) の名称を取得
  iof-scro:org-0001 rdfs:label ?baseOrgName .
  
  {
    # ファーストティア（一次）サプライヤー: Fordに直接供給している企業
    ?supplyRel a iof-scro:SupplyRelationship ;
               obo:BFO_0000195 ?roleA, ?roleB .
    {
      ?roleA a iof-core:BuyerRole ;
             iof-core:roleOf iof-scro:org-0001 .
      ?roleB a iof-core:SupplierRole ;
             iof-core:roleOf ?supplier .
    }
    UNION
    {
      ?roleB a iof-core:BuyerRole ;
             iof-core:roleOf iof-scro:org-0001 .
      ?roleA a iof-core:SupplierRole ;
             iof-core:roleOf ?supplier .
    }
    BIND("first-tier" AS ?tier)
    OPTIONAL { ?supplier rdfs:label ?supplierName . }
  }
  UNION
  {
    # セカンドティア（二次）サプライヤー: まずFordに直接供給している一次サプライヤーを抽出し、
    # その一次サプライヤーに供給している企業を取得
    {
      SELECT DISTINCT ?firstTierSupplier
      WHERE {
        ?supplyRel1 a iof-scro:SupplyRelationship ;
                    obo:BFO_0000195 ?roleC, ?roleD .
        {
          ?roleC a iof-core:BuyerRole ;
                 iof-core:roleOf iof-scro:org-0001 .
          ?roleD a iof-core:SupplierRole ;
                 iof-core:roleOf ?firstTierSupplier .
        }
        UNION
        {
          ?roleD a iof-core:BuyerRole ;
                 iof-core:roleOf iof-scro:org-0001 .
          ?roleC a iof-core:SupplierRole ;
                 iof-core:roleOf ?firstTierSupplier .
        }
      }
    }
    ?supplyRel2 a iof-scro:SupplyRelationship ;
                obo:BFO_0000195 ?roleE, ?roleF .
    {
      ?roleE a iof-core:BuyerRole ;
             iof-core:roleOf ?firstTierSupplier .
      ?roleF a iof-core:SupplierRole ;
             iof-core:roleOf ?supplier .
    }
    UNION
    {
      ?roleF a iof-core:BuyerRole ;
             iof-core:roleOf ?firstTierSupplier .
      ?roleE a iof-core:SupplierRole ;
             iof-core:roleOf ?supplier .
    }
    BIND("second-tier" AS ?tier)
    OPTIONAL { ?supplier rdfs:label ?supplierName . }
  }
}
```

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/574ef1fe-a72e-4696-9338-13436fef73bb.png)

## 次にやるべきこと

### SCRO の Taxonomy の全体像を理解

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/afa9c7a0-9420-4b23-8178-a86377367f55.png)

出所：[ontology/supplychain/README.md at master · iofoundry/ontology](https://github.com/iofoundry/ontology/blob/master/supplychain/README.md)

### IOF Ontology のページの理解

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/7eadc223-2dce-4ce2-8032-ef932e2de090.png)

出所：[IOF](https://spec.industrialontologies.org/iof/)

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/bf754fa2-a02c-45e6-8030-834bf12c3b47.png)

出所：[Ontology Viewer](https://spec.industrialontologies.org/iof/ontology)

### OAGI の atlassian の公開ページを理解

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/24031/790d0d96-cbd8-4cf4-975d-6d123a4c0652.png)

出所：[Industrial Ontologies Foundry - OAGi](https://oagi.atlassian.net/wiki/spaces/IOF/overview)