mirror of
https://github.com/oceanprotocol-archive/squid-js.git
synced 2024-02-02 15:31:51 +01:00
Merge pull request #45 from oceanprotocol/feature/sa_register
Feature/sa register
This commit is contained in:
commit
484ec08d61
@ -1,5 +1,5 @@
|
|||||||
[bumpversion]
|
[bumpversion]
|
||||||
current_version = 0.1.7
|
current_version = 0.1.21
|
||||||
|
|
||||||
[bumpversion:file:package.json]
|
[bumpversion:file:package.json]
|
||||||
|
|
||||||
|
@ -14,7 +14,7 @@ matrix:
|
|||||||
|
|
||||||
before_install:
|
before_install:
|
||||||
- npm install -g npm
|
- npm install -g npm
|
||||||
- npm install -g release-it greenkeeper-lockfile ganache-cli
|
- npm install -g release-it greenkeeper-lockfile ganache-cli@~6.1.8
|
||||||
|
|
||||||
before_script:
|
before_script:
|
||||||
- greenkeeper-lockfile-update
|
- greenkeeper-lockfile-update
|
||||||
|
77
README.md
77
README.md
@ -21,6 +21,7 @@
|
|||||||
## Table of Contents
|
## Table of Contents
|
||||||
|
|
||||||
- [Get started](#get-started)
|
- [Get started](#get-started)
|
||||||
|
- [Examples](#examples)
|
||||||
- [Development](#development)
|
- [Development](#development)
|
||||||
- [Production build](#production-build)
|
- [Production build](#production-build)
|
||||||
- [npm releases](#npm-releases)
|
- [npm releases](#npm-releases)
|
||||||
@ -49,12 +50,31 @@ const { Ocean, Logger } = require('@oceanprotocol/squid')
|
|||||||
You can then connect to a running [Keeper](https://github.com/oceanprotocol/keeper-contracts) & [Aquarius](https://github.com/oceanprotocol/aquarius) instance, e.g.:
|
You can then connect to a running [Keeper](https://github.com/oceanprotocol/keeper-contracts) & [Aquarius](https://github.com/oceanprotocol/aquarius) instance, e.g.:
|
||||||
|
|
||||||
```js
|
```js
|
||||||
const ocean = await new Ocean({
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
nodeUri: 'http://localhost:8545',
|
// the node of the blockchain to connect to, could also be infura
|
||||||
aquariusUri: 'http://localhost:5000'
|
nodeUri: "http://localhost:8545",
|
||||||
|
// the uri of aquarius
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
// the uri of brizo
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
// the uri to the parity node you want to use for encryption and decryption
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
// the uri of the secret store that holds the keys
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
// the threshold of nodes from the secre store that have to agree to the decrypt
|
||||||
|
threshold: 0,
|
||||||
|
// the password for the account (in the local parity node) used to sign messages for secret store
|
||||||
|
password: "unittest",
|
||||||
|
// the address of the account (in the local parity node) used to sign messages for secret store
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
})
|
})
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Examples
|
||||||
|
|
||||||
|
* [Examples](/src/examples/squid)
|
||||||
|
* [Tuna](https://github.com/oceanprotocol/tuna/examples/squid)
|
||||||
|
|
||||||
## Development
|
## Development
|
||||||
|
|
||||||
To start development you need to:
|
To start development you need to:
|
||||||
@ -64,6 +84,29 @@ npm i
|
|||||||
npm start
|
npm start
|
||||||
```
|
```
|
||||||
|
|
||||||
|
### Test
|
||||||
|
|
||||||
|
To start unit tests you need to:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ganache-cli &
|
||||||
|
npm run test
|
||||||
|
```
|
||||||
|
|
||||||
|
or to watch for changes
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ganache-cli &
|
||||||
|
npm run test:watch
|
||||||
|
```
|
||||||
|
|
||||||
|
to create code coverage
|
||||||
|
|
||||||
|
```bash
|
||||||
|
ganache-cli &
|
||||||
|
npm run test:cover
|
||||||
|
```
|
||||||
|
|
||||||
This will start a watcher for changes of the code.
|
This will start a watcher for changes of the code.
|
||||||
|
|
||||||
### Production build
|
### Production build
|
||||||
@ -77,34 +120,10 @@ npm run build
|
|||||||
For a new **patch release**, execute on the machine where you're logged into your npm account:
|
For a new **patch release**, execute on the machine where you're logged into your npm account:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
npm run release
|
./bumpversion path
|
||||||
```
|
```
|
||||||
|
|
||||||
In case you have 2FA setup on npm.js, pass a code as One Time Password:
|
git tag with the latest version and `git push`
|
||||||
|
|
||||||
```bash
|
|
||||||
npm run release --otp <yourcode>
|
|
||||||
```
|
|
||||||
|
|
||||||
Command is powered by [`release-it`](https://github.com/webpro/release-it) package, defined in the `package.json`.
|
|
||||||
|
|
||||||
That's what the command does without any user interaction:
|
|
||||||
|
|
||||||
- create release commit by updating version in `package.json`
|
|
||||||
- create tag for that release commit
|
|
||||||
- push commit & tag
|
|
||||||
- create a new release on GitHub, with change log auto-generated from commit messages
|
|
||||||
- publish to npm as a new release
|
|
||||||
|
|
||||||
If you want to create a **minor** or **major release**, use these commands:
|
|
||||||
|
|
||||||
```bash
|
|
||||||
npm run release-minor
|
|
||||||
```
|
|
||||||
|
|
||||||
```bash
|
|
||||||
npm run release-major
|
|
||||||
```
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
|
2746
package-lock.json
generated
2746
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
17
package.json
17
package.json
@ -1,6 +1,6 @@
|
|||||||
{
|
{
|
||||||
"name": "@oceanprotocol/squid",
|
"name": "@oceanprotocol/squid",
|
||||||
"version": "0.1.7",
|
"version": "0.1.21",
|
||||||
"description": "JavaScript client library for Ocean Protocol",
|
"description": "JavaScript client library for Ocean Protocol",
|
||||||
"main": "dist/squid.js",
|
"main": "dist/squid.js",
|
||||||
"scripts": {
|
"scripts": {
|
||||||
@ -47,18 +47,15 @@
|
|||||||
"url": "https://github.com/oceanprotocol/squid-js/issues"
|
"url": "https://github.com/oceanprotocol/squid-js/issues"
|
||||||
},
|
},
|
||||||
"homepage": "https://github.com/oceanprotocol/squid-js#readme",
|
"homepage": "https://github.com/oceanprotocol/squid-js#readme",
|
||||||
"engines": {
|
|
||||||
"node": ">=8 <10"
|
|
||||||
},
|
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@oceanprotocol/keeper-contracts": "0.3.19",
|
"@oceanprotocol/keeper-contracts": "0.3.22",
|
||||||
"@oceanprotocol/secret-store-client": "0.0.11",
|
"@oceanprotocol/secret-store-client": "0.0.12",
|
||||||
"bignumber.js": "^8.0.1",
|
"bignumber.js": "^8.0.1",
|
||||||
"eth-crypto": "^1.2.5",
|
"eth-crypto": "^1.2.7",
|
||||||
"eth-ecies": "^1.0.3",
|
"eth-ecies": "^1.0.3",
|
||||||
"ethereumjs-util": "^6.0.0",
|
"ethereumjs-util": "^6.0.0",
|
||||||
"jsonwebtoken": "^8.3.0",
|
"jsonwebtoken": "^8.4.0",
|
||||||
"node-fetch": "^2.2.1",
|
"node-fetch": "^2.3.0",
|
||||||
"uuid": "^3.3.2",
|
"uuid": "^3.3.2",
|
||||||
"web3": "1.0.0-beta.36",
|
"web3": "1.0.0-beta.36",
|
||||||
"web3-utils": "1.0.0-beta.36",
|
"web3-utils": "1.0.0-beta.36",
|
||||||
@ -67,7 +64,7 @@
|
|||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@types/chai": "^4.1.7",
|
"@types/chai": "^4.1.7",
|
||||||
"@types/mocha": "^5.2.5",
|
"@types/mocha": "^5.2.5",
|
||||||
"@types/node": "^10.12.6",
|
"@types/node": "^10.12.7",
|
||||||
"chai": "^4.2.0",
|
"chai": "^4.2.0",
|
||||||
"mocha": "^5.2.0",
|
"mocha": "^5.2.0",
|
||||||
"nyc": "^13.1.0",
|
"nyc": "^13.1.0",
|
||||||
|
@ -2,9 +2,11 @@ import {URL} from "whatwg-url"
|
|||||||
import DDO from "../ddo/DDO"
|
import DDO from "../ddo/DDO"
|
||||||
import Config from "../models/Config"
|
import Config from "../models/Config"
|
||||||
import Logger from "../utils/Logger"
|
import Logger from "../utils/Logger"
|
||||||
import AquariusConnectorProvider from "./AquariusConnectorProvider"
|
import WebServiceConnectorProvider from "../utils/WebServiceConnectorProvider"
|
||||||
import SearchQuery from "./query/SearchQuery"
|
import SearchQuery from "./query/SearchQuery"
|
||||||
|
|
||||||
|
const apiPath = "/api/v1/aquarius/assets/ddo"
|
||||||
|
|
||||||
export default class Aquarius {
|
export default class Aquarius {
|
||||||
|
|
||||||
private url: string
|
private url: string
|
||||||
@ -16,7 +18,7 @@ export default class Aquarius {
|
|||||||
|
|
||||||
public async getAccessUrl(accessToken: any, payload: any): Promise<string> {
|
public async getAccessUrl(accessToken: any, payload: any): Promise<string> {
|
||||||
|
|
||||||
const accessUrl: string = await AquariusConnectorProvider.getConnector()
|
const accessUrl: string = await WebServiceConnectorProvider.getConnector()
|
||||||
.post(`${accessToken.service_endpoint}/${accessToken.resource_id}`, payload)
|
.post(`${accessToken.service_endpoint}/${accessToken.resource_id}`, payload)
|
||||||
.then((response: any): string => {
|
.then((response: any): string => {
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
@ -37,78 +39,98 @@ export default class Aquarius {
|
|||||||
return accessUrl
|
return accessUrl
|
||||||
}
|
}
|
||||||
|
|
||||||
public async queryMetadata(query: SearchQuery): Promise<any[]> {
|
public async queryMetadata(query: SearchQuery): Promise<DDO[]> {
|
||||||
|
|
||||||
const result = await AquariusConnectorProvider.getConnector()
|
const result: DDO[] = await WebServiceConnectorProvider.getConnector()
|
||||||
.post(this.url + "/api/v1/aquarius/assets/ddo/query", JSON.stringify(query))
|
.post(`${this.url}${apiPath}/query`, JSON.stringify(query))
|
||||||
.then((response: any) => {
|
.then((response: any) => {
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
return response.json()
|
return response.json() as DDO[]
|
||||||
}
|
}
|
||||||
Logger.error("queryMetadata failed:", response.status, response.statusText)
|
Logger.error("queryMetadata failed:", response.status, response.statusText)
|
||||||
return null
|
return [] as DDO[]
|
||||||
|
})
|
||||||
|
.then((ddos) => {
|
||||||
|
return ddos.map((ddo): DDO => {
|
||||||
|
return new DDO(ddo as DDO)
|
||||||
|
})
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
Logger.error("Error fetching querying metadata: ", error)
|
Logger.error("Error fetching querying metadata: ", error)
|
||||||
|
return [] as DDO[]
|
||||||
})
|
})
|
||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
public async queryMetadataByText(query: SearchQuery): Promise<any[]> {
|
public async queryMetadataByText(query: SearchQuery): Promise<DDO[]> {
|
||||||
|
|
||||||
const fullUrl = new URL(this.url + "/api/v1/aquarius/assets/ddo/query")
|
const fullUrl = new URL(`${this.url}${apiPath}/query`)
|
||||||
fullUrl.searchParams.append("text", query.text)
|
fullUrl.searchParams.append("text", query.text)
|
||||||
fullUrl.searchParams.append("sort", JSON.stringify(query.sort))
|
fullUrl.searchParams.append("sort", decodeURIComponent(JSON.stringify(query.sort)))
|
||||||
fullUrl.searchParams.append("offset", query.offset.toString())
|
fullUrl.searchParams.append("offset", query.offset.toString())
|
||||||
fullUrl.searchParams.append("page", query.page.toString())
|
fullUrl.searchParams.append("page", query.page.toString())
|
||||||
const result = await AquariusConnectorProvider.getConnector()
|
const result: DDO[] = await WebServiceConnectorProvider.getConnector()
|
||||||
.get(fullUrl)
|
.get(fullUrl)
|
||||||
.then((response: any) => {
|
.then((response: any) => {
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
return response.json()
|
return response.json() as DDO[]
|
||||||
}
|
}
|
||||||
Logger.log("queryMetadataByText failed:", response.status, response.statusText)
|
Logger.log("queryMetadataByText failed:", response.status, response.statusText)
|
||||||
return null
|
return [] as DDO[]
|
||||||
|
})
|
||||||
|
.then((ddos) => {
|
||||||
|
return ddos.map((ddo): DDO => {
|
||||||
|
return new DDO(ddo as DDO)
|
||||||
|
})
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
Logger.error("Error fetching querying metadata: ", error)
|
Logger.error("Error fetching querying metadata by text: ", error)
|
||||||
|
return [] as DDO[]
|
||||||
})
|
})
|
||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
public async storeDDO(ddo: DDO): Promise<DDO> {
|
public async storeDDO(ddo: DDO): Promise<DDO> {
|
||||||
const fullUrl = this.url + `/api/v1/aquarius/assets/ddo`
|
const fullUrl = `${this.url}${apiPath}`
|
||||||
const result: DDO = await AquariusConnectorProvider.getConnector()
|
const result: DDO = await WebServiceConnectorProvider.getConnector()
|
||||||
.post(fullUrl, DDO.serialize(ddo))
|
.post(fullUrl, DDO.serialize(ddo))
|
||||||
.then((response: any) => {
|
.then((response: any) => {
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
return response.json()
|
return response.json()
|
||||||
}
|
}
|
||||||
Logger.error("storeDDO failed:", response.status, response.statusText)
|
Logger.error("storeDDO failed:", response.status, response.statusText, ddo)
|
||||||
return null
|
return null as DDO
|
||||||
|
})
|
||||||
|
.then((response: DDO) => {
|
||||||
|
return new DDO(response) as DDO
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
Logger.error("Error fetching querying metadata: ", error)
|
Logger.error("Error fetching querying metadata: ", error)
|
||||||
|
return null as DDO
|
||||||
})
|
})
|
||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
public async retrieveDDO(did: string): Promise<DDO> {
|
public async retrieveDDO(did: string): Promise<DDO> {
|
||||||
const fullUrl = this.url + `/api/v1/aquarius/assets/ddo/${did}`
|
const fullUrl = `${this.url}${apiPath}/${did}`
|
||||||
const result = await AquariusConnectorProvider.getConnector()
|
const result = await WebServiceConnectorProvider.getConnector()
|
||||||
.get(fullUrl)
|
.get(fullUrl)
|
||||||
.then((response: any) => {
|
.then((response: any) => {
|
||||||
if (response.ok) {
|
if (response.ok) {
|
||||||
return response.json()
|
return response.json()
|
||||||
}
|
}
|
||||||
Logger.log("retrieveDDO failed:", response.status, response.statusText)
|
Logger.log("retrieveDDO failed:", response.status, response.statusText, did)
|
||||||
return null
|
return null as DDO
|
||||||
|
})
|
||||||
|
.then((response: DDO) => {
|
||||||
|
return new DDO(response) as DDO
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
Logger.error("Error fetching querying metadata: ", error)
|
Logger.error("Error fetching querying metadata: ", error)
|
||||||
|
return null as DDO
|
||||||
})
|
})
|
||||||
|
|
||||||
return result
|
return result
|
||||||
|
@ -1,19 +0,0 @@
|
|||||||
import AquariusConnector from "./AquariusConnector"
|
|
||||||
|
|
||||||
export default class AquariusConnectorProvider {
|
|
||||||
|
|
||||||
public static setConnector(connector: AquariusConnector) {
|
|
||||||
|
|
||||||
AquariusConnectorProvider.connector = connector
|
|
||||||
}
|
|
||||||
|
|
||||||
public static getConnector(): AquariusConnector {
|
|
||||||
|
|
||||||
if (!AquariusConnectorProvider.connector) {
|
|
||||||
AquariusConnectorProvider.connector = new AquariusConnector()
|
|
||||||
}
|
|
||||||
return AquariusConnectorProvider.connector
|
|
||||||
}
|
|
||||||
|
|
||||||
private static connector: AquariusConnector = null
|
|
||||||
}
|
|
43
src/brizo/Brizo.ts
Normal file
43
src/brizo/Brizo.ts
Normal file
@ -0,0 +1,43 @@
|
|||||||
|
import Config from "../models/Config"
|
||||||
|
import WebServiceConnectorProvider from "../utils/WebServiceConnectorProvider"
|
||||||
|
|
||||||
|
export default class Brizo {
|
||||||
|
private url: string
|
||||||
|
|
||||||
|
constructor(config: Config) {
|
||||||
|
|
||||||
|
this.url = config.brizoUri
|
||||||
|
}
|
||||||
|
|
||||||
|
public getPurchaseEndpoint() {
|
||||||
|
return `${this.url}/api/v1/brizo/services/access/purchase?`
|
||||||
|
}
|
||||||
|
|
||||||
|
public getConsumeEndpoint(pubKey: string, serviceId: string, url: string) {
|
||||||
|
return `${this.url}/api/v1/brizo/services/consume?pubKey=${pubKey}&serviceId=${serviceId}&url=${url}`
|
||||||
|
}
|
||||||
|
|
||||||
|
public getComputeEndpoint(pubKey: string, serviceId: string, algo: string, container: string) {
|
||||||
|
// tslint:disable-next-line
|
||||||
|
return `${this.url}/api/v1/brizo/services/compute?pubKey=${pubKey}&serviceId=${serviceId}&algo=${algo}&container=${container}"`
|
||||||
|
}
|
||||||
|
|
||||||
|
public async initializeServiceAgreement(
|
||||||
|
did: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
serviceDefinitionId: string,
|
||||||
|
signature: string,
|
||||||
|
consumerPublicKey: string): Promise<any> {
|
||||||
|
|
||||||
|
return WebServiceConnectorProvider.getConnector().post(
|
||||||
|
`${this.url}/api/v1/brizo/services/access/initialize`,
|
||||||
|
{
|
||||||
|
did,
|
||||||
|
serviceAgreementId,
|
||||||
|
serviceDefinitionId,
|
||||||
|
signature,
|
||||||
|
consumerPublicKey,
|
||||||
|
})
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
20
src/brizo/BrizoProvider.ts
Normal file
20
src/brizo/BrizoProvider.ts
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
import ConfigProvider from "../ConfigProvider"
|
||||||
|
import Brizo from "./Brizo"
|
||||||
|
|
||||||
|
export default class BrizoProvider {
|
||||||
|
|
||||||
|
public static setBrizo(brizo: Brizo) {
|
||||||
|
|
||||||
|
BrizoProvider.brizo = brizo
|
||||||
|
}
|
||||||
|
|
||||||
|
public static getBrizo() {
|
||||||
|
|
||||||
|
if (!BrizoProvider.brizo) {
|
||||||
|
BrizoProvider.brizo = new Brizo(ConfigProvider.getConfig())
|
||||||
|
}
|
||||||
|
return BrizoProvider.brizo
|
||||||
|
}
|
||||||
|
|
||||||
|
private static brizo: Brizo = null
|
||||||
|
}
|
@ -12,4 +12,5 @@ export default class AdditionalInformation {
|
|||||||
mediaType: "text/turtle",
|
mediaType: "text/turtle",
|
||||||
}as StructuredMarkup,
|
}as StructuredMarkup,
|
||||||
]
|
]
|
||||||
|
public checksum: string
|
||||||
}
|
}
|
||||||
|
@ -1,8 +1,14 @@
|
|||||||
|
import Event from "./Event"
|
||||||
import Parameter from "./Parameter"
|
import Parameter from "./Parameter"
|
||||||
|
|
||||||
export default class Condition {
|
export default class Condition {
|
||||||
public name: string = "lockPayment"
|
public contractName: string = "AccessCondition"
|
||||||
|
public methodName: string = "lockPayment"
|
||||||
public timeout: number = 0
|
public timeout: number = 0
|
||||||
public conditionKey: string
|
public conditionKey: string = "0x12122434"
|
||||||
public parameters: Parameter[]
|
public parameters: Parameter[]
|
||||||
|
public events: Event[]
|
||||||
|
public dependencies: string[] = []
|
||||||
|
public dependencyTimeoutFlags: number[] = []
|
||||||
|
public isTerminalCondition: boolean = false
|
||||||
}
|
}
|
||||||
|
@ -20,18 +20,37 @@ export default class DDO {
|
|||||||
public authentication: Authentication[]
|
public authentication: Authentication[]
|
||||||
public service: Service[]
|
public service: Service[]
|
||||||
|
|
||||||
// @ts-ignore
|
|
||||||
private assa: string
|
|
||||||
|
|
||||||
public constructor(ddo?: {
|
public constructor(ddo?: {
|
||||||
id?: string,
|
id?: string,
|
||||||
publicKey?: PublicKey[],
|
publicKey?: any[],
|
||||||
authentication?: Authentication[],
|
authentication?: Authentication[],
|
||||||
service?: Service[],
|
service?: Service[],
|
||||||
}) {
|
}) {
|
||||||
|
this.authentication = ddo ? ddo.authentication ? ddo.authentication : [] : []
|
||||||
this.id = ddo ? ddo.id ? ddo.id : null : null
|
this.id = ddo ? ddo.id ? ddo.id : null : null
|
||||||
this.publicKey = ddo ? ddo.publicKey ? ddo.publicKey : [] : []
|
this.publicKey = ddo ? ddo.publicKey ? ddo.publicKey : [] : []
|
||||||
this.authentication = ddo ? ddo.authentication ? ddo.authentication : [] : []
|
|
||||||
this.service = ddo ? ddo.service ? ddo.service : [] : []
|
this.service = ddo ? ddo.service ? ddo.service : [] : []
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public findServiceById(serviceDefinitionId: string): Service {
|
||||||
|
|
||||||
|
if (!serviceDefinitionId) {
|
||||||
|
throw new Error("serviceDefinitionId not set")
|
||||||
|
}
|
||||||
|
|
||||||
|
const service: Service = this.service.find((s) => s.serviceDefinitionId === serviceDefinitionId)
|
||||||
|
|
||||||
|
return service
|
||||||
|
}
|
||||||
|
|
||||||
|
public findServiceByType(serviceType: string): Service {
|
||||||
|
|
||||||
|
if (!serviceType) {
|
||||||
|
throw new Error("serviceType not set")
|
||||||
|
}
|
||||||
|
|
||||||
|
const service: Service = this.service.find((s) => s.type === serviceType)
|
||||||
|
|
||||||
|
return service
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
7
src/ddo/Event.ts
Normal file
7
src/ddo/Event.ts
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
import EventHandlers from "./EventHandlers"
|
||||||
|
|
||||||
|
export default class Event {
|
||||||
|
public name: string
|
||||||
|
public actorType: string[]
|
||||||
|
public handlers: EventHandlers
|
||||||
|
}
|
5
src/ddo/EventHandlers.ts
Normal file
5
src/ddo/EventHandlers.ts
Normal file
@ -0,0 +1,5 @@
|
|||||||
|
export default class EventHandlers {
|
||||||
|
public moduleName: string = "serviceAgreement"
|
||||||
|
public functionName: string = "fulfillAgreement"
|
||||||
|
public version: string = "0.1"
|
||||||
|
}
|
@ -3,52 +3,66 @@ import Curation from "./Curation"
|
|||||||
import MetaDataBase from "./MetaDataBase"
|
import MetaDataBase from "./MetaDataBase"
|
||||||
import StructuredMarkup from "./StructuredMarkup"
|
import StructuredMarkup from "./StructuredMarkup"
|
||||||
|
|
||||||
|
const base: MetaDataBase = {
|
||||||
|
name: "UK Weather information 2011",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase
|
||||||
|
|
||||||
|
const curation: Curation = {
|
||||||
|
rating: 0.93,
|
||||||
|
numVotes: 123,
|
||||||
|
schema: "Binary Votting",
|
||||||
|
} as Curation
|
||||||
|
|
||||||
|
const additionalInformation: AdditionalInformation = {
|
||||||
|
updateFrecuency: "yearly",
|
||||||
|
structuredMarkup: [
|
||||||
|
{
|
||||||
|
uri: "http://skos.um.es/unescothes/C01194/jsonld",
|
||||||
|
mediaType: "application/ld+json",
|
||||||
|
} as StructuredMarkup,
|
||||||
|
{
|
||||||
|
uri: "http://skos.um.es/unescothes/C01194/turtle",
|
||||||
|
mediaType: "text/turtle",
|
||||||
|
} as StructuredMarkup,
|
||||||
|
],
|
||||||
|
} as AdditionalInformation
|
||||||
|
|
||||||
export default class MetaData {
|
export default class MetaData {
|
||||||
|
|
||||||
public base: MetaDataBase = {
|
public additionalInformation: AdditionalInformation
|
||||||
name: "UK Weather information 2011",
|
public base: MetaDataBase
|
||||||
type: "dataset",
|
public curation: Curation
|
||||||
description: "Weather information of UK including temperature and humidity",
|
|
||||||
size: "3.1gb",
|
|
||||||
dateCreated: "2012-02-01T10:55:11+00:00",
|
|
||||||
author: "Met Office",
|
|
||||||
license: "CC-BY",
|
|
||||||
copyrightHolder: "Met Office",
|
|
||||||
encoding: "UTF-8",
|
|
||||||
compression: "zip",
|
|
||||||
contentType: "text/csv",
|
|
||||||
// tslint:disable-next-line
|
|
||||||
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
|
||||||
contentUrls: [
|
|
||||||
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
|
||||||
],
|
|
||||||
links: [
|
|
||||||
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
|
||||||
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
|
||||||
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
|
||||||
],
|
|
||||||
inLanguage: "en",
|
|
||||||
tags: "weather, uk, 2011, temperature, humidity",
|
|
||||||
price: 10,
|
|
||||||
} as MetaDataBase
|
|
||||||
|
|
||||||
public curation: Curation = {
|
constructor(metaData?: MetaData) {
|
||||||
rating: 0.93,
|
this.additionalInformation = metaData ?
|
||||||
numVotes: 123,
|
metaData.additionalInformation ? metaData.additionalInformation :
|
||||||
schema: "Binary Votting",
|
additionalInformation : additionalInformation
|
||||||
} as Curation
|
this.base = metaData ? metaData.base ? metaData.base : base : base
|
||||||
|
this.curation = metaData ? metaData.curation ? metaData.curation : curation : curation
|
||||||
|
}
|
||||||
|
|
||||||
public additionalInformation: AdditionalInformation = {
|
|
||||||
updateFrecuency: "yearly",
|
|
||||||
structuredMarkup: [
|
|
||||||
{
|
|
||||||
uri: "http://skos.um.es/unescothes/C01194/jsonld",
|
|
||||||
mediaType: "application/ld+json",
|
|
||||||
} as StructuredMarkup,
|
|
||||||
{
|
|
||||||
uri: "http://skos.um.es/unescothes/C01194/turtle",
|
|
||||||
mediaType: "text/turtle",
|
|
||||||
} as StructuredMarkup,
|
|
||||||
],
|
|
||||||
} as AdditionalInformation
|
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,8 @@ export default class MetaDataBase {
|
|||||||
public compression: string = "zip"
|
public compression: string = "zip"
|
||||||
public contentType: string = "text/csv"
|
public contentType: string = "text/csv"
|
||||||
public workExample: string = "423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68"
|
public workExample: string = "423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68"
|
||||||
public contentUrls: string[] = [
|
public contentUrls: string | string[] = [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
]
|
]
|
||||||
public links: any[] = [
|
public links: any[] = [
|
||||||
|
73
src/examples/ExecuteAgreement.ts
Normal file
73
src/examples/ExecuteAgreement.ts
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
import DDO from "../ddo/DDO"
|
||||||
|
import MetaData from "../ddo/MetaData"
|
||||||
|
import MetaDataBase from "../ddo/MetaDataBase"
|
||||||
|
import Service from "../ddo/Service"
|
||||||
|
import {Account, Logger, Ocean, ServiceAgreement} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const publisher: Account = (await ocean.getAccounts())[0]
|
||||||
|
const consumer: Account = (await ocean.getAccounts())[1]
|
||||||
|
|
||||||
|
const metaData = new MetaData({
|
||||||
|
base: {
|
||||||
|
name: "Office Humidity",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase,
|
||||||
|
} as MetaData)
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(metaData, publisher)
|
||||||
|
Logger.log("did", ddo.id)
|
||||||
|
|
||||||
|
const accessService = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
const serviceAgreementSignatureResult: any = await ocean.signServiceAgreement(ddo.id,
|
||||||
|
accessService.serviceDefinitionId, consumer)
|
||||||
|
Logger.log("ServiceAgreement Id:", serviceAgreementSignatureResult.serviceAgreementId)
|
||||||
|
Logger.log("ServiceAgreement Signature:", serviceAgreementSignatureResult.serviceAgreementSignature)
|
||||||
|
|
||||||
|
const service: Service = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
const serviceAgreement: ServiceAgreement = await ocean.executeServiceAgreement(
|
||||||
|
ddo.id,
|
||||||
|
service.serviceDefinitionId,
|
||||||
|
serviceAgreementSignatureResult.serviceAgreementId,
|
||||||
|
serviceAgreementSignatureResult.serviceAgreementSignature,
|
||||||
|
consumer,
|
||||||
|
publisher)
|
||||||
|
Logger.log("ServiceAgreement Id:", serviceAgreement.getId())
|
||||||
|
|
||||||
|
})()
|
75
src/examples/InitializeAgreement.ts
Normal file
75
src/examples/InitializeAgreement.ts
Normal file
@ -0,0 +1,75 @@
|
|||||||
|
import DDO from "../ddo/DDO"
|
||||||
|
import MetaData from "../ddo/MetaData"
|
||||||
|
import MetaDataBase from "../ddo/MetaDataBase"
|
||||||
|
import Service from "../ddo/Service"
|
||||||
|
import {Account, Logger, Ocean} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const publisher: Account = (await ocean.getAccounts())[0]
|
||||||
|
const consumer: Account = (await ocean.getAccounts())[1]
|
||||||
|
|
||||||
|
const metaData = new MetaData({
|
||||||
|
base: {
|
||||||
|
name: "Office Humidity",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase,
|
||||||
|
} as MetaData)
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(metaData, publisher)
|
||||||
|
Logger.log("did", ddo.id)
|
||||||
|
|
||||||
|
const accessService = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
const serviceAgreementSignatureResult: any = await ocean
|
||||||
|
.signServiceAgreement(
|
||||||
|
ddo.id,
|
||||||
|
accessService.serviceDefinitionId,
|
||||||
|
consumer)
|
||||||
|
Logger.log("ServiceAgreement Id:", serviceAgreementSignatureResult.serviceAgreementId)
|
||||||
|
Logger.log("ServiceAgreement Signature:", serviceAgreementSignatureResult.serviceAgreementSignature)
|
||||||
|
|
||||||
|
const service: Service = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
await ocean
|
||||||
|
.initializeServiceAgreement(
|
||||||
|
ddo.id,
|
||||||
|
service.serviceDefinitionId,
|
||||||
|
serviceAgreementSignatureResult.serviceAgreementId,
|
||||||
|
serviceAgreementSignatureResult.serviceAgreementSignature,
|
||||||
|
consumer)
|
||||||
|
|
||||||
|
})()
|
@ -1,20 +0,0 @@
|
|||||||
import DDO from "../ddo/DDO"
|
|
||||||
import MetaData from "../ddo/MetaData"
|
|
||||||
import {Account, Logger, Ocean} from "../squid"
|
|
||||||
|
|
||||||
(async () => {
|
|
||||||
const ocean: Ocean = await Ocean.getInstance({
|
|
||||||
nodeUri: "http://localhost:8545",
|
|
||||||
aquariusUri: "http://localhost:5000",
|
|
||||||
parityUri: "http://localhost:9545",
|
|
||||||
secretStoreUri: "https://secret-store.dev-ocean.com",
|
|
||||||
threshold: 2,
|
|
||||||
password: "unittest",
|
|
||||||
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
|
||||||
})
|
|
||||||
|
|
||||||
const publisher: Account = (await ocean.getAccounts())[0]
|
|
||||||
|
|
||||||
const ddo: DDO = await ocean.registerAsset(new MetaData(), publisher)
|
|
||||||
Logger.log(ddo.id)
|
|
||||||
})()
|
|
52
src/examples/RegisterAsset.ts
Normal file
52
src/examples/RegisterAsset.ts
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
import DDO from "../ddo/DDO"
|
||||||
|
import MetaData from "../ddo/MetaData"
|
||||||
|
import MetaDataBase from "../ddo/MetaDataBase"
|
||||||
|
import {Account, Logger, Ocean} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const publisher: Account = (await ocean.getAccounts())[0]
|
||||||
|
|
||||||
|
const metaData = new MetaData({
|
||||||
|
base: {
|
||||||
|
name: "Office Humidity",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase,
|
||||||
|
} as MetaData)
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(metaData, publisher)
|
||||||
|
Logger.log(ddo.id)
|
||||||
|
})()
|
22
src/examples/RegisterServiceAgreementTemplates.ts
Normal file
22
src/examples/RegisterServiceAgreementTemplates.ts
Normal file
@ -0,0 +1,22 @@
|
|||||||
|
import {Account, Logger, Ocean, ServiceAgreementTemplate, Templates} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const templateOwner: Account = (await ocean.getAccounts())[5]
|
||||||
|
|
||||||
|
const serviceAgreementTemplate: ServiceAgreementTemplate = new ServiceAgreementTemplate(new Templates.Access())
|
||||||
|
const serviceAgreementRegistered: boolean = await serviceAgreementTemplate.register(templateOwner.getId())
|
||||||
|
|
||||||
|
Logger.log("ServiceAgreement registered:", serviceAgreementRegistered,
|
||||||
|
"templateId:", serviceAgreementTemplate.getId())
|
||||||
|
})()
|
25
src/examples/Search.ts
Normal file
25
src/examples/Search.ts
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
import DDO from "../ddo/DDO"
|
||||||
|
import {Logger, Ocean} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const result: DDO[] = await ocean.searchAssetsByText("Office Humidity")
|
||||||
|
const names: string[] = result.map((ddo: DDO): string => {
|
||||||
|
const service = ddo.findServiceByType("Metadata")
|
||||||
|
if (service && service.metadata) {
|
||||||
|
return service.metadata.base.name
|
||||||
|
}
|
||||||
|
})
|
||||||
|
|
||||||
|
Logger.log(names.length, names)
|
||||||
|
})()
|
85
src/examples/SignAgreement.ts
Normal file
85
src/examples/SignAgreement.ts
Normal file
@ -0,0 +1,85 @@
|
|||||||
|
import AdditionalInformation from "../ddo/AdditionalInformation"
|
||||||
|
import Curation from "../ddo/Curation"
|
||||||
|
import DDO from "../ddo/DDO"
|
||||||
|
import MetaData from "../ddo/MetaData"
|
||||||
|
import MetaDataBase from "../ddo/MetaDataBase"
|
||||||
|
import Service from "../ddo/Service"
|
||||||
|
import {Account, Logger, Ocean} from "../squid"
|
||||||
|
|
||||||
|
(async () => {
|
||||||
|
const ocean: Ocean = await Ocean.getInstance({
|
||||||
|
nodeUri: "http://localhost:8545",
|
||||||
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:8030",
|
||||||
|
parityUri: "http://localhost:9545",
|
||||||
|
secretStoreUri: "http://localhost:12001",
|
||||||
|
threshold: 0,
|
||||||
|
password: "unittest",
|
||||||
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
|
})
|
||||||
|
|
||||||
|
const publisher: Account = (await ocean.getAccounts())[0]
|
||||||
|
const consumer: Account = (await ocean.getAccounts())[1]
|
||||||
|
|
||||||
|
const metaData = {
|
||||||
|
additionalInformation: {
|
||||||
|
structuredMarkup: [
|
||||||
|
{
|
||||||
|
mediaType: "application/ld+json",
|
||||||
|
uri: "http://skos.um.es/unescothes/C01194/jsonld",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
mediaType: "text/turtle",
|
||||||
|
uri: "http://skos.um.es/unescothes/C01194/turtle",
|
||||||
|
},
|
||||||
|
],
|
||||||
|
updateFrecuency: "yearly",
|
||||||
|
checksum: "efdd14d39feb726e321931f408b3454d26f1a4899bcc608a68b5397f23203174",
|
||||||
|
} as AdditionalInformation,
|
||||||
|
base: {
|
||||||
|
name: "Office Humidity",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase,
|
||||||
|
curation: {
|
||||||
|
rating: 0.94,
|
||||||
|
numVotes: 124,
|
||||||
|
schema: "Binary Votting",
|
||||||
|
} as Curation,
|
||||||
|
}
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(metaData as MetaData, publisher)
|
||||||
|
Logger.log("did", ddo.id)
|
||||||
|
|
||||||
|
const accessService: Service = ddo.findServiceByType("Access")
|
||||||
|
const serviceAgreementResult: any = await ocean
|
||||||
|
.signServiceAgreement(
|
||||||
|
ddo.id,
|
||||||
|
accessService.serviceDefinitionId,
|
||||||
|
consumer)
|
||||||
|
|
||||||
|
Logger.log("ServiceAgreement Id:", serviceAgreementResult.serviceAgreementId)
|
||||||
|
Logger.log("ServiceAgreement Signature:", serviceAgreementResult.serviceAgreementSignature)
|
||||||
|
})()
|
9
src/examples/fire_lazers.sh
Executable file
9
src/examples/fire_lazers.sh
Executable file
@ -0,0 +1,9 @@
|
|||||||
|
#!/bin/bash
|
||||||
|
|
||||||
|
set -e
|
||||||
|
|
||||||
|
npm run run src/examples/RegisterServiceAgreementTemplates.ts
|
||||||
|
npm run run src/examples/RegisterAsset.ts
|
||||||
|
npm run run src/examples/Search.ts
|
||||||
|
npm run run src/examples/SignAgreement.ts
|
||||||
|
npm run run src/examples/ExecuteAgreement.ts
|
@ -15,11 +15,11 @@ export default class ContractHandler {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public static set(name: string, contractInstance: Contract) {
|
protected static set(name: string, contractInstance: Contract) {
|
||||||
ContractHandler.contracts.set(name, contractInstance)
|
ContractHandler.contracts.set(name, contractInstance)
|
||||||
}
|
}
|
||||||
|
|
||||||
public static has(name: string): boolean {
|
protected static has(name: string): boolean {
|
||||||
return ContractHandler.contracts.has(name)
|
return ContractHandler.contracts.has(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3,16 +3,14 @@ import GenericContract from "./contracts/GenericContract"
|
|||||||
|
|
||||||
export default class ContractReflector {
|
export default class ContractReflector {
|
||||||
|
|
||||||
public static async reflectContractMethod(pathToMethod: string): Promise<MethodReflection> {
|
public static async reflectContractMethod(contractName: string, methodName: string): Promise<MethodReflection> {
|
||||||
const parts: string[] = pathToMethod.split(".")
|
const contract = await GenericContract.getInstance(contractName)
|
||||||
|
|
||||||
const contract = await GenericContract.getInstance(parts[0])
|
|
||||||
return {
|
return {
|
||||||
contractName: parts[0],
|
contractName,
|
||||||
methodName: parts[1],
|
methodName,
|
||||||
address: contract.getAddress(),
|
address: contract.getAddress(),
|
||||||
signature: contract.getSignatureOfMethod(parts[1]),
|
signature: contract.getSignatureOfMethod(methodName),
|
||||||
inputs: contract.getInputsOfMethod(parts[1]),
|
inputs: contract.getInputsOfMethod(methodName),
|
||||||
} as MethodReflection
|
} as MethodReflection
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
import OceanAuth from "./contracts/Auth"
|
import OceanAuth from "./contracts/Auth"
|
||||||
import AccessConditions from "./contracts/conditions/AccessConditions"
|
import AccessConditions from "./contracts/conditions/AccessConditions"
|
||||||
|
import PaymentConditions from "./contracts/conditions/PaymentConditions"
|
||||||
import DIDRegistry from "./contracts/DIDRegistry"
|
import DIDRegistry from "./contracts/DIDRegistry"
|
||||||
import OceanMarket from "./contracts/Market"
|
import OceanMarket from "./contracts/Market"
|
||||||
import ServiceAgreement from "./contracts/ServiceAgreement"
|
import ServiceAgreement from "./contracts/ServiceAgreement"
|
||||||
@ -18,6 +19,7 @@ export default class Keeper {
|
|||||||
Keeper.instance.token = await OceanToken.getInstance()
|
Keeper.instance.token = await OceanToken.getInstance()
|
||||||
Keeper.instance.serviceAgreement = await ServiceAgreement.getInstance()
|
Keeper.instance.serviceAgreement = await ServiceAgreement.getInstance()
|
||||||
Keeper.instance.accessConditions = await AccessConditions.getInstance()
|
Keeper.instance.accessConditions = await AccessConditions.getInstance()
|
||||||
|
Keeper.instance.paymentConditions = await PaymentConditions.getInstance()
|
||||||
Keeper.instance.didRegistry = await DIDRegistry.getInstance()
|
Keeper.instance.didRegistry = await DIDRegistry.getInstance()
|
||||||
}
|
}
|
||||||
return Keeper.instance
|
return Keeper.instance
|
||||||
@ -30,12 +32,13 @@ export default class Keeper {
|
|||||||
public auth: OceanAuth
|
public auth: OceanAuth
|
||||||
public serviceAgreement: ServiceAgreement
|
public serviceAgreement: ServiceAgreement
|
||||||
public accessConditions: AccessConditions
|
public accessConditions: AccessConditions
|
||||||
|
public paymentConditions: PaymentConditions
|
||||||
public didRegistry: DIDRegistry
|
public didRegistry: DIDRegistry
|
||||||
|
|
||||||
public async getNetworkName(): Promise<string> {
|
public async getNetworkName(): Promise<string> {
|
||||||
return Web3Provider.getWeb3().eth.net.getId()
|
return Web3Provider.getWeb3().eth.net.getId()
|
||||||
.then((networkId) => {
|
.then((networkId) => {
|
||||||
let network: string = "unknown"
|
let network: string = "Unknown"
|
||||||
|
|
||||||
switch (networkId) {
|
switch (networkId) {
|
||||||
case 1:
|
case 1:
|
||||||
@ -53,8 +56,11 @@ export default class Keeper {
|
|||||||
case 42:
|
case 42:
|
||||||
network = "Kovan"
|
network = "Kovan"
|
||||||
break
|
break
|
||||||
|
case 8995:
|
||||||
|
network = "Ocean_POA_AWS"
|
||||||
|
break
|
||||||
default:
|
default:
|
||||||
network = "development"
|
network = "Development"
|
||||||
}
|
}
|
||||||
return network
|
return network
|
||||||
})
|
})
|
||||||
|
@ -60,19 +60,25 @@ export default abstract class ContractBase {
|
|||||||
if (!this.contract.methods[name]) {
|
if (!this.contract.methods[name]) {
|
||||||
throw new Error(`Method "${name}" is not part of contract "${this.contractName}"`)
|
throw new Error(`Method "${name}" is not part of contract "${this.contractName}"`)
|
||||||
}
|
}
|
||||||
|
const method = this.contract.methods[name]
|
||||||
try {
|
try {
|
||||||
const tx = this.contract.methods[name](...args)
|
const tx = method(...args)
|
||||||
const gas = await tx.estimateGas(args, {
|
const estimatedGas = await tx.estimateGas(args, {
|
||||||
from,
|
from,
|
||||||
})
|
})
|
||||||
return tx.send({
|
return tx.send({
|
||||||
from,
|
from,
|
||||||
gas,
|
gas: estimatedGas,
|
||||||
})
|
})
|
||||||
} catch (err) {
|
} catch (err) {
|
||||||
const argString = JSON.stringify(args, null, 2)
|
const mappedArgs = this.searchMethod(name).inputs.map((input, i) => {
|
||||||
|
return {
|
||||||
|
name: input.name,
|
||||||
|
value: args[i],
|
||||||
|
}
|
||||||
|
})
|
||||||
Logger.error(`Sending transaction "${name}" on contract "${this.contractName}" failed.`)
|
Logger.error(`Sending transaction "${name}" on contract "${this.contractName}" failed.`)
|
||||||
Logger.error(`Args: ${argString} From: ${from}`)
|
Logger.error(`Parameters: ${JSON.stringify(mappedArgs, null, 2)} from: ${from}`)
|
||||||
throw err
|
throw err
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -11,12 +11,14 @@ export default class ServiceAgreement extends ContractBase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public async setupAgreementTemplate(templateId: string, methodReflections: MethodReflection[],
|
public async setupAgreementTemplate(templateId: string, methodReflections: MethodReflection[],
|
||||||
dependencyMatrix: number[], name: any, ownerAddress: string)
|
dependencyMatrix: number[], name: any, fulfillmentIndices: number[],
|
||||||
|
fulfillmentOperator: number,
|
||||||
|
ownerAddress: string)
|
||||||
: Promise<Receipt> {
|
: Promise<Receipt> {
|
||||||
|
|
||||||
return this.send("setupAgreementTemplate", ownerAddress, [
|
return this.send("setupAgreementTemplate", ownerAddress, [
|
||||||
templateId, methodReflections.map((r) => r.address),
|
templateId, methodReflections.map((r) => r.address),
|
||||||
methodReflections.map((r) => r.signature), dependencyMatrix, name, [0], 0,
|
methodReflections.map((r) => r.signature), dependencyMatrix, name, fulfillmentIndices, fulfillmentOperator,
|
||||||
])
|
])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,3 +1,4 @@
|
|||||||
|
import {Receipt} from "web3-utils"
|
||||||
import ContractBase from "../ContractBase"
|
import ContractBase from "../ContractBase"
|
||||||
|
|
||||||
export default class PaymentConditions extends ContractBase {
|
export default class PaymentConditions extends ContractBase {
|
||||||
@ -7,4 +8,11 @@ export default class PaymentConditions extends ContractBase {
|
|||||||
await paymentConditions.init()
|
await paymentConditions.init()
|
||||||
return paymentConditions
|
return paymentConditions
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public async lockPayment(serviceAgreementId: string, assetId: string, price: number, consumerAddress: string)
|
||||||
|
: Promise<Receipt> {
|
||||||
|
return this.send("lockPayment", consumerAddress, [
|
||||||
|
serviceAgreementId, "0x" + assetId, price,
|
||||||
|
])
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,6 +3,10 @@ export default class Config {
|
|||||||
// the url to the aquarius
|
// the url to the aquarius
|
||||||
public aquariusUri: string
|
public aquariusUri: string
|
||||||
|
|
||||||
|
/* Brizo Config */
|
||||||
|
// the url to the brizo
|
||||||
|
public brizoUri: string
|
||||||
|
|
||||||
/* Keeper Config */
|
/* Keeper Config */
|
||||||
// the uri to the node we want to connect to, not need if web3Provider is set
|
// the uri to the node we want to connect to, not need if web3Provider is set
|
||||||
public nodeUri?: string
|
public nodeUri?: string
|
||||||
|
4
src/models/InputType.ts
Normal file
4
src/models/InputType.ts
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
export default class InputType {
|
||||||
|
public name: string
|
||||||
|
public type: string
|
||||||
|
}
|
@ -1,7 +1,9 @@
|
|||||||
|
import InputType from "./InputType"
|
||||||
|
|
||||||
export default class MethodReflection {
|
export default class MethodReflection {
|
||||||
public contractName: string
|
public contractName: string
|
||||||
public methodName: string
|
public methodName: string
|
||||||
public address: string
|
public address: string
|
||||||
public signature: string
|
public signature: string
|
||||||
public inputs: any[]
|
public inputs: InputType[]
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import BigNumber from "bignumber.js"
|
import BigNumber from "bignumber.js"
|
||||||
|
import * as EthJsUtils from "ethereumjs-util"
|
||||||
import Keeper from "../keeper/Keeper"
|
import Keeper from "../keeper/Keeper"
|
||||||
import Web3Provider from "../keeper/Web3Provider"
|
import Web3Provider from "../keeper/Web3Provider"
|
||||||
import Balance from "../models/Balance"
|
import Balance from "../models/Balance"
|
||||||
@ -33,9 +34,19 @@ export default class Account extends OceanBase {
|
|||||||
return this.balance
|
return this.balance
|
||||||
}
|
}
|
||||||
|
|
||||||
// Transactions with gas cost
|
|
||||||
public async requestTokens(amount: number): Promise<number> {
|
public async requestTokens(amount: number): Promise<number> {
|
||||||
await (await Keeper.getInstance()).market.requestTokens(amount, this.id)
|
await (await Keeper.getInstance()).market.requestTokens(amount, this.id)
|
||||||
return amount
|
return amount
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public async getPublicKey(): Promise<string> {
|
||||||
|
|
||||||
|
const web3 = Web3Provider.getWeb3()
|
||||||
|
|
||||||
|
const msg = web3.utils.sha3(this.getId())
|
||||||
|
const sig = await web3.eth.sign(msg, this.getId())
|
||||||
|
const {v, r, s} = EthJsUtils.fromRpcSig(sig)
|
||||||
|
|
||||||
|
return EthJsUtils.ecrecover(EthJsUtils.toBuffer(msg), v, r, s).toString("hex")
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,17 +1,21 @@
|
|||||||
import Aquarius from "../aquarius/Aquarius"
|
|
||||||
import AquariusProvider from "../aquarius/AquariusProvider"
|
import AquariusProvider from "../aquarius/AquariusProvider"
|
||||||
import SearchQuery from "../aquarius/query/SearchQuery"
|
import SearchQuery from "../aquarius/query/SearchQuery"
|
||||||
|
import BrizoProvider from "../brizo/BrizoProvider"
|
||||||
import ConfigProvider from "../ConfigProvider"
|
import ConfigProvider from "../ConfigProvider"
|
||||||
|
import Authentication from "../ddo/Authentication"
|
||||||
import DDOCondition from "../ddo/Condition"
|
import DDOCondition from "../ddo/Condition"
|
||||||
import DDO from "../ddo/DDO"
|
import DDO from "../ddo/DDO"
|
||||||
|
import Event from "../ddo/Event"
|
||||||
|
import EventHandlers from "../ddo/EventHandlers"
|
||||||
import MetaData from "../ddo/MetaData"
|
import MetaData from "../ddo/MetaData"
|
||||||
import Parameter from "../ddo/Parameter"
|
import Parameter from "../ddo/Parameter"
|
||||||
import Service from "../ddo/Service"
|
import Service from "../ddo/Service"
|
||||||
import Keeper from "../keeper/Keeper"
|
import Keeper from "../keeper/Keeper"
|
||||||
import Web3Provider from "../keeper/Web3Provider"
|
import Web3Provider from "../keeper/Web3Provider"
|
||||||
import Config from "../models/Config"
|
import Config from "../models/Config"
|
||||||
import ValuePair from "../models/ValuePair"
|
import InputType from "../models/InputType"
|
||||||
import ValueType from "../models/ValueType"
|
import ValueType from "../models/ValueType"
|
||||||
|
import SecretStoreProvider from "../secretstore/SecretStoreProvider"
|
||||||
import Logger from "../utils/Logger"
|
import Logger from "../utils/Logger"
|
||||||
import Account from "./Account"
|
import Account from "./Account"
|
||||||
import IdGenerator from "./IdGenerator"
|
import IdGenerator from "./IdGenerator"
|
||||||
@ -28,7 +32,6 @@ export default class Ocean {
|
|||||||
ConfigProvider.setConfig(config)
|
ConfigProvider.setConfig(config)
|
||||||
Ocean.instance = new Ocean()
|
Ocean.instance = new Ocean()
|
||||||
Ocean.instance.keeper = await Keeper.getInstance()
|
Ocean.instance.keeper = await Keeper.getInstance()
|
||||||
Ocean.instance.aquarius = await AquariusProvider.getAquarius()
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return Ocean.instance
|
return Ocean.instance
|
||||||
@ -37,7 +40,6 @@ export default class Ocean {
|
|||||||
private static instance = null
|
private static instance = null
|
||||||
|
|
||||||
private keeper: Keeper
|
private keeper: Keeper
|
||||||
private aquarius: Aquarius
|
|
||||||
|
|
||||||
private constructor() {
|
private constructor() {
|
||||||
}
|
}
|
||||||
@ -50,20 +52,23 @@ export default class Ocean {
|
|||||||
return ethAccounts.map((address: string) => new Account(address))
|
return ethAccounts.map((address: string) => new Account(address))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public async resolveDID(did): Promise<DDO> {
|
||||||
|
|
||||||
|
return AquariusProvider.getAquarius().retrieveDDO(did)
|
||||||
|
}
|
||||||
|
|
||||||
public async registerAsset(metadata: MetaData, publisher: Account): Promise<DDO> {
|
public async registerAsset(metadata: MetaData, publisher: Account): Promise<DDO> {
|
||||||
|
|
||||||
const {didRegistry} = this.keeper
|
const {didRegistry} = this.keeper
|
||||||
|
const aquarius = AquariusProvider.getAquarius()
|
||||||
|
const brizo = BrizoProvider.getBrizo()
|
||||||
|
|
||||||
const id: string = IdGenerator.generateId()
|
const id: string = IdGenerator.generateId()
|
||||||
const did: string = `did:op:${id}`
|
const did: string = `did:op:${id}`
|
||||||
const serviceDefinitionId: string = IdGenerator.generatePrefixedId()
|
const serviceDefinitionId: string = IdGenerator.generatePrefixedId()
|
||||||
|
|
||||||
metadata.base.contentUrls = metadata.base.contentUrls.map((contentUrl) => {
|
metadata.base.contentUrls =
|
||||||
|
await SecretStoreProvider.getSecretStore().encryptDocument(id, metadata.base.contentUrls)
|
||||||
// todo encrypt url in secret store
|
|
||||||
Logger.log(contentUrl)
|
|
||||||
return "0x00000"
|
|
||||||
})
|
|
||||||
|
|
||||||
const template = new Access()
|
const template = new Access()
|
||||||
const serviceAgreementTemplate = new ServiceAgreementTemplate(template)
|
const serviceAgreementTemplate = new ServiceAgreementTemplate(template)
|
||||||
@ -72,31 +77,90 @@ export default class Ocean {
|
|||||||
const conditions: Condition[] = await serviceAgreementTemplate.getConditions()
|
const conditions: Condition[] = await serviceAgreementTemplate.getConditions()
|
||||||
|
|
||||||
// create ddo conditions out of the keys
|
// create ddo conditions out of the keys
|
||||||
const ddoConditions: DDOCondition[] = conditions.map((condition: Condition): DDOCondition => {
|
const ddoConditions: DDOCondition[] = conditions
|
||||||
return {
|
.map((condition: Condition, index: number): DDOCondition => {
|
||||||
name: condition.methodReflection.methodName,
|
const events: Event[] = [
|
||||||
timeout: condition.timeout,
|
{
|
||||||
conditionKey: condition.condtionKey,
|
name: "PaymentReleased",
|
||||||
parameters: condition.methodReflection.inputs.map((input: ValuePair) => {
|
actorType: [
|
||||||
return {
|
"consumer",
|
||||||
...input,
|
],
|
||||||
value: "xxx",
|
handlers: {
|
||||||
} as Parameter
|
moduleName: "serviceAgreement",
|
||||||
}),
|
functionName: "fulfillAgreement",
|
||||||
|
version: "0.1",
|
||||||
|
} as EventHandlers,
|
||||||
|
} as Event,
|
||||||
|
]
|
||||||
|
|
||||||
} as DDOCondition
|
const mapParameterValueToName = (name) => {
|
||||||
})
|
|
||||||
const serviceEndpoint = this.aquarius.getServiceEndpoint(did)
|
switch (name) {
|
||||||
|
case "price":
|
||||||
|
return metadata.base.price
|
||||||
|
case "assetId":
|
||||||
|
return "0x" + id
|
||||||
|
case "documentKeyId":
|
||||||
|
return "0x1234"
|
||||||
|
}
|
||||||
|
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
const parameters: Parameter[] = condition.methodReflection.inputs.map((input: InputType) => {
|
||||||
|
return {
|
||||||
|
name: input.name,
|
||||||
|
type: input.type,
|
||||||
|
value: mapParameterValueToName(input.name),
|
||||||
|
} as Parameter
|
||||||
|
})
|
||||||
|
|
||||||
|
// Logger.log(`${condition.methodReflection.contractName}.${condition.methodReflection.methodName}`,
|
||||||
|
// JSON.stringify(parameters, null, 2))
|
||||||
|
|
||||||
|
return {
|
||||||
|
contractName: condition.methodReflection.contractName,
|
||||||
|
methodName: condition.methodReflection.methodName,
|
||||||
|
timeout: condition.timeout,
|
||||||
|
index,
|
||||||
|
conditionKey: condition.condtionKey,
|
||||||
|
parameters,
|
||||||
|
events,
|
||||||
|
dependencies: condition.dependencies,
|
||||||
|
dependencyTimeoutFlags: condition.dependencyTimeoutFlags,
|
||||||
|
isTerminalCondition: condition.isTerminalCondition,
|
||||||
|
} as DDOCondition
|
||||||
|
})
|
||||||
|
|
||||||
|
const serviceEndpoint = aquarius.getServiceEndpoint(did)
|
||||||
|
|
||||||
// create ddo itself
|
// create ddo itself
|
||||||
const ddo: DDO = new DDO({
|
const ddo: DDO = new DDO({
|
||||||
|
authentication: [{
|
||||||
|
type: "RsaSignatureAuthentication2018",
|
||||||
|
publicKey: did + "#keys-1",
|
||||||
|
} as Authentication],
|
||||||
id: did,
|
id: did,
|
||||||
|
publicKey: [
|
||||||
|
{
|
||||||
|
id: did + "#keys-1",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
type: "Ed25519VerificationKey2018",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
owner: did,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
publicKeyBase58: await publisher.getPublicKey(),
|
||||||
|
},
|
||||||
|
],
|
||||||
service: [
|
service: [
|
||||||
{
|
{
|
||||||
type: template.templateName,
|
type: template.templateName,
|
||||||
// tslint:disable-next-line
|
purchaseEndpoint: brizo.getPurchaseEndpoint(),
|
||||||
serviceEndpoint: "http://mybrizo.org/api/v1/brizo/services/consume?pubKey=${pubKey}&serviceId={serviceId}&url={url}",
|
serviceEndpoint: brizo.getConsumeEndpoint(publisher.getId(),
|
||||||
purchaseEndpoint: "http://mybrizo.org/api/v1/brizo/services/access/purchase?",
|
serviceDefinitionId, metadata.base.contentUrls[0]),
|
||||||
// the id of the service agreement?
|
// the id of the service agreement?
|
||||||
serviceDefinitionId,
|
serviceDefinitionId,
|
||||||
// the id of the service agreement template
|
// the id of the service agreement template
|
||||||
@ -104,41 +168,99 @@ export default class Ocean {
|
|||||||
conditions: ddoConditions,
|
conditions: ddoConditions,
|
||||||
} as Service,
|
} as Service,
|
||||||
{
|
{
|
||||||
|
type: "Compute",
|
||||||
|
serviceEndpoint: brizo.getComputeEndpoint(publisher.getId(),
|
||||||
|
serviceDefinitionId, "xxx", "xxx"),
|
||||||
|
} as Service,
|
||||||
|
{
|
||||||
|
type: "Metadata",
|
||||||
serviceEndpoint,
|
serviceEndpoint,
|
||||||
metadata,
|
metadata,
|
||||||
} as Service,
|
} as Service,
|
||||||
],
|
],
|
||||||
})
|
})
|
||||||
|
|
||||||
const storedDdo = await this.aquarius.storeDDO(ddo)
|
const storedDdo = await aquarius.storeDDO(ddo)
|
||||||
|
|
||||||
await didRegistry.registerAttribute(id, ValueType.DID, "Metadata", serviceEndpoint,
|
await didRegistry.registerAttribute(
|
||||||
|
id,
|
||||||
|
ValueType.DID,
|
||||||
|
"Metadata",
|
||||||
|
serviceEndpoint,
|
||||||
publisher.getId())
|
publisher.getId())
|
||||||
|
|
||||||
return storedDdo
|
return storedDdo
|
||||||
}
|
}
|
||||||
|
|
||||||
public async purchase(did: string, consumer: Account): Promise<ServiceAgreement> {
|
public async signServiceAgreement(did: string,
|
||||||
|
serviceDefinitionId: string,
|
||||||
|
consumer: Account): Promise<any> {
|
||||||
|
|
||||||
|
const ddo = await AquariusProvider.getAquarius().retrieveDDO(did)
|
||||||
|
const id = did.replace("did:op:", "")
|
||||||
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
|
try {
|
||||||
|
const serviceAgreementSignature: string = await ServiceAgreement.signServiceAgreement(id,
|
||||||
|
ddo, serviceDefinitionId, serviceAgreementId, consumer)
|
||||||
|
return {
|
||||||
|
serviceAgreementId,
|
||||||
|
serviceAgreementSignature,
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
|
||||||
|
Logger.error("Signing ServiceAgreement failed!", err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public async initializeServiceAgreement(did: string,
|
||||||
|
serviceDefinitionId: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
serviceAgreementSignature: string,
|
||||||
|
consumer: Account) {
|
||||||
|
const result = await BrizoProvider
|
||||||
|
.getBrizo()
|
||||||
|
.initializeServiceAgreement(
|
||||||
|
did,
|
||||||
|
serviceAgreementId,
|
||||||
|
serviceDefinitionId,
|
||||||
|
serviceAgreementSignature,
|
||||||
|
await consumer.getPublicKey())
|
||||||
|
|
||||||
|
Logger.log(result)
|
||||||
|
}
|
||||||
|
|
||||||
|
public async executeServiceAgreement(did: string,
|
||||||
|
serviceDefinitionId: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
serviceAgreementSignature: string,
|
||||||
|
consumer: Account,
|
||||||
|
publisher: Account): Promise<ServiceAgreement> {
|
||||||
|
|
||||||
const ddo = await AquariusProvider.getAquarius().retrieveDDO(did)
|
const ddo = await AquariusProvider.getAquarius().retrieveDDO(did)
|
||||||
const id = did.replace("did:op:", "")
|
const id = did.replace("did:op:", "")
|
||||||
|
|
||||||
const serviceAgreementId: string = IdGenerator.generateId()
|
const serviceAgreement: ServiceAgreement = await ServiceAgreement
|
||||||
const serviceAgreement: ServiceAgreement = await ServiceAgreement.signServiceAgreement(id,
|
.executeServiceAgreement(
|
||||||
// todo get publisher from ddo
|
id,
|
||||||
ddo, serviceAgreementId, consumer, new Account())
|
ddo,
|
||||||
|
serviceDefinitionId,
|
||||||
|
serviceAgreementId,
|
||||||
|
serviceAgreementSignature,
|
||||||
|
consumer,
|
||||||
|
publisher)
|
||||||
|
|
||||||
return serviceAgreement
|
return serviceAgreement
|
||||||
}
|
}
|
||||||
|
|
||||||
public async searchAssets(query: SearchQuery): Promise<any[]> {
|
public async searchAssets(query: SearchQuery): Promise<DDO[]> {
|
||||||
return this.aquarius.queryMetadata(query)
|
return AquariusProvider.getAquarius().queryMetadata(query)
|
||||||
}
|
}
|
||||||
|
|
||||||
public async searchAssetsByText(text: string): Promise<any[]> {
|
public async searchAssetsByText(text: string): Promise<DDO[]> {
|
||||||
return this.aquarius.queryMetadataByText({
|
return AquariusProvider.getAquarius().queryMetadataByText({
|
||||||
text,
|
text,
|
||||||
page: 1,
|
page: 0,
|
||||||
offset: 100,
|
offset: 100,
|
||||||
query: {
|
query: {
|
||||||
value: 1,
|
value: 1,
|
||||||
|
@ -3,5 +3,8 @@ import MethodReflection from "../../models/MethodReflection"
|
|||||||
export default class Condition {
|
export default class Condition {
|
||||||
public methodReflection: MethodReflection
|
public methodReflection: MethodReflection
|
||||||
public condtionKey: string
|
public condtionKey: string
|
||||||
|
public dependencies: string[]
|
||||||
|
public dependencyTimeoutFlags: number[]
|
||||||
|
public isTerminalCondition: boolean
|
||||||
public timeout: number
|
public timeout: number
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,9 @@
|
|||||||
export default class Method {
|
export default class Method {
|
||||||
public path: string
|
public name: string
|
||||||
public dependency: number
|
public contractName: string
|
||||||
|
public methodName: string
|
||||||
public timeout: number
|
public timeout: number
|
||||||
|
public dependencies: string[]
|
||||||
|
public dependencyTimeoutFlags: number[]
|
||||||
|
public isTerminalCondition: boolean
|
||||||
}
|
}
|
||||||
|
@ -1,66 +1,130 @@
|
|||||||
import Condition from "../../ddo/Condition"
|
import Condition from "../../ddo/Condition"
|
||||||
import DDO from "../../ddo/DDO"
|
import DDO from "../../ddo/DDO"
|
||||||
|
import Service from "../../ddo/Service"
|
||||||
import Keeper from "../../keeper/Keeper"
|
import Keeper from "../../keeper/Keeper"
|
||||||
import Web3Provider from "../../keeper/Web3Provider"
|
import Web3Provider from "../../keeper/Web3Provider"
|
||||||
import ValuePair from "../../models/ValuePair"
|
import ValuePair from "../../models/ValuePair"
|
||||||
|
import Logger from "../../utils/Logger"
|
||||||
import Account from "../Account"
|
import Account from "../Account"
|
||||||
import OceanBase from "../OceanBase"
|
import OceanBase from "../OceanBase"
|
||||||
|
|
||||||
export default class ServiceAgreement extends OceanBase {
|
export default class ServiceAgreement extends OceanBase {
|
||||||
|
|
||||||
public static async signServiceAgreement(assetId: string, ddo: DDO, serviceAgreementId: string, consumer: Account,
|
public static async signServiceAgreement(assetId: string,
|
||||||
publisher: Account):
|
ddo: DDO,
|
||||||
Promise<ServiceAgreement> {
|
serviceDefinitionId: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
consumer: Account): Promise<string> {
|
||||||
|
|
||||||
const values: ValuePair[] = ServiceAgreement.getValuesFromDDO(ddo, serviceAgreementId)
|
// Logger.log("signing SA", serviceAgreementId)
|
||||||
|
|
||||||
|
const service: Service = ddo.findServiceById(serviceDefinitionId)
|
||||||
|
const values: ValuePair[] = ServiceAgreement.getValuesFromService(service, serviceAgreementId)
|
||||||
const valueHashes = ServiceAgreement.createValueHashes(values)
|
const valueHashes = ServiceAgreement.createValueHashes(values)
|
||||||
const timeoutValues: number[] = ServiceAgreement.getTimeoutValuesFromDDO(ddo)
|
const timeoutValues: number[] = ServiceAgreement.getTimeoutValuesFromService(service)
|
||||||
|
|
||||||
const serviceAgreementHashSignature = await ServiceAgreement.createSAHashSignature(ddo, serviceAgreementId,
|
const serviceAgreementHashSignature = await ServiceAgreement
|
||||||
values, valueHashes, timeoutValues, consumer)
|
.createSAHashSignature(
|
||||||
|
service,
|
||||||
const serviceAgreement: ServiceAgreement = await ServiceAgreement.executeAgreement(ddo,
|
serviceAgreementId,
|
||||||
serviceAgreementId, values, valueHashes, timeoutValues, serviceAgreementHashSignature, consumer, publisher)
|
values,
|
||||||
|
valueHashes,
|
||||||
return serviceAgreement
|
timeoutValues,
|
||||||
}
|
consumer)
|
||||||
|
|
||||||
public static async createSAHashSignature(ddo: DDO, serviceAgreementId: string, values: ValuePair[],
|
|
||||||
valueHashes: string[], timeoutValues: number[], consumer: Account):
|
|
||||||
Promise<string> {
|
|
||||||
|
|
||||||
const conditionKeys: string[] = ddo.service[0].conditions.map((condition) => {
|
|
||||||
return condition.conditionKey
|
|
||||||
})
|
|
||||||
|
|
||||||
const serviceAgreementHash = ServiceAgreement.hashServiceAgreement(ddo.service[0].templateId,
|
|
||||||
serviceAgreementId, conditionKeys, valueHashes, timeoutValues)
|
|
||||||
|
|
||||||
const serviceAgreementHashSignature =
|
|
||||||
await Web3Provider.getWeb3().eth.sign(serviceAgreementHash, consumer.getId())
|
|
||||||
|
|
||||||
return serviceAgreementHashSignature
|
return serviceAgreementHashSignature
|
||||||
}
|
}
|
||||||
|
|
||||||
private static async executeAgreement(ddo: DDO, serviceAgreementId: string, values: ValuePair[],
|
public static async executeServiceAgreement(assetId: string,
|
||||||
valueHashes: string[], timeoutValues: number[],
|
ddo: DDO,
|
||||||
serviceAgreementHashSignature: string, consumer: Account,
|
serviceDefinitionId: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
serviceAgreementHashSignature: string,
|
||||||
|
consumer: Account,
|
||||||
|
publisher: Account): Promise<ServiceAgreement> {
|
||||||
|
|
||||||
|
// Logger.log("executing SA", serviceAgreementId)
|
||||||
|
|
||||||
|
const service: Service = ddo.findServiceById(serviceDefinitionId)
|
||||||
|
const values: ValuePair[] = ServiceAgreement.getValuesFromService(service, serviceAgreementId)
|
||||||
|
const valueHashes = ServiceAgreement.createValueHashes(values)
|
||||||
|
const timeoutValues: number[] = ServiceAgreement.getTimeoutValuesFromService(service)
|
||||||
|
|
||||||
|
// todo get consumer from ddo
|
||||||
|
const serviceAgreement: ServiceAgreement = await ServiceAgreement.executeAgreement(ddo,
|
||||||
|
serviceDefinitionId, serviceAgreementId, valueHashes, timeoutValues, serviceAgreementHashSignature,
|
||||||
|
consumer.getId(), publisher)
|
||||||
|
|
||||||
|
return serviceAgreement
|
||||||
|
}
|
||||||
|
|
||||||
|
private static async createSAHashSignature(service: Service,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
values: ValuePair[],
|
||||||
|
valueHashes: string[],
|
||||||
|
timeoutValues: number[],
|
||||||
|
consumer: Account):
|
||||||
|
Promise<string> {
|
||||||
|
|
||||||
|
if (!service.templateId) {
|
||||||
|
throw new Error("TemplateId not found in ddo.")
|
||||||
|
}
|
||||||
|
|
||||||
|
const conditionKeys: string[] = service.conditions.map((condition) => {
|
||||||
|
return condition.conditionKey
|
||||||
|
})
|
||||||
|
|
||||||
|
const serviceAgreementHash = ServiceAgreement
|
||||||
|
.hashServiceAgreement(
|
||||||
|
service.templateId,
|
||||||
|
serviceAgreementId,
|
||||||
|
conditionKeys,
|
||||||
|
valueHashes,
|
||||||
|
timeoutValues)
|
||||||
|
|
||||||
|
const serviceAgreementHashSignature = await Web3Provider
|
||||||
|
.getWeb3().eth.sign(serviceAgreementHash, consumer.getId())
|
||||||
|
|
||||||
|
return serviceAgreementHashSignature
|
||||||
|
}
|
||||||
|
|
||||||
|
private static async executeAgreement(ddo: DDO,
|
||||||
|
serviceDefinitionId: string,
|
||||||
|
serviceAgreementId: string,
|
||||||
|
valueHashes: string[],
|
||||||
|
timeoutValues: number[],
|
||||||
|
serviceAgreementHashSignature: string,
|
||||||
|
consumerAddress: string,
|
||||||
publisher: Account): Promise<ServiceAgreement> {
|
publisher: Account): Promise<ServiceAgreement> {
|
||||||
|
|
||||||
const {serviceAgreement} = await Keeper.getInstance()
|
const {serviceAgreement} = await Keeper.getInstance()
|
||||||
const executeAgreementReceipt = await serviceAgreement.executeAgreement(
|
|
||||||
ddo.service[0].templateId, serviceAgreementHashSignature, consumer.getId(), valueHashes,
|
const service: Service = ddo.findServiceById(serviceDefinitionId)
|
||||||
timeoutValues, serviceAgreementId, ddo.id, publisher.getId())
|
|
||||||
|
if (!service.templateId) {
|
||||||
|
throw new Error(`TemplateId not found in service "${service.type}" ddo.`)
|
||||||
|
}
|
||||||
|
|
||||||
|
const executeAgreementReceipt = await serviceAgreement
|
||||||
|
.executeAgreement(
|
||||||
|
service.templateId,
|
||||||
|
serviceAgreementHashSignature,
|
||||||
|
consumerAddress,
|
||||||
|
valueHashes,
|
||||||
|
timeoutValues,
|
||||||
|
serviceAgreementId,
|
||||||
|
ddo.id,
|
||||||
|
publisher.getId())
|
||||||
|
|
||||||
if (executeAgreementReceipt.events.ExecuteAgreement.returnValues.state === false) {
|
if (executeAgreementReceipt.events.ExecuteAgreement.returnValues.state === false) {
|
||||||
throw new Error("signing service agreement failed.")
|
throw new Error("executing service agreement failed.")
|
||||||
}
|
}
|
||||||
|
|
||||||
return new ServiceAgreement(
|
return new ServiceAgreement(
|
||||||
executeAgreementReceipt.events.ExecuteAgreement.returnValues.serviceAgreementId,
|
executeAgreementReceipt.events.ExecuteAgreement.returnValues.serviceAgreementId,
|
||||||
ddo,
|
ddo,
|
||||||
publisher,
|
publisher,
|
||||||
consumer,
|
new Account(consumerAddress),
|
||||||
executeAgreementReceipt.events.ExecuteAgreement.returnValues.state,
|
executeAgreementReceipt.events.ExecuteAgreement.returnValues.state,
|
||||||
executeAgreementReceipt.events.ExecuteAgreement.returnValues.status,
|
executeAgreementReceipt.events.ExecuteAgreement.returnValues.status,
|
||||||
)
|
)
|
||||||
@ -73,12 +137,18 @@ export default class ServiceAgreement extends OceanBase {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static hashSingleValue(data: ValuePair): string {
|
private static hashSingleValue(data: ValuePair): string {
|
||||||
return Web3Provider.getWeb3().utils.soliditySha3(data).toString("hex")
|
try {
|
||||||
|
return Web3Provider.getWeb3().utils.soliditySha3(data).toString("hex")
|
||||||
|
} catch (err) {
|
||||||
|
Logger.error(`Hashing of ${JSON.stringify(data, null, 2)} failed.`)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private static hashServiceAgreement(serviceAgreementTemplateId: string, serviceAgreementId: string,
|
private static hashServiceAgreement(serviceAgreementTemplateId: string,
|
||||||
conditionKeys: string[], valueHashes: string[], timeouts: number[])
|
serviceAgreementId: string,
|
||||||
: string {
|
conditionKeys: string[],
|
||||||
|
valueHashes: string[],
|
||||||
|
timeouts: number[]): string {
|
||||||
const args = [
|
const args = [
|
||||||
{type: "bytes32", value: serviceAgreementTemplateId} as ValuePair,
|
{type: "bytes32", value: serviceAgreementTemplateId} as ValuePair,
|
||||||
{type: "bytes32[]", value: conditionKeys} as ValuePair,
|
{type: "bytes32[]", value: conditionKeys} as ValuePair,
|
||||||
@ -90,31 +160,51 @@ export default class ServiceAgreement extends OceanBase {
|
|||||||
return Web3Provider.getWeb3().utils.soliditySha3(...args).toString("hex")
|
return Web3Provider.getWeb3().utils.soliditySha3(...args).toString("hex")
|
||||||
}
|
}
|
||||||
|
|
||||||
private static getTimeoutValuesFromDDO(ddo: DDO): number[] {
|
private static getTimeoutValuesFromService(service: Service): number[] {
|
||||||
const timeoutValues: number[] = ddo.service[0].conditions.map((condition: Condition) => {
|
const timeoutValues: number[] = service.conditions.map((condition: Condition) => {
|
||||||
return condition.timeout
|
return condition.timeout
|
||||||
})
|
})
|
||||||
|
|
||||||
return timeoutValues
|
return timeoutValues
|
||||||
}
|
}
|
||||||
|
|
||||||
private static getValuesFromDDO(ddo: DDO, serviceAgreementId: string): ValuePair[] {
|
private static getValuesFromService(service: Service, serviceAgreementId: string): ValuePair[] {
|
||||||
const values: ValuePair[] = [
|
|
||||||
{type: "bool", value: true} as ValuePair,
|
const values: ValuePair[] = []
|
||||||
{type: "bool", value: false} as ValuePair,
|
|
||||||
{type: "bool", value: false} as ValuePair,
|
service.conditions.forEach((condition) => {
|
||||||
{type: "uint", value: 120} as ValuePair,
|
condition.parameters.forEach((parameter) => {
|
||||||
{type: "string", value: serviceAgreementId} as ValuePair,
|
values.push({
|
||||||
]
|
type: parameter.type,
|
||||||
|
value: parameter.name === "serviceId" ? "0x" + serviceAgreementId : parameter.value,
|
||||||
|
} as ValuePair)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
// Logger.log("Values", JSON.stringify(values, null, 2))
|
||||||
|
|
||||||
return values
|
return values
|
||||||
}
|
}
|
||||||
|
|
||||||
private constructor(serviceAgreementId: string, ddo: DDO, private publisher: Account, consumer: Account,
|
private constructor(serviceAgreementId: string,
|
||||||
state: boolean, status: boolean) {
|
ddo: DDO,
|
||||||
|
private publisher: Account,
|
||||||
|
consumer: Account,
|
||||||
|
state: boolean,
|
||||||
|
status: boolean) {
|
||||||
super(serviceAgreementId)
|
super(serviceAgreementId)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public async lockPayment(assetId: string, price: number, consumer: Account): Promise<boolean> {
|
||||||
|
const {paymentConditions} = await Keeper.getInstance()
|
||||||
|
|
||||||
|
const lockPaymentRceipt =
|
||||||
|
await paymentConditions.lockPayment(this.getId(), assetId, price,
|
||||||
|
consumer.getId())
|
||||||
|
|
||||||
|
return lockPaymentRceipt.status
|
||||||
|
}
|
||||||
|
|
||||||
public async grantAccess(assetId: string, documentId: string): Promise<boolean> {
|
public async grantAccess(assetId: string, documentId: string): Promise<boolean> {
|
||||||
const {accessConditions} = await Keeper.getInstance()
|
const {accessConditions} = await Keeper.getInstance()
|
||||||
|
|
||||||
|
@ -31,35 +31,54 @@ export default class ServiceAgreementTemplate extends OceanBase {
|
|||||||
|
|
||||||
const dependencyMatrix: number[] =
|
const dependencyMatrix: number[] =
|
||||||
await Promise.all(this.template.Methods.map(async (method: Method) => {
|
await Promise.all(this.template.Methods.map(async (method: Method) => {
|
||||||
// tslint:disable-next-line
|
return this.compressDependencies(method.dependencies, method.dependencyTimeoutFlags)
|
||||||
return method.dependency | method.timeout
|
|
||||||
}))
|
}))
|
||||||
|
|
||||||
|
const fulfillmentIndices: number[] = this.template.Methods
|
||||||
|
.map((method: Method, i: number) => method.isTerminalCondition ? i : undefined)
|
||||||
|
.filter((index: number) => index !== undefined)
|
||||||
|
|
||||||
const {serviceAgreement} = await Keeper.getInstance()
|
const {serviceAgreement} = await Keeper.getInstance()
|
||||||
|
|
||||||
const methodReflections = await this.getMethodReflections()
|
const methodReflections = await this.getMethodReflections()
|
||||||
|
|
||||||
const owner = await this.getOwner()
|
const owner = await this.getOwner()
|
||||||
|
|
||||||
if (!owner.getId().startsWith("0x0")) {
|
if (owner.getId() === templateOwnerAddress) {
|
||||||
Logger.error(`Template with id "${this.template.id}" already registered.`)
|
// tslint:disable-next-line
|
||||||
|
Logger.error(`Template with id "${this.template.id}" is already registered to your account "${templateOwnerAddress}".`)
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
const receipt = await serviceAgreement.setupAgreementTemplate(
|
if (!owner.getId().startsWith("0x0")) {
|
||||||
this.template.id, methodReflections, dependencyMatrix,
|
Logger.error(`Template with id "${this.template.id}" already registered by someone else.`)
|
||||||
Web3Provider.getWeb3().utils.fromAscii(this.template.templateName),
|
return false
|
||||||
templateOwnerAddress)
|
|
||||||
|
|
||||||
const templateId = receipt.events.SetupAgreementTemplate.returnValues.serviceTemplateId
|
|
||||||
|
|
||||||
if (templateId !== this.template.id) {
|
|
||||||
// tslint:disable-next-line
|
|
||||||
throw new Error(`TemplateId missmatch on ${this.template.templateName}! Should be "${this.template.id}" but is ${templateId}`)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (receipt.status) {
|
const receipt = await serviceAgreement
|
||||||
Logger.error("Registering template failed")
|
.setupAgreementTemplate(
|
||||||
|
this.template.id,
|
||||||
|
methodReflections,
|
||||||
|
dependencyMatrix,
|
||||||
|
Web3Provider.getWeb3().utils.fromAscii(this.template.templateName),
|
||||||
|
fulfillmentIndices,
|
||||||
|
this.template.fulfillmentOperator,
|
||||||
|
templateOwnerAddress)
|
||||||
|
|
||||||
|
const {serviceTemplateId, provider} = receipt.events.SetupAgreementTemplate.returnValues
|
||||||
|
|
||||||
|
if (serviceTemplateId !== this.template.id) {
|
||||||
|
// tslint:disable-next-line
|
||||||
|
throw new Error(`TemplateId missmatch on ${this.template.templateName}! Should be "${this.template.id}" but is ${serviceTemplateId}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (provider !== templateOwnerAddress) {
|
||||||
|
// tslint:disable-next-line
|
||||||
|
throw new Error(`Template owner missmatch on ${this.template.templateName}! Should be "${templateOwnerAddress}" but is ${provider}`)
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!receipt.status) {
|
||||||
|
Logger.error(`Registering template failed, status was "false".`)
|
||||||
}
|
}
|
||||||
|
|
||||||
return receipt.status
|
return receipt.status
|
||||||
@ -83,23 +102,54 @@ export default class ServiceAgreementTemplate extends OceanBase {
|
|||||||
const methodReflections = await this.getMethodReflections()
|
const methodReflections = await this.getMethodReflections()
|
||||||
|
|
||||||
const conditions: Condition[] = methodReflections.map((methodReflection, i) => {
|
const conditions: Condition[] = methodReflections.map((methodReflection, i) => {
|
||||||
|
const method: Method = this.template.Methods[i]
|
||||||
return {
|
return {
|
||||||
methodReflection,
|
methodReflection,
|
||||||
timeout: this.template.Methods[i].timeout,
|
timeout: method.timeout,
|
||||||
condtionKey: ServiceAgreementTemplate.generateConditionsKey(this.getId(),
|
dependencies: method.dependencies,
|
||||||
methodReflection),
|
dependencyTimeoutFlags: method.dependencyTimeoutFlags,
|
||||||
|
isTerminalCondition: method.isTerminalCondition,
|
||||||
|
condtionKey: ServiceAgreementTemplate
|
||||||
|
.generateConditionsKey(this.getId(), methodReflection),
|
||||||
} as Condition
|
} as Condition
|
||||||
})
|
})
|
||||||
|
|
||||||
return conditions
|
return conditions
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private compressDependencies(dependencies: string[], dependencyTimeoutFlags: number[]): number {
|
||||||
|
|
||||||
|
if (dependencies.length !== dependencyTimeoutFlags.length) {
|
||||||
|
throw new Error("Deps and timeouts need the same length")
|
||||||
|
}
|
||||||
|
|
||||||
|
// map name to index
|
||||||
|
const mappedDependencies: number[] = dependencies.map((dep: string) => {
|
||||||
|
return this.template.Methods.findIndex((m) => m.name === dep)
|
||||||
|
})
|
||||||
|
|
||||||
|
let compressedDependencyValue = 0
|
||||||
|
const numBits = 2 // 1st for dependency, 2nd for timeout flag
|
||||||
|
for (let i = 0; i < mappedDependencies.length; i++) {
|
||||||
|
const dependencyIndex = mappedDependencies[i]
|
||||||
|
const timeout = dependencyTimeoutFlags[i]
|
||||||
|
const offset = i * numBits
|
||||||
|
// tslint:disable-next-line
|
||||||
|
compressedDependencyValue |= dependencyIndex * 2 ** (offset + 0) // the dependency bit
|
||||||
|
// tslint:disable-next-line
|
||||||
|
compressedDependencyValue |= timeout * 2 ** (offset + 1) // the timeout bit
|
||||||
|
}
|
||||||
|
|
||||||
|
return compressedDependencyValue
|
||||||
|
}
|
||||||
|
|
||||||
private async getMethodReflections(): Promise<MethodReflection[]> {
|
private async getMethodReflections(): Promise<MethodReflection[]> {
|
||||||
const methodReflections: MethodReflection[] =
|
const methodReflections: MethodReflection[] = []
|
||||||
await Promise.all(this.template.Methods.map(async (method: Method) => {
|
for (const method of this.template.Methods) {
|
||||||
const methodReflection = await ContractReflector.reflectContractMethod(method.path)
|
methodReflections.push(
|
||||||
return methodReflection
|
await ContractReflector.reflectContractMethod(method.contractName, method.methodName),
|
||||||
}))
|
)
|
||||||
|
}
|
||||||
return methodReflections
|
return methodReflections
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -7,24 +7,40 @@ export default class Access extends TemplateBase {
|
|||||||
public id: string = "0x044852b2a670ade5407e78fb2863c51de9fcb96542a07186fe3aeda6bb8a116d"
|
public id: string = "0x044852b2a670ade5407e78fb2863c51de9fcb96542a07186fe3aeda6bb8a116d"
|
||||||
public Methods: Method[] = [
|
public Methods: Method[] = [
|
||||||
{
|
{
|
||||||
path: "PaymentConditions.lockPayment",
|
name: "lockPayment",
|
||||||
dependency: 0,
|
contractName: "PaymentConditions",
|
||||||
|
methodName: "lockPayment",
|
||||||
|
timeout: 0,
|
||||||
|
dependencies: [],
|
||||||
|
dependencyTimeoutFlags: [],
|
||||||
|
isTerminalCondition: false,
|
||||||
|
} as Method,
|
||||||
|
{
|
||||||
|
name: "grantAccess",
|
||||||
|
contractName: "AccessConditions",
|
||||||
|
methodName: "grantAccess",
|
||||||
timeout: 10,
|
timeout: 10,
|
||||||
|
dependencies: ["lockPayment"],
|
||||||
|
dependencyTimeoutFlags: [0],
|
||||||
|
isTerminalCondition: false,
|
||||||
} as Method,
|
} as Method,
|
||||||
{
|
{
|
||||||
path: "AccessConditions.grantAccess",
|
name: "releasePayment",
|
||||||
dependency: 1,
|
contractName: "PaymentConditions",
|
||||||
timeout: 500,
|
methodName: "releasePayment",
|
||||||
|
timeout: 10,
|
||||||
|
dependencies: ["grantAccess"],
|
||||||
|
dependencyTimeoutFlags: [0],
|
||||||
|
isTerminalCondition: true,
|
||||||
} as Method,
|
} as Method,
|
||||||
{
|
{
|
||||||
path: "PaymentConditions.releasePayment",
|
name: "refundPayment",
|
||||||
dependency: 4,
|
contractName: "PaymentConditions",
|
||||||
timeout: 17,
|
methodName: "refundPayment",
|
||||||
} as Method,
|
timeout: 10,
|
||||||
{
|
dependencies: ["lockPayment", "grantAccess"],
|
||||||
path: "PaymentConditions.refundPayment",
|
dependencyTimeoutFlags: [0, 1],
|
||||||
dependency: 1,
|
isTerminalCondition: true,
|
||||||
timeout: 40,
|
|
||||||
} as Method,
|
} as Method,
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -7,24 +7,40 @@ export default class FitchainCompute extends TemplateBase {
|
|||||||
public id: string = "0xc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc6"
|
public id: string = "0xc89efdaa54c0f20c7adf612882df0950f5a951637e0307cdcb4c672f298b8bc6"
|
||||||
public Methods: Method[] = [
|
public Methods: Method[] = [
|
||||||
{
|
{
|
||||||
path: "PaymentConditions.lockPayment",
|
name: "lockPayment",
|
||||||
dependency: 0,
|
contractName: "PaymentConditions",
|
||||||
|
methodName: "lockPayment",
|
||||||
|
timeout: 0,
|
||||||
|
dependencies: [],
|
||||||
|
dependencyTimeoutFlags: [],
|
||||||
|
isTerminalCondition: false,
|
||||||
|
} as Method,
|
||||||
|
{
|
||||||
|
name: "grantAccess",
|
||||||
|
contractName: "AccessConditions",
|
||||||
|
methodName: "grantAccess",
|
||||||
timeout: 10,
|
timeout: 10,
|
||||||
|
dependencies: ["lockPayment"],
|
||||||
|
dependencyTimeoutFlags: [0],
|
||||||
|
isTerminalCondition: false,
|
||||||
} as Method,
|
} as Method,
|
||||||
{
|
{
|
||||||
path: "AccessConditions.grantAccess",
|
name: "releasePayment",
|
||||||
dependency: 1,
|
contractName: "PaymentConditions",
|
||||||
timeout: 500,
|
methodName: "releasePayment",
|
||||||
|
timeout: 10,
|
||||||
|
dependencies: ["grantAccess"],
|
||||||
|
dependencyTimeoutFlags: [0],
|
||||||
|
isTerminalCondition: true,
|
||||||
} as Method,
|
} as Method,
|
||||||
{
|
{
|
||||||
path: "PaymentConditions.releasePayment",
|
name: "refundPayment",
|
||||||
dependency: 4,
|
contractName: "PaymentConditions",
|
||||||
timeout: 17,
|
methodName: "refundPayment",
|
||||||
} as Method,
|
timeout: 10,
|
||||||
{
|
dependencies: ["lockPayment", "grantAccess"],
|
||||||
path: "PaymentConditions.refundPayment",
|
dependencyTimeoutFlags: [0, 1],
|
||||||
dependency: 1,
|
isTerminalCondition: true,
|
||||||
timeout: 40,
|
|
||||||
} as Method,
|
} as Method,
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
@ -3,5 +3,6 @@ import Method from "../Method"
|
|||||||
export default abstract class TemplateBase {
|
export default abstract class TemplateBase {
|
||||||
public Methods: Method[]
|
public Methods: Method[]
|
||||||
public templateName: string
|
public templateName: string
|
||||||
|
public fulfillmentOperator: number = 1
|
||||||
public id: string = "0x00000000000000000000000000000000000000000000000000000000000000"
|
public id: string = "0x00000000000000000000000000000000000000000000000000000000000000"
|
||||||
}
|
}
|
||||||
|
@ -1,11 +1,18 @@
|
|||||||
import Account from "./ocean/Account"
|
import Account from "./ocean/Account"
|
||||||
import Ocean from "./ocean/Ocean"
|
import Ocean from "./ocean/Ocean"
|
||||||
import ServiceAgreement from "./ocean/ServiceAgreements/ServiceAgreement"
|
import ServiceAgreement from "./ocean/ServiceAgreements/ServiceAgreement"
|
||||||
|
import ServiceAgreementTemplate from "./ocean/ServiceAgreements/ServiceAgreementTemplate"
|
||||||
|
import Access from "./ocean/ServiceAgreements/Templates/Access"
|
||||||
|
import FitchainCompute from "./ocean/ServiceAgreements/Templates/FitchainCompute"
|
||||||
import Logger from "./utils/Logger"
|
import Logger from "./utils/Logger"
|
||||||
|
|
||||||
|
const Templates = {Access, FitchainCompute}
|
||||||
|
|
||||||
export {
|
export {
|
||||||
Ocean,
|
Ocean,
|
||||||
ServiceAgreement,
|
ServiceAgreement,
|
||||||
|
ServiceAgreementTemplate,
|
||||||
Logger,
|
Logger,
|
||||||
|
Templates,
|
||||||
Account,
|
Account,
|
||||||
}
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import fetch from "node-fetch"
|
import fetch from "node-fetch"
|
||||||
|
|
||||||
export default class AquariusConnector {
|
export default class WebServiceConnector {
|
||||||
|
|
||||||
public async post(url, payload): Promise<any> {
|
public async post(url, payload): Promise<any> {
|
||||||
return this.fetch(url, {
|
return this.fetch(url, {
|
19
src/utils/WebServiceConnectorProvider.ts
Normal file
19
src/utils/WebServiceConnectorProvider.ts
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
import WebServiceConnector from "./WebServiceConnector"
|
||||||
|
|
||||||
|
export default class WebServiceConnectorProvider {
|
||||||
|
|
||||||
|
public static setConnector(connector: WebServiceConnector) {
|
||||||
|
|
||||||
|
WebServiceConnectorProvider.instance = connector
|
||||||
|
}
|
||||||
|
|
||||||
|
public static getConnector(): WebServiceConnector {
|
||||||
|
|
||||||
|
if (!WebServiceConnectorProvider.instance) {
|
||||||
|
WebServiceConnectorProvider.instance = new WebServiceConnector()
|
||||||
|
}
|
||||||
|
return WebServiceConnectorProvider.instance
|
||||||
|
}
|
||||||
|
|
||||||
|
private static instance: WebServiceConnector = null
|
||||||
|
}
|
@ -1,66 +1,84 @@
|
|||||||
import * as assert from "assert"
|
import * as assert from "assert"
|
||||||
import Aquarius from "../../src/aquarius/Aquarius"
|
import Aquarius from "../../src/aquarius/Aquarius"
|
||||||
import AquariusConnectorProvider from "../../src/aquarius/AquariusConnectorProvider"
|
|
||||||
import SearchQuery from "../../src/aquarius/query/SearchQuery"
|
import SearchQuery from "../../src/aquarius/query/SearchQuery"
|
||||||
import DDO from "../../src/ddo/DDO"
|
import DDO from "../../src/ddo/DDO"
|
||||||
import IdGenerator from "../../src/ocean/IdGenerator"
|
import IdGenerator from "../../src/ocean/IdGenerator"
|
||||||
|
import WebServiceConnectorProvider from "../../src/utils/WebServiceConnectorProvider"
|
||||||
import config from "../config"
|
import config from "../config"
|
||||||
import AquariusConnectorMock from "../mocks/AquariusConnector.mock"
|
import WebServiceConnectorMock from "../mocks/WebServiceConnector.mock"
|
||||||
// import * as jsonDDO from "../testdata/ddo.json"
|
|
||||||
|
|
||||||
describe("Aquarius", () => {
|
describe("Aquarius", () => {
|
||||||
|
|
||||||
const aquarius: Aquarius = new Aquarius(config)
|
const aquarius: Aquarius = new Aquarius(config)
|
||||||
describe("#queryMetadata()", () => {
|
describe("#queryMetadata()", () => {
|
||||||
|
|
||||||
|
const query = {
|
||||||
|
offset: 100,
|
||||||
|
page: 0,
|
||||||
|
query: {
|
||||||
|
value: 1,
|
||||||
|
},
|
||||||
|
sort: {
|
||||||
|
value: 1,
|
||||||
|
},
|
||||||
|
text: "Office",
|
||||||
|
} as SearchQuery
|
||||||
|
|
||||||
it("should query metadata", async () => {
|
it("should query metadata", async () => {
|
||||||
|
|
||||||
const query = {
|
|
||||||
offset: 100,
|
|
||||||
page: 0,
|
|
||||||
query: {
|
|
||||||
value: 1,
|
|
||||||
},
|
|
||||||
sort: {
|
|
||||||
value: 1,
|
|
||||||
},
|
|
||||||
text: "Office",
|
|
||||||
} as SearchQuery
|
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock())
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock([new DDO()]))
|
||||||
|
|
||||||
const result: any[] = await aquarius.queryMetadata(query)
|
const result: DDO[] = await aquarius.queryMetadata(query)
|
||||||
assert(result)
|
assert(result)
|
||||||
assert(result.length !== null)
|
assert(result.length !== null)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it("should query metadata and return real ddo", async () => {
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock([new DDO()]))
|
||||||
|
|
||||||
|
const result: DDO[] = await aquarius.queryMetadata(query)
|
||||||
|
assert(result)
|
||||||
|
assert(result[0].findServiceById)
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
describe("#queryMetadataByText()", () => {
|
describe("#queryMetadataByText()", () => {
|
||||||
|
|
||||||
|
const query = {
|
||||||
|
offset: 100,
|
||||||
|
page: 0,
|
||||||
|
query: {
|
||||||
|
value: 1,
|
||||||
|
},
|
||||||
|
sort: {
|
||||||
|
value: 1,
|
||||||
|
},
|
||||||
|
text: "Office",
|
||||||
|
} as SearchQuery
|
||||||
|
|
||||||
it("should query metadata by text", async () => {
|
it("should query metadata by text", async () => {
|
||||||
|
|
||||||
const query = {
|
|
||||||
offset: 100,
|
|
||||||
page: 0,
|
|
||||||
query: {
|
|
||||||
value: 1,
|
|
||||||
},
|
|
||||||
sort: {
|
|
||||||
value: 1,
|
|
||||||
},
|
|
||||||
text: "Office",
|
|
||||||
} as SearchQuery
|
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock())
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock([new DDO()]))
|
||||||
|
|
||||||
const result: any[] = await aquarius.queryMetadataByText(query)
|
const result: DDO[] = await aquarius.queryMetadataByText(query)
|
||||||
assert(result)
|
assert(result)
|
||||||
assert(result.length !== null)
|
assert(result.length !== null)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
it("should query metadata and return real ddo", async () => {
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock([new DDO()]))
|
||||||
|
|
||||||
|
const result: DDO[] = await aquarius.queryMetadataByText(query)
|
||||||
|
assert(result)
|
||||||
|
assert(result[0].findServiceById)
|
||||||
|
})
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
describe("#storeDDO()", () => {
|
describe("#storeDDO()", () => {
|
||||||
@ -73,7 +91,7 @@ describe("Aquarius", () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock(ddo))
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
|
||||||
const result: DDO = await aquarius.storeDDO(ddo)
|
const result: DDO = await aquarius.storeDDO(ddo)
|
||||||
assert(result)
|
assert(result)
|
||||||
@ -91,7 +109,7 @@ describe("Aquarius", () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock(ddo))
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
|
||||||
const storageResult: DDO = await aquarius.storeDDO(ddo)
|
const storageResult: DDO = await aquarius.storeDDO(ddo)
|
||||||
assert(storageResult)
|
assert(storageResult)
|
||||||
|
@ -2,10 +2,11 @@ import Config from "../src/models/Config"
|
|||||||
|
|
||||||
export default {
|
export default {
|
||||||
aquariusUri: "http://localhost:5000",
|
aquariusUri: "http://localhost:5000",
|
||||||
|
brizoUri: "http://localhost:3000",
|
||||||
nodeUri: "http://localhost:8545",
|
nodeUri: "http://localhost:8545",
|
||||||
parityUri: "http://localhost:9545",
|
parityUri: "http://localhost:9545",
|
||||||
secretStoreUri: "https://secret-store.dev-ocean.com",
|
secretStoreUri: "http://localhost:12001",
|
||||||
threshold: 2,
|
threshold: 0,
|
||||||
password: "unittest",
|
password: "unittest",
|
||||||
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
address: "0xed243adfb84a6626eba46178ccb567481c6e655d",
|
||||||
web3Provider: null,
|
web3Provider: null,
|
||||||
|
@ -107,6 +107,7 @@ describe("DDO", () => {
|
|||||||
workExample: "423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
workExample: "423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
contentUrls: [
|
contentUrls: [
|
||||||
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
],
|
],
|
||||||
links: [
|
links: [
|
||||||
{
|
{
|
||||||
|
@ -33,7 +33,7 @@ describe("Keeper", () => {
|
|||||||
|
|
||||||
it("should get development as default", async () => {
|
it("should get development as default", async () => {
|
||||||
const networkName: string = await keeper.getNetworkName()
|
const networkName: string = await keeper.getNetworkName()
|
||||||
assert(networkName === "development")
|
assert(networkName === "Development")
|
||||||
})
|
})
|
||||||
|
|
||||||
})
|
})
|
||||||
|
@ -17,7 +17,9 @@ export default class TestContractHandler extends ContractHandler {
|
|||||||
await TestContractHandler.deployContracts(deployerAddress)
|
await TestContractHandler.deployContracts(deployerAddress)
|
||||||
|
|
||||||
// register templates
|
// register templates
|
||||||
|
Logger.log(`Registering Access Template from ${deployerAddress}`)
|
||||||
await new ServiceAgreementTemplate(new Access()).register(deployerAddress)
|
await new ServiceAgreementTemplate(new Access()).register(deployerAddress)
|
||||||
|
Logger.log(`Registering FitchainCompute Template from ${deployerAddress}`)
|
||||||
await new ServiceAgreementTemplate(new FitchainCompute()).register(deployerAddress)
|
await new ServiceAgreementTemplate(new FitchainCompute()).register(deployerAddress)
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -78,7 +80,7 @@ export default class TestContractHandler extends ContractHandler {
|
|||||||
|
|
||||||
// dont redeploy if there is already something loaded
|
// dont redeploy if there is already something loaded
|
||||||
if (ContractHandler.has(name)) {
|
if (ContractHandler.has(name)) {
|
||||||
return ContractHandler.get(name)
|
return await ContractHandler.get(name)
|
||||||
}
|
}
|
||||||
|
|
||||||
const web3 = Web3Provider.getWeb3()
|
const web3 = Web3Provider.getWeb3()
|
||||||
|
@ -1,8 +1,20 @@
|
|||||||
import Aquarius from "../../src/aquarius/Aquarius"
|
import Aquarius from "../../src/aquarius/Aquarius"
|
||||||
|
import DDO from "../../src/ddo/DDO"
|
||||||
|
|
||||||
|
const ddoStore: Map<string, any> = new Map<string, any>()
|
||||||
|
|
||||||
export default class AquariusMock extends Aquarius {
|
export default class AquariusMock extends Aquarius {
|
||||||
|
|
||||||
public async getAccessUrl(accessToken: any, payload: any): Promise<string> {
|
public async getAccessUrl(accessToken: any, payload: any): Promise<string> {
|
||||||
return "http://test/test"
|
return "http://test/test"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public async storeDDO(ddo: DDO): Promise<DDO> {
|
||||||
|
ddoStore.set(ddo.id, ddo)
|
||||||
|
return ddo
|
||||||
|
}
|
||||||
|
|
||||||
|
public async retrieveDDO(did: string): Promise<DDO> {
|
||||||
|
return ddoStore.get(did)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
10
test/mocks/Brizo.mock.ts
Normal file
10
test/mocks/Brizo.mock.ts
Normal file
@ -0,0 +1,10 @@
|
|||||||
|
import Brizo from "../../src/brizo/Brizo"
|
||||||
|
|
||||||
|
export default class BrizoMock extends Brizo {
|
||||||
|
|
||||||
|
public async initializeServiceAgreement(did: string, serviceAgreementId: string, serviceDefinitionId: string,
|
||||||
|
signature: string, consumerPublicKey: string): Promise<any> {
|
||||||
|
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
}
|
@ -1,7 +1,7 @@
|
|||||||
import AquariusConnector from "../../src/aquarius/AquariusConnector"
|
import WebServiceConnector from "../../src/utils/WebServiceConnector"
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
export default class AquariusConnectorMock extends AquariusConnector {
|
export default class WebServiceConnectorMock extends WebServiceConnector {
|
||||||
|
|
||||||
constructor(private returnData: any) {
|
constructor(private returnData: any) {
|
||||||
super()
|
super()
|
||||||
@ -14,10 +14,10 @@ export default class AquariusConnectorMock extends AquariusConnector {
|
|||||||
resolve({
|
resolve({
|
||||||
ok: true,
|
ok: true,
|
||||||
json: () => {
|
json: () => {
|
||||||
return this.returnData ? this.returnData : []
|
return this.returnData ? this.returnData : {}
|
||||||
},
|
},
|
||||||
text: () => {
|
text: () => {
|
||||||
return this.returnData ? this.returnData.toString() : ""
|
return this.returnData ? JSON.stringify(this.returnData.toString()) : ""
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
})
|
})
|
@ -75,4 +75,14 @@ describe("Account", () => {
|
|||||||
assert(tokensGranted === tokens)
|
assert(tokensGranted === tokens)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe("#getPublicKey()", () => {
|
||||||
|
|
||||||
|
it("should get the public key of an account", async () => {
|
||||||
|
const publicKey = await accounts[1].getPublicKey()
|
||||||
|
assert(publicKey)
|
||||||
|
|
||||||
|
assert(publicKey.length === 128)
|
||||||
|
})
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
@ -1,16 +1,22 @@
|
|||||||
import {assert} from "chai"
|
import {assert} from "chai"
|
||||||
import AquariusProvider from "../../src/aquarius/AquariusProvider"
|
import AquariusProvider from "../../src/aquarius/AquariusProvider"
|
||||||
import SearchQuery from "../../src/aquarius/query/SearchQuery"
|
import SearchQuery from "../../src/aquarius/query/SearchQuery"
|
||||||
|
import BrizoProvider from "../../src/brizo/BrizoProvider"
|
||||||
import ConfigProvider from "../../src/ConfigProvider"
|
import ConfigProvider from "../../src/ConfigProvider"
|
||||||
import DDO from "../../src/ddo/DDO"
|
import DDO from "../../src/ddo/DDO"
|
||||||
import MetaData from "../../src/ddo/MetaData"
|
import MetaData from "../../src/ddo/MetaData"
|
||||||
|
import Service from "../../src/ddo/Service"
|
||||||
import Account from "../../src/ocean/Account"
|
import Account from "../../src/ocean/Account"
|
||||||
import Ocean from "../../src/ocean/Ocean"
|
import Ocean from "../../src/ocean/Ocean"
|
||||||
|
import ServiceAgreement from "../../src/ocean/ServiceAgreements/ServiceAgreement"
|
||||||
import SecretStoreProvider from "../../src/secretstore/SecretStoreProvider"
|
import SecretStoreProvider from "../../src/secretstore/SecretStoreProvider"
|
||||||
|
import WebServiceConnectorProvider from "../../src/utils/WebServiceConnectorProvider"
|
||||||
import config from "../config"
|
import config from "../config"
|
||||||
import TestContractHandler from "../keeper/TestContractHandler"
|
import TestContractHandler from "../keeper/TestContractHandler"
|
||||||
import AquariusMock from "../mocks/Aquarius.mock"
|
import AquariusMock from "../mocks/Aquarius.mock"
|
||||||
|
import BrizoMock from "../mocks/Brizo.mock"
|
||||||
import SecretStoreMock from "../mocks/SecretStore.mock"
|
import SecretStoreMock from "../mocks/SecretStore.mock"
|
||||||
|
import WebServiceConnectorMock from "../mocks/WebServiceConnector.mock"
|
||||||
|
|
||||||
let ocean: Ocean
|
let ocean: Ocean
|
||||||
let accounts: Account[]
|
let accounts: Account[]
|
||||||
@ -21,6 +27,7 @@ describe("Ocean", () => {
|
|||||||
before(async () => {
|
before(async () => {
|
||||||
ConfigProvider.setConfig(config)
|
ConfigProvider.setConfig(config)
|
||||||
AquariusProvider.setAquarius(new AquariusMock(config))
|
AquariusProvider.setAquarius(new AquariusMock(config))
|
||||||
|
BrizoProvider.setBrizo(new BrizoMock(config))
|
||||||
SecretStoreProvider.setSecretStore(new SecretStoreMock(config))
|
SecretStoreProvider.setSecretStore(new SecretStoreMock(config))
|
||||||
await TestContractHandler.prepareContracts()
|
await TestContractHandler.prepareContracts()
|
||||||
ocean = await Ocean.getInstance(config)
|
ocean = await Ocean.getInstance(config)
|
||||||
@ -52,6 +59,21 @@ describe("Ocean", () => {
|
|||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe("#resolveDID()", () => {
|
||||||
|
|
||||||
|
it("should resolve a did to a ddo", async () => {
|
||||||
|
|
||||||
|
const metaData: MetaData = new MetaData()
|
||||||
|
const ddo: DDO = await ocean.registerAsset(metaData, testPublisher)
|
||||||
|
|
||||||
|
const resolvedDDO: DDO = await ocean.resolveDID(ddo.id)
|
||||||
|
|
||||||
|
assert(resolvedDDO)
|
||||||
|
assert(resolvedDDO.id === ddo.id)
|
||||||
|
})
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
describe("#registerAsset()", () => {
|
describe("#registerAsset()", () => {
|
||||||
|
|
||||||
it("should register an asset", async () => {
|
it("should register an asset", async () => {
|
||||||
@ -97,4 +119,54 @@ describe("Ocean", () => {
|
|||||||
})
|
})
|
||||||
|
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe("#signServiceAgreement()", () => {
|
||||||
|
|
||||||
|
it("should sign an service agreement", async () => {
|
||||||
|
|
||||||
|
const publisher = accounts[0]
|
||||||
|
const consumer = accounts[1]
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(new MetaData(), publisher)
|
||||||
|
|
||||||
|
const service: Service = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
|
||||||
|
const serviceAgreementSignature: any = await ocean.signServiceAgreement(ddo.id,
|
||||||
|
service.serviceDefinitionId, consumer)
|
||||||
|
|
||||||
|
assert(serviceAgreementSignature)
|
||||||
|
assert(serviceAgreementSignature.serviceAgreementId)
|
||||||
|
assert(serviceAgreementSignature.serviceAgreementSignature)
|
||||||
|
assert(serviceAgreementSignature.serviceAgreementSignature.startsWith("0x"))
|
||||||
|
})
|
||||||
|
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("#executeServiceAgreement()", () => {
|
||||||
|
|
||||||
|
it("should execute an service agreement", async () => {
|
||||||
|
|
||||||
|
const publisher = accounts[0]
|
||||||
|
const consumer = accounts[1]
|
||||||
|
|
||||||
|
const ddo: DDO = await ocean.registerAsset(new MetaData(), publisher)
|
||||||
|
const service: Service = ddo.findServiceByType("Access")
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
|
||||||
|
const signServiceAgreementResult: any = await ocean.signServiceAgreement(ddo.id,
|
||||||
|
service.serviceDefinitionId, consumer)
|
||||||
|
|
||||||
|
const serviceAgreement: ServiceAgreement = await ocean.executeServiceAgreement(ddo.id,
|
||||||
|
service.serviceDefinitionId, signServiceAgreementResult.serviceAgreementId,
|
||||||
|
signServiceAgreementResult.serviceAgreementSignature, consumer, publisher)
|
||||||
|
|
||||||
|
assert(serviceAgreement)
|
||||||
|
})
|
||||||
|
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
@ -1,10 +1,13 @@
|
|||||||
import {assert} from "chai"
|
import {assert} from "chai"
|
||||||
import AquariusConnectorProvider from "../../src/aquarius/AquariusConnectorProvider"
|
|
||||||
import ConfigProvider from "../../src/ConfigProvider"
|
import ConfigProvider from "../../src/ConfigProvider"
|
||||||
import DDOCondition from "../../src/ddo/Condition"
|
import DDOCondition from "../../src/ddo/Condition"
|
||||||
import DDO from "../../src/ddo/DDO"
|
import DDO from "../../src/ddo/DDO"
|
||||||
|
import Event from "../../src/ddo/Event"
|
||||||
|
import EventHandlers from "../../src/ddo/EventHandlers"
|
||||||
|
import MetaData from "../../src/ddo/MetaData"
|
||||||
import Parameter from "../../src/ddo/Parameter"
|
import Parameter from "../../src/ddo/Parameter"
|
||||||
import Service from "../../src/ddo/Service"
|
import Service from "../../src/ddo/Service"
|
||||||
|
import InputType from "../../src/models/InputType"
|
||||||
import Account from "../../src/ocean/Account"
|
import Account from "../../src/ocean/Account"
|
||||||
import IdGenerator from "../../src/ocean/IdGenerator"
|
import IdGenerator from "../../src/ocean/IdGenerator"
|
||||||
import Ocean from "../../src/ocean/Ocean"
|
import Ocean from "../../src/ocean/Ocean"
|
||||||
@ -12,16 +15,20 @@ import Condition from "../../src/ocean/ServiceAgreements/Condition"
|
|||||||
import ServiceAgreement from "../../src/ocean/ServiceAgreements/ServiceAgreement"
|
import ServiceAgreement from "../../src/ocean/ServiceAgreements/ServiceAgreement"
|
||||||
import ServiceAgreementTemplate from "../../src/ocean/ServiceAgreements/ServiceAgreementTemplate"
|
import ServiceAgreementTemplate from "../../src/ocean/ServiceAgreements/ServiceAgreementTemplate"
|
||||||
import Access from "../../src/ocean/ServiceAgreements/Templates/Access"
|
import Access from "../../src/ocean/ServiceAgreements/Templates/Access"
|
||||||
|
import WebServiceConnectorProvider from "../../src/utils/WebServiceConnectorProvider"
|
||||||
import config from "../config"
|
import config from "../config"
|
||||||
import TestContractHandler from "../keeper/TestContractHandler"
|
import TestContractHandler from "../keeper/TestContractHandler"
|
||||||
import AquariusConnectorMock from "../mocks/AquariusConnector.mock"
|
import WebServiceConnectorMock from "../mocks/WebServiceConnector.mock"
|
||||||
|
|
||||||
let ocean: Ocean
|
let ocean: Ocean
|
||||||
let accounts: Account[]
|
let accounts: Account[]
|
||||||
let publisherAccount: Account
|
let publisherAccount: Account
|
||||||
let consumerAccount: Account
|
let consumerAccount: Account
|
||||||
|
|
||||||
let serviceDefinition
|
let accessService: Service
|
||||||
|
let metaDataService: Service
|
||||||
|
|
||||||
|
const assetId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
describe("ServiceAgreement", () => {
|
describe("ServiceAgreement", () => {
|
||||||
|
|
||||||
@ -34,6 +41,7 @@ describe("ServiceAgreement", () => {
|
|||||||
publisherAccount = accounts[1]
|
publisherAccount = accounts[1]
|
||||||
consumerAccount = accounts[2]
|
consumerAccount = accounts[2]
|
||||||
|
|
||||||
|
const metadata = new MetaData()
|
||||||
const serviceAgreementTemplate: ServiceAgreementTemplate =
|
const serviceAgreementTemplate: ServiceAgreementTemplate =
|
||||||
new ServiceAgreementTemplate(new Access())
|
new ServiceAgreementTemplate(new Access())
|
||||||
|
|
||||||
@ -41,44 +49,108 @@ describe("ServiceAgreement", () => {
|
|||||||
const conditions: Condition[] = await serviceAgreementTemplate.getConditions()
|
const conditions: Condition[] = await serviceAgreementTemplate.getConditions()
|
||||||
|
|
||||||
// create ddo conditions out of the keys
|
// create ddo conditions out of the keys
|
||||||
const ddoConditions: DDOCondition[] = conditions.map((condition): DDOCondition => {
|
const ddoConditions: DDOCondition[] = conditions.map((condition, index): DDOCondition => {
|
||||||
|
|
||||||
|
const events: Event[] = [
|
||||||
|
{
|
||||||
|
name: "PaymentReleased",
|
||||||
|
actorType: [
|
||||||
|
"consumer",
|
||||||
|
],
|
||||||
|
handlers: {
|
||||||
|
moduleName: "serviceAgreement",
|
||||||
|
functionName: "fulfillAgreement",
|
||||||
|
version: "0.1",
|
||||||
|
} as EventHandlers,
|
||||||
|
} as Event,
|
||||||
|
]
|
||||||
|
|
||||||
|
const mapParameterValueToName = (name) => {
|
||||||
|
|
||||||
|
switch (name) {
|
||||||
|
case "price":
|
||||||
|
return metadata.base.price
|
||||||
|
case "assetId":
|
||||||
|
return "0x" + assetId
|
||||||
|
case "documentKeyId":
|
||||||
|
return "0x1234"
|
||||||
|
}
|
||||||
|
|
||||||
|
return null
|
||||||
|
}
|
||||||
|
|
||||||
|
const parameters: Parameter[] = condition.methodReflection.inputs.map((input: InputType) => {
|
||||||
|
return {
|
||||||
|
name: input.name,
|
||||||
|
type: input.type,
|
||||||
|
value: mapParameterValueToName(input.name),
|
||||||
|
} as Parameter
|
||||||
|
})
|
||||||
|
|
||||||
return {
|
return {
|
||||||
name: condition.methodReflection.methodName,
|
contractName: condition.methodReflection.contractName,
|
||||||
|
methodName: condition.methodReflection.methodName,
|
||||||
timeout: condition.timeout,
|
timeout: condition.timeout,
|
||||||
|
index,
|
||||||
conditionKey: condition.condtionKey,
|
conditionKey: condition.condtionKey,
|
||||||
parameters: condition.methodReflection.inputs.map((input) => {
|
parameters,
|
||||||
return {
|
events,
|
||||||
...input,
|
dependencies: condition.dependencies,
|
||||||
value: "xx",
|
dependencyTimeoutFlags: condition.dependencyTimeoutFlags,
|
||||||
}as Parameter
|
isTerminalCondition: condition.isTerminalCondition,
|
||||||
}),
|
|
||||||
} as DDOCondition
|
} as DDOCondition
|
||||||
})
|
})
|
||||||
|
|
||||||
serviceDefinition = [
|
accessService = {
|
||||||
{
|
type: "Access",
|
||||||
serviceDefinitionId: IdGenerator.generateId(),
|
serviceDefinitionId: IdGenerator.generateId(),
|
||||||
templateId: serviceAgreementTemplate.getId(),
|
templateId: serviceAgreementTemplate.getId(),
|
||||||
conditions: ddoConditions,
|
conditions: ddoConditions,
|
||||||
} as Service,
|
} as Service
|
||||||
]
|
|
||||||
|
|
||||||
|
metaDataService = {
|
||||||
|
type: "MetaData",
|
||||||
|
metadata,
|
||||||
|
} as Service
|
||||||
})
|
})
|
||||||
|
|
||||||
describe("#signServiceAgreement()", () => {
|
describe("#signServiceAgreement()", () => {
|
||||||
|
it("should sign an service agreement", async () => {
|
||||||
|
|
||||||
|
const id: string = IdGenerator.generateId()
|
||||||
|
const did: string = `did:op:${id}`
|
||||||
|
const ddo = new DDO({id: did, service: [accessService]})
|
||||||
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
|
||||||
|
const serviceAgreementSignature: string =
|
||||||
|
await ServiceAgreement.signServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, consumerAccount)
|
||||||
|
|
||||||
|
assert(serviceAgreementSignature)
|
||||||
|
assert(serviceAgreementSignature.startsWith("0x"))
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("#executeServiceAgreement()", () => {
|
||||||
it("should execute an service agreement", async () => {
|
it("should execute an service agreement", async () => {
|
||||||
|
|
||||||
const id: string = IdGenerator.generateId()
|
const id: string = IdGenerator.generateId()
|
||||||
const did: string = `did:op:${id}`
|
const did: string = `did:op:${id}`
|
||||||
const ddo = new DDO({id: did, service: serviceDefinition})
|
const ddo = new DDO({id: did, service: [accessService]})
|
||||||
const assetId: string = IdGenerator.generateId()
|
|
||||||
const serviceAgreementId: string = IdGenerator.generateId()
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock(ddo))
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
const serviceAgreementSignature: string =
|
||||||
|
await ServiceAgreement.signServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, consumerAccount)
|
||||||
|
|
||||||
const serviceAgreement: ServiceAgreement =
|
const serviceAgreement: ServiceAgreement =
|
||||||
await ServiceAgreement.signServiceAgreement(assetId, ddo, serviceAgreementId, consumerAccount,
|
await ServiceAgreement.executeServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
publisherAccount)
|
serviceAgreementId, serviceAgreementSignature, consumerAccount, publisherAccount)
|
||||||
assert(serviceAgreement)
|
assert(serviceAgreement)
|
||||||
|
|
||||||
const serviceDefinitionId = serviceAgreement.getId()
|
const serviceDefinitionId = serviceAgreement.getId()
|
||||||
@ -92,15 +164,19 @@ describe("ServiceAgreement", () => {
|
|||||||
|
|
||||||
const id: string = IdGenerator.generateId()
|
const id: string = IdGenerator.generateId()
|
||||||
const did: string = `did:op:${id}`
|
const did: string = `did:op:${id}`
|
||||||
const ddo = new DDO({id: did, service: serviceDefinition})
|
const ddo = new DDO({id: did, service: [accessService]})
|
||||||
const assetId: string = IdGenerator.generateId()
|
|
||||||
const serviceAgreementId: string = IdGenerator.generateId()
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock(ddo))
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
const serviceAgreementSignature: string =
|
||||||
|
await ServiceAgreement.signServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, consumerAccount)
|
||||||
|
assert(serviceAgreementSignature)
|
||||||
|
|
||||||
const serviceAgreement: ServiceAgreement =
|
const serviceAgreement: ServiceAgreement =
|
||||||
await ServiceAgreement.signServiceAgreement(assetId, ddo, serviceAgreementId, consumerAccount,
|
await ServiceAgreement.executeServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
publisherAccount)
|
serviceAgreementId, serviceAgreementSignature, consumerAccount, publisherAccount)
|
||||||
assert(serviceAgreement)
|
assert(serviceAgreement)
|
||||||
|
|
||||||
const status = await serviceAgreement.getStatus()
|
const status = await serviceAgreement.getStatus()
|
||||||
@ -108,24 +184,57 @@ describe("ServiceAgreement", () => {
|
|||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
describe("#grantAccess()", () => {
|
describe("#lockPayment()", () => {
|
||||||
it("should grant access in that service agreement", async () => {
|
xit("should lock the payment in that service agreement", async () => {
|
||||||
|
|
||||||
const id: string = IdGenerator.generateId()
|
const id: string = IdGenerator.generateId()
|
||||||
const did: string = `did:op:${id}`
|
const did: string = `did:op:${id}`
|
||||||
const ddo = new DDO({id: did, service: serviceDefinition})
|
const ddo = new DDO({id: did, service: [accessService, metaDataService]})
|
||||||
const assetId: string = IdGenerator.generateId()
|
|
||||||
const serviceAgreementId: string = IdGenerator.generateId()
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
AquariusConnectorProvider.setConnector(new AquariusConnectorMock(ddo))
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
const serviceAgreementSignature: string =
|
||||||
|
await ServiceAgreement.signServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, consumerAccount)
|
||||||
|
assert(serviceAgreementSignature)
|
||||||
|
|
||||||
const serviceAgreement: ServiceAgreement =
|
const serviceAgreement: ServiceAgreement =
|
||||||
await ServiceAgreement.signServiceAgreement(assetId, ddo, serviceAgreementId, consumerAccount,
|
await ServiceAgreement.executeServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
publisherAccount)
|
serviceAgreementId, serviceAgreementSignature, consumerAccount, publisherAccount)
|
||||||
assert(serviceAgreement)
|
assert(serviceAgreement)
|
||||||
|
|
||||||
const fulfilled: boolean = await serviceAgreement.grantAccess(assetId, IdGenerator.generateId())
|
const paid: boolean = await serviceAgreement.lockPayment(assetId, metaDataService.metadata.base.price,
|
||||||
assert(fulfilled)
|
consumerAccount)
|
||||||
|
assert(paid)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
|
describe("#grantAccess()", () => {
|
||||||
|
xit("should grant access in that service agreement", async () => {
|
||||||
|
|
||||||
|
const id: string = IdGenerator.generateId()
|
||||||
|
const did: string = `did:op:${id}`
|
||||||
|
const ddo = new DDO({id: did, service: [accessService]})
|
||||||
|
const serviceAgreementId: string = IdGenerator.generateId()
|
||||||
|
|
||||||
|
// @ts-ignore
|
||||||
|
WebServiceConnectorProvider.setConnector(new WebServiceConnectorMock(ddo))
|
||||||
|
const serviceAgreementSignature: string =
|
||||||
|
await ServiceAgreement.signServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, consumerAccount)
|
||||||
|
assert(serviceAgreementSignature)
|
||||||
|
|
||||||
|
const serviceAgreement: ServiceAgreement =
|
||||||
|
await ServiceAgreement.executeServiceAgreement(assetId, ddo, accessService.serviceDefinitionId,
|
||||||
|
serviceAgreementId, serviceAgreementSignature, consumerAccount, publisherAccount)
|
||||||
|
assert(serviceAgreement)
|
||||||
|
|
||||||
|
const paid: boolean = await serviceAgreement.lockPayment(assetId, 10, consumerAccount)
|
||||||
|
assert(paid)
|
||||||
|
|
||||||
|
const accessGranted: boolean = await serviceAgreement.grantAccess(assetId, IdGenerator.generateId())
|
||||||
|
assert(accessGranted)
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
@ -39,6 +39,20 @@ describe("ServiceAgreementTemplate", () => {
|
|||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
|
describe("#getConditions()", () => {
|
||||||
|
it("should setup an Access agreement template correctly", async () => {
|
||||||
|
|
||||||
|
const access: TemplateBase = new Access()
|
||||||
|
access.id = IdGenerator.generatePrefixedId()
|
||||||
|
const serviceAgreementTemplate: ServiceAgreementTemplate =
|
||||||
|
new ServiceAgreementTemplate(access)
|
||||||
|
assert(serviceAgreementTemplate)
|
||||||
|
|
||||||
|
const conds = await serviceAgreementTemplate.getConditions()
|
||||||
|
assert(conds)
|
||||||
|
})
|
||||||
|
})
|
||||||
|
|
||||||
describe("#getStatus()", () => {
|
describe("#getStatus()", () => {
|
||||||
it("should get the status of a newly deployed agreement template", async () => {
|
it("should get the status of a newly deployed agreement template", async () => {
|
||||||
|
|
||||||
|
34
test/testdata/MetaData.ts
vendored
Normal file
34
test/testdata/MetaData.ts
vendored
Normal file
@ -0,0 +1,34 @@
|
|||||||
|
import MetaDataModel from "../../src/ddo/MetaData"
|
||||||
|
import MetaDataBase from "../../src/ddo/MetaDataBase"
|
||||||
|
|
||||||
|
const MetaData = new MetaDataModel({
|
||||||
|
base: {
|
||||||
|
name: "Office Humidity",
|
||||||
|
type: "dataset",
|
||||||
|
description: "Weather information of UK including temperature and humidity",
|
||||||
|
size: "3.1gb",
|
||||||
|
dateCreated: "2012-02-01T10:55:11+00:00",
|
||||||
|
author: "Met Office",
|
||||||
|
license: "CC-BY",
|
||||||
|
copyrightHolder: "Met Office",
|
||||||
|
encoding: "UTF-8",
|
||||||
|
compression: "zip",
|
||||||
|
contentType: "text/csv",
|
||||||
|
// tslint:disable-next-line
|
||||||
|
workExample: "stationId,latitude,longitude,datetime,temperature,humidity423432fsd,51.509865,-0.118092,2011-01-01T10:55:11+00:00,7.2,68",
|
||||||
|
contentUrls: [
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
"https://testocnfiles.blob.core.windows.net/testfiles/testzkp.zip",
|
||||||
|
],
|
||||||
|
links: [
|
||||||
|
{sample1: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-daily/"},
|
||||||
|
{sample2: "http://data.ceda.ac.uk/badc/ukcp09/data/gridded-land-obs/gridded-land-obs-averages-25km/"},
|
||||||
|
{fieldsDescription: "http://data.ceda.ac.uk/badc/ukcp09/"},
|
||||||
|
],
|
||||||
|
inLanguage: "en",
|
||||||
|
tags: "weather, uk, 2011, temperature, humidity",
|
||||||
|
price: 10,
|
||||||
|
} as MetaDataBase,
|
||||||
|
} as MetaDataModel)
|
||||||
|
|
||||||
|
export default MetaData
|
Loading…
Reference in New Issue
Block a user