From e2dc810fc2eeb4dbd3c4c61fa5b06af8019bff6c Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 9 Aug 2023 21:11:59 +0100 Subject: [PATCH 01/18] Reworked HTTP API router to support multiple API versions, made json-schema-service more generic, added /v1/info route --- .../http-api/base-http-api-controller.js | 1 + src/controllers/http-api/http-api-router.js | 66 ++++++++++++------- ...bid-suggestion-http-api-controller-old.js} | 2 +- .../get-http-api-controller-old.js} | 4 +- .../info-http-api-controller-old.js} | 6 +- .../local-store-http-api-controller-old.js} | 4 +- .../publish-http-api-controller-old.js} | 4 +- .../query-http-api-controller-old.js} | 4 +- .../bid-suggestion-schema-old.js} | 0 .../request-schema/get-schema-old.js} | 2 +- .../request-schema/local-store-schema-old.js} | 2 +- .../request-schema/publish-schema-old.js} | 0 .../request-schema/query-schema-old.js} | 2 +- .../request-schema/update-schema-old.js} | 0 .../result-http-api-controller-old.js} | 17 +++-- .../update-http-api-controller-old.js} | 4 +- .../v1/info-http-api-controller-v1.js | 29 ++++++++ .../http-client/http-client-module-manager.js | 28 ++++++++ src/service/file-service.js | 4 ++ src/service/json-schema-service.js | 47 ++++++++----- src/service/util/string-util.js | 13 ++++ 21 files changed, 173 insertions(+), 66 deletions(-) rename src/controllers/http-api/{bid-suggestion-http-api-controller.js => old/bid-suggestion-http-api-controller-old.js} (97%) rename src/controllers/http-api/{get-http-api-controller.js => old/get-http-api-controller-old.js} (96%) rename src/controllers/http-api/{info-http-api-controller.js => old/info-http-api-controller-old.js} (62%) rename src/controllers/http-api/{local-store-http-api-controller.js => old/local-store-http-api-controller-old.js} (95%) rename src/controllers/http-api/{publish-http-api-controller.js => old/publish-http-api-controller-old.js} (96%) rename src/controllers/http-api/{query-http-api-controller.js => old/query-http-api-controller-old.js} (88%) rename src/controllers/http-api/{request-schema/bid-suggestion-schema.js => old/request-schema/bid-suggestion-schema-old.js} (100%) rename src/controllers/http-api/{request-schema/get-schema.js => old/request-schema/get-schema-old.js} (88%) rename src/controllers/http-api/{request-schema/local-store-schema.js => old/request-schema/local-store-schema-old.js} (93%) rename src/controllers/http-api/{request-schema/publish-schema.js => old/request-schema/publish-schema-old.js} (100%) rename src/controllers/http-api/{request-schema/query-schema.js => old/request-schema/query-schema-old.js} (93%) rename src/controllers/http-api/{request-schema/update-schema.js => old/request-schema/update-schema-old.js} (100%) rename src/controllers/http-api/{result-http-api-controller.js => old/result-http-api-controller-old.js} (77%) rename src/controllers/http-api/{update-http-api-controller.js => old/update-http-api-controller-old.js} (96%) create mode 100644 src/controllers/http-api/v1/info-http-api-controller-v1.js create mode 100644 src/service/util/string-util.js diff --git a/src/controllers/http-api/base-http-api-controller.js b/src/controllers/http-api/base-http-api-controller.js index fe742fd5a9..3a080b9f5a 100644 --- a/src/controllers/http-api/base-http-api-controller.js +++ b/src/controllers/http-api/base-http-api-controller.js @@ -1,5 +1,6 @@ class BaseController { constructor(ctx) { + this.config = ctx.config; this.logger = ctx.logger; } diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index 04cc727c7e..4c96ddbbd8 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -1,85 +1,103 @@ +import stringUtil from '../../service/util/string-util.js'; + class HttpApiRouter { constructor(ctx) { this.config = ctx.config; this.httpClientModuleManager = ctx.httpClientModuleManager; - this.getHttpApiController = ctx.getHttpApiController; - this.publishHttpApiController = ctx.publishHttpApiController; - this.updateHttpApiController = ctx.updateHttpApiController; - this.localStoreHttpApiController = ctx.localStoreHttpApiController; - this.queryHttpApiController = ctx.queryHttpApiController; - this.resultHttpApiController = ctx.resultHttpApiController; - this.infoHttpApiController = ctx.infoHttpApiController; - this.bidSuggestionHttpApiController = ctx.bidSuggestionHttpApiController; + const versions = this.httpClientModuleManager.getApiVersions(); + + for (const version of versions) { + const versionedMethodControllers = + this.httpClientModuleManager.getMethodControllers(version); + + for (const versionedController of versionedMethodControllers) { + this[versionedController] = ctx[versionedController]; + } + } this.jsonSchemaService = ctx.jsonSchemaService; } async initialize() { this.initializeBeforeMiddlewares(); - this.initializeListeners(); + await this.initializeListeners(); this.initializeAfterMiddlewares(); await this.httpClientModuleManager.listen(); } - initializeListeners() { + async initializeListeners() { + await this.initializeVersionedListeners('v1'); + await this.initializeOldListeners(); + } + + async initializeOldListeners() { this.httpClientModuleManager.post( '/publish', (req, res) => { - this.publishHttpApiController.handlePublishRequest(req, res); + this.publishHttpApiControllerOld.handlePublishRequest(req, res); }, - { rateLimit: true, requestSchema: this.jsonSchemaService.publishSchema() }, + { rateLimit: true, requestSchema: await this.jsonSchemaService.publishSchema('old') }, ); this.httpClientModuleManager.post( '/update', (req, res) => { - this.updateHttpApiController.handleUpdateRequest(req, res); + this.updateHttpApiControllerOld.handleUpdateRequest(req, res); }, - { rateLimit: true, requestSchema: this.jsonSchemaService.updateSchema() }, + { rateLimit: true, requestSchema: await this.jsonSchemaService.updateSchema('old') }, ); this.httpClientModuleManager.post( '/query', (req, res) => { - this.queryHttpApiController.handleQueryRequest(req, res); + this.queryHttpApiControllerOld.handleQueryRequest(req, res); }, - { requestSchema: this.jsonSchemaService.querySchema() }, + { requestSchema: await this.jsonSchemaService.querySchema('old') }, ); this.httpClientModuleManager.post( '/local-store', (req, res) => { - this.localStoreHttpApiController.handleLocalStoreRequest(req, res); + this.localHttpApiControllerOld.handleLocalStoreRequest(req, res); }, - { requestSchema: this.jsonSchemaService.localStoreSchema() }, + { requestSchema: await this.jsonSchemaService.localStoreSchema('old') }, ); this.httpClientModuleManager.post( '/get', (req, res) => { - this.getHttpApiController.handleGetRequest(req, res); + this.getHttpApiControllerOld.handleGetRequest(req, res); }, - { rateLimit: true, requestSchema: this.jsonSchemaService.getSchema() }, + { rateLimit: true, requestSchema: await this.jsonSchemaService.getSchema('old') }, ); this.httpClientModuleManager.get('/:operation/:operationId', (req, res) => { - this.resultHttpApiController.handleOperationResultRequest(req, res); + this.resultHttpApiControllerOld.handleOperationResultRequest(req, res); }); this.httpClientModuleManager.get('/info', (req, res) => { - this.infoHttpApiController.handleInfoRequest(req, res); + this.infoHttpApiControllerOld.handleInfoRequest(req, res); }); this.httpClientModuleManager.get( '/bid-suggestion', (req, res) => { - this.bidSuggestionHttpApiController.handleBidSuggestionRequest(req, res); + this.bidSuggestionHttpApiControllerOld.handleBidSuggestionRequest(req, res); }, - { requestSchema: this.jsonSchemaService.bidSuggestionSchema() }, + { requestSchema: await this.jsonSchemaService.bidSuggestionSchema('old') }, ); } + async initializeVersionedListeners(version) { + this.httpClientModuleManager.get(`/${version}/info`, (req, res) => { + this[`infoHttpApiController${stringUtil.capitalize(version)}`].handleInfoRequest( + req, + res, + ); + }); + } + initializeBeforeMiddlewares() { this.httpClientModuleManager.initializeBeforeMiddlewares(); } diff --git a/src/controllers/http-api/bid-suggestion-http-api-controller.js b/src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js similarity index 97% rename from src/controllers/http-api/bid-suggestion-http-api-controller.js rename to src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js index 2bf0967b56..3fbc054e19 100644 --- a/src/controllers/http-api/bid-suggestion-http-api-controller.js +++ b/src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js @@ -1,4 +1,4 @@ -import BaseController from './base-http-api-controller.js'; +import BaseController from '../base-http-api-controller.js'; class BidSuggestionController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/get-http-api-controller.js b/src/controllers/http-api/old/get-http-api-controller-old.js similarity index 96% rename from src/controllers/http-api/get-http-api-controller.js rename to src/controllers/http-api/old/get-http-api-controller-old.js index 8855bb0a99..b34e541a7c 100644 --- a/src/controllers/http-api/get-http-api-controller.js +++ b/src/controllers/http-api/old/get-http-api-controller-old.js @@ -4,8 +4,8 @@ import { CONTENT_ASSET_HASH_FUNCTION_ID, DEFAULT_GET_STATE, ERROR_TYPE, -} from '../../constants/constants.js'; -import BaseController from './base-http-api-controller.js'; +} from '../../../constants/constants.js'; +import BaseController from '../base-http-api-controller.js'; class GetController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/info-http-api-controller.js b/src/controllers/http-api/old/info-http-api-controller-old.js similarity index 62% rename from src/controllers/http-api/info-http-api-controller.js rename to src/controllers/http-api/old/info-http-api-controller-old.js index 03ee42ebd5..e6c316ee0e 100644 --- a/src/controllers/http-api/info-http-api-controller.js +++ b/src/controllers/http-api/old/info-http-api-controller-old.js @@ -1,11 +1,11 @@ import { createRequire } from 'module'; -import BaseController from './base-http-api-controller.js'; +import BaseController from '../base-http-api-controller.js'; const require = createRequire(import.meta.url); -const { version } = require('../../../package.json'); +const { version } = require('../../../../package.json'); class InfoController extends BaseController { - handleInfoRequest(req, res) { + handleInfoRequest(_, res) { this.returnResponse(res, 200, { version, }); diff --git a/src/controllers/http-api/local-store-http-api-controller.js b/src/controllers/http-api/old/local-store-http-api-controller-old.js similarity index 95% rename from src/controllers/http-api/local-store-http-api-controller.js rename to src/controllers/http-api/old/local-store-http-api-controller-old.js index 88f5e4c3dd..a0609d4814 100644 --- a/src/controllers/http-api/local-store-http-api-controller.js +++ b/src/controllers/http-api/old/local-store-http-api-controller-old.js @@ -1,5 +1,5 @@ -import BaseController from './base-http-api-controller.js'; -import { OPERATION_ID_STATUS } from '../../constants/constants.js'; +import BaseController from '../base-http-api-controller.js'; +import { OPERATION_ID_STATUS } from '../../../constants/constants.js'; class LocalStoreController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/publish-http-api-controller.js b/src/controllers/http-api/old/publish-http-api-controller-old.js similarity index 96% rename from src/controllers/http-api/publish-http-api-controller.js rename to src/controllers/http-api/old/publish-http-api-controller-old.js index 133823a1a1..2fd11d9b8b 100644 --- a/src/controllers/http-api/publish-http-api-controller.js +++ b/src/controllers/http-api/old/publish-http-api-controller-old.js @@ -1,11 +1,11 @@ -import BaseController from './base-http-api-controller.js'; +import BaseController from '../base-http-api-controller.js'; import { ERROR_TYPE, OPERATION_ID_STATUS, OPERATION_STATUS, CONTENT_ASSET_HASH_FUNCTION_ID, LOCAL_STORE_TYPES, -} from '../../constants/constants.js'; +} from '../../../constants/constants.js'; class PublishController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/query-http-api-controller.js b/src/controllers/http-api/old/query-http-api-controller-old.js similarity index 88% rename from src/controllers/http-api/query-http-api-controller.js rename to src/controllers/http-api/old/query-http-api-controller-old.js index 7fcd2e10b5..dd4e6c77ad 100644 --- a/src/controllers/http-api/query-http-api-controller.js +++ b/src/controllers/http-api/old/query-http-api-controller-old.js @@ -1,6 +1,6 @@ -import BaseController from './base-http-api-controller.js'; +import BaseController from '../base-http-api-controller.js'; -import { OPERATION_ID_STATUS } from '../../constants/constants.js'; +import { OPERATION_ID_STATUS } from '../../../constants/constants.js'; class QueryController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/request-schema/bid-suggestion-schema.js b/src/controllers/http-api/old/request-schema/bid-suggestion-schema-old.js similarity index 100% rename from src/controllers/http-api/request-schema/bid-suggestion-schema.js rename to src/controllers/http-api/old/request-schema/bid-suggestion-schema-old.js diff --git a/src/controllers/http-api/request-schema/get-schema.js b/src/controllers/http-api/old/request-schema/get-schema-old.js similarity index 88% rename from src/controllers/http-api/request-schema/get-schema.js rename to src/controllers/http-api/old/request-schema/get-schema-old.js index 6d1d6b05a0..a01a9a4e2c 100644 --- a/src/controllers/http-api/request-schema/get-schema.js +++ b/src/controllers/http-api/old/request-schema/get-schema-old.js @@ -1,4 +1,4 @@ -import { GET_STATES } from '../../../constants/constants.js'; +import { GET_STATES } from '../../../../constants/constants.js'; export default () => ({ type: 'object', diff --git a/src/controllers/http-api/request-schema/local-store-schema.js b/src/controllers/http-api/old/request-schema/local-store-schema-old.js similarity index 93% rename from src/controllers/http-api/request-schema/local-store-schema.js rename to src/controllers/http-api/old/request-schema/local-store-schema-old.js index 2c06ae748b..6cf8268cd2 100644 --- a/src/controllers/http-api/request-schema/local-store-schema.js +++ b/src/controllers/http-api/old/request-schema/local-store-schema-old.js @@ -1,4 +1,4 @@ -import { LOCAL_STORE_TYPES } from '../../../constants/constants.js'; +import { LOCAL_STORE_TYPES } from '../../../../constants/constants.js'; export default (blockchainImplementationNames) => ({ type: 'array', diff --git a/src/controllers/http-api/request-schema/publish-schema.js b/src/controllers/http-api/old/request-schema/publish-schema-old.js similarity index 100% rename from src/controllers/http-api/request-schema/publish-schema.js rename to src/controllers/http-api/old/request-schema/publish-schema-old.js diff --git a/src/controllers/http-api/request-schema/query-schema.js b/src/controllers/http-api/old/request-schema/query-schema-old.js similarity index 93% rename from src/controllers/http-api/request-schema/query-schema.js rename to src/controllers/http-api/old/request-schema/query-schema-old.js index 3f971ba0a2..e245d7d87f 100644 --- a/src/controllers/http-api/request-schema/query-schema.js +++ b/src/controllers/http-api/old/request-schema/query-schema-old.js @@ -1,4 +1,4 @@ -import { QUERY_TYPES, TRIPLE_STORE_REPOSITORIES } from '../../../constants/constants.js'; +import { QUERY_TYPES, TRIPLE_STORE_REPOSITORIES } from '../../../../constants/constants.js'; export default () => ({ type: 'object', diff --git a/src/controllers/http-api/request-schema/update-schema.js b/src/controllers/http-api/old/request-schema/update-schema-old.js similarity index 100% rename from src/controllers/http-api/request-schema/update-schema.js rename to src/controllers/http-api/old/request-schema/update-schema-old.js diff --git a/src/controllers/http-api/result-http-api-controller.js b/src/controllers/http-api/old/result-http-api-controller-old.js similarity index 77% rename from src/controllers/http-api/result-http-api-controller.js rename to src/controllers/http-api/old/result-http-api-controller-old.js index 120ae86249..569aa9978a 100644 --- a/src/controllers/http-api/result-http-api-controller.js +++ b/src/controllers/http-api/old/result-http-api-controller-old.js @@ -1,19 +1,22 @@ -import { OPERATION_ID_STATUS } from '../../constants/constants.js'; -import BaseController from './base-http-api-controller.js'; - -const availableOperations = ['publish', 'get', 'query', 'local-store', 'update']; +import { OPERATION_ID_STATUS } from '../../../constants/constants.js'; +import BaseController from '../base-http-api-controller.js'; class ResultController extends BaseController { constructor(ctx) { super(ctx); this.operationIdService = ctx.operationIdService; + + const controllers = ctx.httpClientModuleManager.getMethodControllers('old', false); + this.availableOperations = controllers.map( + (controller) => controller.split('-http-api-controller-')[0], + ); } async handleOperationResultRequest(req, res) { - if (!availableOperations.includes(req.params.operation)) { + if (!this.availableOperations.includes(req.params.operation)) { return this.returnResponse(res, 400, { code: 400, - message: `Unsupported operation, available operations are: ${availableOperations}`, + message: `Unsupported operation: ${req.params.operation}, available operations are: ${this.availableOperations}`, }); } @@ -21,7 +24,7 @@ class ResultController extends BaseController { if (!this.operationIdService.operationIdInRightFormat(operationId)) { return this.returnResponse(res, 400, { code: 400, - message: 'Operation id is in wrong format', + message: `Operation id: ${operationId} is in wrong format`, }); } diff --git a/src/controllers/http-api/update-http-api-controller.js b/src/controllers/http-api/old/update-http-api-controller-old.js similarity index 96% rename from src/controllers/http-api/update-http-api-controller.js rename to src/controllers/http-api/old/update-http-api-controller-old.js index 676950de04..ed79327aee 100644 --- a/src/controllers/http-api/update-http-api-controller.js +++ b/src/controllers/http-api/old/update-http-api-controller-old.js @@ -1,11 +1,11 @@ -import BaseController from './base-http-api-controller.js'; +import BaseController from '../base-http-api-controller.js'; import { ERROR_TYPE, OPERATION_ID_STATUS, OPERATION_STATUS, CONTENT_ASSET_HASH_FUNCTION_ID, LOCAL_STORE_TYPES, -} from '../../constants/constants.js'; +} from '../../../constants/constants.js'; class UpdateController extends BaseController { constructor(ctx) { diff --git a/src/controllers/http-api/v1/info-http-api-controller-v1.js b/src/controllers/http-api/v1/info-http-api-controller-v1.js new file mode 100644 index 0000000000..241f65d465 --- /dev/null +++ b/src/controllers/http-api/v1/info-http-api-controller-v1.js @@ -0,0 +1,29 @@ +import { createRequire } from 'module'; +import BaseController from '../base-http-api-controller.js'; + +const require = createRequire(import.meta.url); +const { version } = require('../../../../package.json'); + +class InfoControllerV1 extends BaseController { + handleInfoRequest(_, res) { + this.returnResponse(res, 200, { + version, + ...this.filterConfig(), + }); + } + + filterConfig() { + const nodeConfigData = { + tripleStores: Object.entries(this.config.modules.tripleStore.implementation) + .filter(([, value]) => value.enabled) + .map(([key]) => key), + blockchains: Object.entries(this.config.modules.blockchain.implementation) + .filter(([, value]) => value.enabled) + .map(([key]) => key), + }; + + return nodeConfigData; + } +} + +export default InfoControllerV1; diff --git a/src/modules/http-client/http-client-module-manager.js b/src/modules/http-client/http-client-module-manager.js index ef3c54a39b..6e56f7a4b4 100644 --- a/src/modules/http-client/http-client-module-manager.js +++ b/src/modules/http-client/http-client-module-manager.js @@ -1,15 +1,43 @@ +import fs from 'fs'; +import path from 'path'; import BaseModuleManager from '../base-module-manager.js'; +import stringUtil from '../../service/util/string-util.js'; class HttpClientModuleManager extends BaseModuleManager { constructor(ctx) { super(ctx); this.authService = ctx.authService; + this.fileService = ctx.fileService; } getName() { return 'httpClient'; } + getApiVersions() { + const httpControllersPath = this.fileService.getHttpControllersFolderPath(); + return fs + .readdirSync(httpControllersPath) + .filter((folder) => fs.statSync(path.join(httpControllersPath, folder)).isDirectory()); + } + + getMethodControllers(version, camelCase = true) { + const versionFolder = path.join(this.fileService.getHttpControllersFolderPath(), version); + + const methodControllers = []; + for (const controller of fs.readdirSync(versionFolder)) { + if (!controller.endsWith(`-http-api-controller-${version}.js`)) continue; + + if (camelCase) { + methodControllers.push(stringUtil.toCamelCase(controller.replace('.js', ''))); + } else { + methodControllers.push(controller.replace('.js', '')); + } + } + + return methodControllers; + } + get(route, callback, options = {}) { if (this.initialized) { return this.getImplementation().module.get(route, callback, options); diff --git a/src/service/file-service.js b/src/service/file-service.js index aa1c5be91b..74cc66e24c 100644 --- a/src/service/file-service.js +++ b/src/service/file-service.js @@ -104,6 +104,10 @@ class FileService { } } + getHttpControllersFolderPath() { + return path.join(appRootPath.path, 'src/controllers/http-api'); + } + getDataFolderPath() { if (process.env.NODE_ENV === 'testnet' || process.env.NODE_ENV === 'mainnet') { return path.join(appRootPath.path, '..', this.config.appDataPath); diff --git a/src/service/json-schema-service.js b/src/service/json-schema-service.js index 3f7186500c..555fe10a5c 100644 --- a/src/service/json-schema-service.js +++ b/src/service/json-schema-service.js @@ -1,37 +1,48 @@ -import publishSchema from '../controllers/http-api/request-schema/publish-schema.js'; -import updateSchema from '../controllers/http-api/request-schema/update-schema.js'; -import getSchema from '../controllers/http-api/request-schema/get-schema.js'; -import querySchema from '../controllers/http-api/request-schema/query-schema.js'; -import bidSuggestionSchema from '../controllers/http-api/request-schema/bid-suggestion-schema.js'; -import localStoreSchema from '../controllers/http-api/request-schema/local-store-schema.js'; +import path from 'path'; +import appRootPath from 'app-root-path'; class JsonSchemaService { constructor(ctx) { this.blockchainModuleManager = ctx.blockchainModuleManager; } - bidSuggestionSchema() { - return bidSuggestionSchema(this.blockchainModuleManager.getImplementationNames()); + async loadSchema(version, schemaName) { + const schemaPath = path.resolve( + appRootPath.path, + `src/controllers/http-api/${version}/request-schema/${schemaName}-schema-${version}.js`, + ); + const schemaModule = await import(schemaPath); + const schemaFunction = schemaModule.default; + + if (schemaFunction.length >= 1) { + return schemaFunction(this.blockchainModuleManager.getImplementationNames()); + } + + return schemaFunction(); + } + + async bidSuggestionSchema(version) { + return this.loadSchema(version, 'bid-suggestion'); } - publishSchema() { - return publishSchema(this.blockchainModuleManager.getImplementationNames()); + async publishSchema(version) { + return this.loadSchema(version, 'publish'); } - updateSchema() { - return updateSchema(this.blockchainModuleManager.getImplementationNames()); + async updateSchema(version) { + return this.loadSchema(version, 'update'); } - getSchema() { - return getSchema(); + async getSchema(version) { + return this.loadSchema(version, 'get'); } - querySchema() { - return querySchema(); + async querySchema(version) { + return this.loadSchema(version, 'query'); } - localStoreSchema() { - return localStoreSchema(this.blockchainModuleManager.getImplementationNames()); + async localStoreSchema(version) { + return this.loadSchema(version, 'local-store'); } } diff --git a/src/service/util/string-util.js b/src/service/util/string-util.js new file mode 100644 index 0000000000..caf2039a70 --- /dev/null +++ b/src/service/util/string-util.js @@ -0,0 +1,13 @@ +class StringUtil { + toCamelCase(str) { + return str.replace(/[-_]+(.)/g, (_, group) => group.toUpperCase()); + } + + capitalize(str) { + return str.charAt(0).toUpperCase() + str.slice(1); + } +} + +const stringUtil = new StringUtil(); + +export default stringUtil; From 40c324fe53e8da138160d0b0d5f533a7c2b1670a Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 9 Aug 2023 21:38:28 +0100 Subject: [PATCH 02/18] Fixed wrong controller name --- src/controllers/http-api/http-api-router.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index 4c96ddbbd8..931ff993b6 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -59,7 +59,7 @@ class HttpApiRouter { this.httpClientModuleManager.post( '/local-store', (req, res) => { - this.localHttpApiControllerOld.handleLocalStoreRequest(req, res); + this.localStoreHttpApiControllerOld.handleLocalStoreRequest(req, res); }, { requestSchema: await this.jsonSchemaService.localStoreSchema('old') }, ); From 108922a490cc94c3c0aa60dc9fb683faa0254a18 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Mon, 14 Aug 2023 15:42:27 +0100 Subject: [PATCH 03/18] Moved API version related functions to the separate service, added use/createRouterInstance to express-http-client --- src/controllers/http-api/http-api-router.js | 30 ++++++----- .../old/result-http-api-controller-old.js | 5 +- .../http-client/http-client-module-manager.js | 37 ++++--------- .../implementation/express-http-client.js | 8 +++ src/service/http-api-service.js | 54 +++++++++++++++++++ 5 files changed, 90 insertions(+), 44 deletions(-) create mode 100644 src/service/http-api-service.js diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index 931ff993b6..1943e9ec46 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -5,14 +5,16 @@ class HttpApiRouter { this.config = ctx.config; this.httpClientModuleManager = ctx.httpClientModuleManager; - const versions = this.httpClientModuleManager.getApiVersions(); + const versions = ctx.httpApiService.getApiVersions(); for (const version of versions) { - const versionedMethodControllers = - this.httpClientModuleManager.getMethodControllers(version); + const operations = ctx.httpApiService.getAvailableOperations(version, true); - for (const versionedController of versionedMethodControllers) { - this[versionedController] = ctx[versionedController]; + for (const operation of operations) { + const versionedOperation = `${operation}HttpApiController${stringUtil.capitalize( + version, + )}`; + this[versionedOperation] = ctx[versionedOperation]; } } @@ -31,6 +33,15 @@ class HttpApiRouter { await this.initializeOldListeners(); } + async initializeVersionedListeners(version) { + this.httpClientModuleManager.get(`/${version}/info`, (req, res) => { + this[`infoHttpApiController${stringUtil.capitalize(version)}`].handleInfoRequest( + req, + res, + ); + }); + } + async initializeOldListeners() { this.httpClientModuleManager.post( '/publish', @@ -89,15 +100,6 @@ class HttpApiRouter { ); } - async initializeVersionedListeners(version) { - this.httpClientModuleManager.get(`/${version}/info`, (req, res) => { - this[`infoHttpApiController${stringUtil.capitalize(version)}`].handleInfoRequest( - req, - res, - ); - }); - } - initializeBeforeMiddlewares() { this.httpClientModuleManager.initializeBeforeMiddlewares(); } diff --git a/src/controllers/http-api/old/result-http-api-controller-old.js b/src/controllers/http-api/old/result-http-api-controller-old.js index 569aa9978a..72ca09313f 100644 --- a/src/controllers/http-api/old/result-http-api-controller-old.js +++ b/src/controllers/http-api/old/result-http-api-controller-old.js @@ -6,10 +6,7 @@ class ResultController extends BaseController { super(ctx); this.operationIdService = ctx.operationIdService; - const controllers = ctx.httpClientModuleManager.getMethodControllers('old', false); - this.availableOperations = controllers.map( - (controller) => controller.split('-http-api-controller-')[0], - ); + this.availableOperations = ctx.httpApiService.getAvailableOperations('old'); } async handleOperationResultRequest(req, res) { diff --git a/src/modules/http-client/http-client-module-manager.js b/src/modules/http-client/http-client-module-manager.js index 6e56f7a4b4..a2bede9b12 100644 --- a/src/modules/http-client/http-client-module-manager.js +++ b/src/modules/http-client/http-client-module-manager.js @@ -1,7 +1,4 @@ -import fs from 'fs'; -import path from 'path'; import BaseModuleManager from '../base-module-manager.js'; -import stringUtil from '../../service/util/string-util.js'; class HttpClientModuleManager extends BaseModuleManager { constructor(ctx) { @@ -14,39 +11,27 @@ class HttpClientModuleManager extends BaseModuleManager { return 'httpClient'; } - getApiVersions() { - const httpControllersPath = this.fileService.getHttpControllersFolderPath(); - return fs - .readdirSync(httpControllersPath) - .filter((folder) => fs.statSync(path.join(httpControllersPath, folder)).isDirectory()); + get(route, callback, options = {}) { + if (this.initialized) { + return this.getImplementation().module.get(route, callback, options); + } } - getMethodControllers(version, camelCase = true) { - const versionFolder = path.join(this.fileService.getHttpControllersFolderPath(), version); - - const methodControllers = []; - for (const controller of fs.readdirSync(versionFolder)) { - if (!controller.endsWith(`-http-api-controller-${version}.js`)) continue; - - if (camelCase) { - methodControllers.push(stringUtil.toCamelCase(controller.replace('.js', ''))); - } else { - methodControllers.push(controller.replace('.js', '')); - } + post(route, callback, options = {}) { + if (this.initialized) { + return this.getImplementation().module.post(route, callback, options); } - - return methodControllers; } - get(route, callback, options = {}) { + use(route, callback, options) { if (this.initialized) { - return this.getImplementation().module.get(route, callback, options); + return this.getImplementation().module.use(route, callback, options); } } - post(route, callback, options = {}) { + createRouterInstance() { if (this.initialized) { - return this.getImplementation().module.post(route, callback, options); + return this.getImplementation().module.createRouterInstance(); } } diff --git a/src/modules/http-client/implementation/express-http-client.js b/src/modules/http-client/implementation/express-http-client.js index d14fa2b93a..345cc5339c 100644 --- a/src/modules/http-client/implementation/express-http-client.js +++ b/src/modules/http-client/implementation/express-http-client.js @@ -24,6 +24,14 @@ class ExpressHttpClient { this.app.post(route, ...this.selectMiddlewares(options), callback); } + use(route, callback, options) { + this.app.use(route, callback, options); + } + + createRouterInstance() { + return express.Router(); + } + sendResponse(res, status, returnObject) { res.status(status); res.send(returnObject); diff --git a/src/service/http-api-service.js b/src/service/http-api-service.js new file mode 100644 index 0000000000..db1309a2c2 --- /dev/null +++ b/src/service/http-api-service.js @@ -0,0 +1,54 @@ +import fs from 'fs'; +import path from 'path'; +import stringUtil from './util/string-util.js'; + +class HttpApiService { + constructor(ctx) { + this.fileService = ctx.fileService; + } + + getApiVersions(sort = false) { + const httpControllersPath = this.fileService.getHttpControllersFolderPath(); + const versions = fs.readdirSync(httpControllersPath).filter((folder) => { + if (!fs.statSync(path.join(httpControllersPath, folder)).isDirectory()) return false; + if (folder === 'old') return true; + return /^v\d+$/.test(folder); + }); + + if (sort) { + return versions.sort((a, b) => { + if (a === 'old') return 1; + if (b === 'old') return -1; + + return parseInt(b.substring(1), 10) - parseInt(a.substring(1), 10); + }); + } + + return versions; + } + + getAvailableOperations(version, camelCase = false) { + const versionFolder = path.join(this.fileService.getHttpControllersFolderPath(), version); + + const operations = []; + for (const controller of fs.readdirSync(versionFolder)) { + let operation; + + if (!controller.endsWith(`-http-api-controller-${version}.js`)) { + continue; + } else { + operation = controller.replace(`-http-api-controller-${version}.js`, ''); + } + + if (camelCase) { + operations.push(stringUtil.toCamelCase(operation)); + } else { + operations.push(operation); + } + } + + return operations; + } +} + +export default HttpApiService; From b2cfd36fbfd81910fab10fa0f95250a41992e580 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 16 Aug 2023 13:25:59 +0100 Subject: [PATCH 04/18] Renamed old HTTP API version to v0, mounted /* routes to /v0/*, mounted /latest/* routes to the latest versions of the respective routes, made router generic, added routes config --- src/constants/constants.js | 83 +++++++++ src/controllers/http-api/http-api-router.js | 157 +++++++++--------- .../bid-suggestion-http-api-controller-v0.js} | 2 +- .../get-http-api-controller-v0.js} | 2 +- .../info-http-api-controller-v0.js} | 2 +- .../local-store-http-api-controller-v0.js} | 2 +- .../publish-http-api-controller-v0.js} | 2 +- .../query-http-api-controller-v0.js} | 2 +- .../bid-suggestion-schema-v0.js} | 4 +- .../request-schema/get-schema-v0.js} | 0 .../request-schema/local-store-schema-v0.js} | 4 +- .../request-schema/publish-schema-v0.js} | 4 +- .../request-schema/query-schema-v0.js} | 0 .../request-schema/update-schema-v0.js} | 4 +- .../result-http-api-controller-v0.js} | 6 +- .../update-http-api-controller-v0.js} | 2 +- .../v1/info-http-api-controller-v1.js | 2 +- .../http-client/http-client-module-manager.js | 8 +- .../implementation/express-http-client.js | 2 +- src/service/http-api-service.js | 54 ------ src/service/json-schema-service.js | 30 ++-- 21 files changed, 206 insertions(+), 166 deletions(-) rename src/controllers/http-api/{old/bid-suggestion-http-api-controller-old.js => v0/bid-suggestion-http-api-controller-v0.js} (97%) rename src/controllers/http-api/{old/get-http-api-controller-old.js => v0/get-http-api-controller-v0.js} (98%) rename src/controllers/http-api/{old/info-http-api-controller-old.js => v0/info-http-api-controller-v0.js} (91%) rename src/controllers/http-api/{old/local-store-http-api-controller-old.js => v0/local-store-http-api-controller-v0.js} (98%) rename src/controllers/http-api/{old/publish-http-api-controller-old.js => v0/publish-http-api-controller-v0.js} (98%) rename src/controllers/http-api/{old/query-http-api-controller-old.js => v0/query-http-api-controller-v0.js} (96%) rename src/controllers/http-api/{old/request-schema/bid-suggestion-schema-old.js => v0/request-schema/bid-suggestion-schema-v0.js} (88%) rename src/controllers/http-api/{old/request-schema/get-schema-old.js => v0/request-schema/get-schema-v0.js} (100%) rename src/controllers/http-api/{old/request-schema/local-store-schema-old.js => v0/request-schema/local-store-schema-v0.js} (90%) rename src/controllers/http-api/{old/request-schema/update-schema-old.js => v0/request-schema/publish-schema-v0.js} (87%) rename src/controllers/http-api/{old/request-schema/query-schema-old.js => v0/request-schema/query-schema-v0.js} (100%) rename src/controllers/http-api/{old/request-schema/publish-schema-old.js => v0/request-schema/update-schema-v0.js} (87%) rename src/controllers/http-api/{old/result-http-api-controller-old.js => v0/result-http-api-controller-v0.js} (92%) rename src/controllers/http-api/{old/update-http-api-controller-old.js => v0/update-http-api-controller-v0.js} (98%) delete mode 100644 src/service/http-api-service.js diff --git a/src/constants/constants.js b/src/constants/constants.js index 9c807292ea..28c3836f2a 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -414,6 +414,89 @@ export const ARCHIVE_UPDATE_RESPONSES_FOLDER = 'update_responses'; */ export const COMMAND_QUEUE_PARALLELISM = 100; +/** + * @constant {object} HTTP_API_ROUTES - + * Network protocols + */ +export const HTTP_API_ROUTES = { + v0: [ + { + method: 'post', + name: 'publish', + path: '/publish', + controller: 'publishHttpApiControllerV0', + options: { + rateLimit: true, + schema: { + name: 'publishSchema', + args: { + blockchainImplementationNames: + 'blockchainModuleManager.getImplementationNames', + }, + }, + }, + }, + { + method: 'post', + name: 'update', + path: '/update', + controller: 'updateHttpApiControllerV0', + options: { rateLimit: true, schema: { name: 'updateSchema', args: {} } }, + }, + { + method: 'post', + name: 'query', + path: '/query', + controller: 'queryHttpApiControllerV0', + options: { schema: { name: 'querySchema', args: {} } }, + }, + { + method: 'post', + name: 'local-store', + path: '/local-store', + controller: 'localStoreHttpApiControllerV0', + options: { schema: { name: 'localStoreSchema', args: {} } }, + }, + { + method: 'post', + name: 'get', + path: '/get', + controller: 'getHttpApiControllerV0', + options: { rateLimit: true, schema: { name: 'getSchema', args: {} } }, + }, + { + method: 'get', + name: 'result', + path: '/:operation/:operationId', + controller: 'resultHttpApiControllerV0', + options: {}, + }, + { + method: 'get', + name: 'info', + path: '/info', + controller: 'infoHttpApiControllerV0', + options: {}, + }, + { + method: 'get', + name: 'bid-suggestion', + path: '/bid-suggestion', + controller: 'bidSuggestionHttpApiControllerV0', + options: { schema: { name: 'bidSuggestionSchema', args: {} } }, + }, + ], + v1: [ + { + method: 'get', + name: 'info', + path: '/info', + controller: 'infoHttpApiControllerV1', + options: {}, + }, + ], +}; + /** * @constant {object} NETWORK_PROTOCOLS - * Network protocols diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index 1943e9ec46..f992783abd 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -1,112 +1,117 @@ import stringUtil from '../../service/util/string-util.js'; +import { HTTP_API_ROUTES } from '../../constants/constants.js'; class HttpApiRouter { constructor(ctx) { this.config = ctx.config; this.httpClientModuleManager = ctx.httpClientModuleManager; - const versions = ctx.httpApiService.getApiVersions(); + this.apiRoutes = HTTP_API_ROUTES; + this.apiVersions = Object.keys(this.apiRoutes); - for (const version of versions) { - const operations = ctx.httpApiService.getAvailableOperations(version, true); + this.routers = {}; + for (const version of this.apiVersions) { + this.routers[version] = this.httpClientModuleManager.createRouterInstance(); + + const operations = this.apiRoutes[version].map((route) => route.name); for (const operation of operations) { - const versionedOperation = `${operation}HttpApiController${stringUtil.capitalize( - version, - )}`; + const versionedOperation = `${stringUtil.toCamelCase( + operation, + )}HttpApiController${stringUtil.capitalize(version)}`; this[versionedOperation] = ctx[versionedOperation]; } } + this.routers.latest = this.httpClientModuleManager.createRouterInstance(); + this.blockchainModuleManager = ctx.blockchainModuleManager; this.jsonSchemaService = ctx.jsonSchemaService; } async initialize() { this.initializeBeforeMiddlewares(); - await this.initializeListeners(); + await this.initializeVersionedListeners(); + this.initializeRouters(); this.initializeAfterMiddlewares(); await this.httpClientModuleManager.listen(); } - async initializeListeners() { - await this.initializeVersionedListeners('v1'); - await this.initializeOldListeners(); + initializeBeforeMiddlewares() { + this.httpClientModuleManager.initializeBeforeMiddlewares(); } - async initializeVersionedListeners(version) { - this.httpClientModuleManager.get(`/${version}/info`, (req, res) => { - this[`infoHttpApiController${stringUtil.capitalize(version)}`].handleInfoRequest( - req, - res, - ); - }); + async initializeVersionedListeners() { + const descendingOrderedVersions = this.apiVersions.sort((a, b) => b.localeCompare(a)); + const mountedLatestRoutes = new Set(); + + for (const version of descendingOrderedVersions) { + for (const route of this.apiRoutes[version]) { + const { method, path, controller, options } = route; + + if (options.schema) { + const argumentsObject = {}; + + for (const [argName, argFuncRef] of Object.entries(options.schema.args)) { + // eslint-disable-next-line no-await-in-loop + argumentsObject[argName] = await this._executeFunctionFromConfigRef( + this, + argFuncRef, + ); + } + + // eslint-disable-next-line no-await-in-loop + options.requestSchema = await this.jsonSchemaService[options.schema.name]( + version, + argumentsObject, + ); + } + + const middlewares = this.httpClientModuleManager.selectMiddlewares(options); + const callback = (req, res) => { + this[controller].handleRequest(req, res); + }; + + this.routers[version][method](path, ...middlewares, callback); + + if (!mountedLatestRoutes.has(route.name)) { + this.routers.latest[method](path, ...middlewares, callback); + mountedLatestRoutes.add(route.name); + } + } + } } - async initializeOldListeners() { - this.httpClientModuleManager.post( - '/publish', - (req, res) => { - this.publishHttpApiControllerOld.handlePublishRequest(req, res); - }, - { rateLimit: true, requestSchema: await this.jsonSchemaService.publishSchema('old') }, - ); - - this.httpClientModuleManager.post( - '/update', - (req, res) => { - this.updateHttpApiControllerOld.handleUpdateRequest(req, res); - }, - { rateLimit: true, requestSchema: await this.jsonSchemaService.updateSchema('old') }, - ); - - this.httpClientModuleManager.post( - '/query', - (req, res) => { - this.queryHttpApiControllerOld.handleQueryRequest(req, res); - }, - { requestSchema: await this.jsonSchemaService.querySchema('old') }, - ); - - this.httpClientModuleManager.post( - '/local-store', - (req, res) => { - this.localStoreHttpApiControllerOld.handleLocalStoreRequest(req, res); - }, - { requestSchema: await this.jsonSchemaService.localStoreSchema('old') }, - ); - - this.httpClientModuleManager.post( - '/get', - (req, res) => { - this.getHttpApiControllerOld.handleGetRequest(req, res); - }, - { rateLimit: true, requestSchema: await this.jsonSchemaService.getSchema('old') }, - ); - - this.httpClientModuleManager.get('/:operation/:operationId', (req, res) => { - this.resultHttpApiControllerOld.handleOperationResultRequest(req, res); - }); - - this.httpClientModuleManager.get('/info', (req, res) => { - this.infoHttpApiControllerOld.handleInfoRequest(req, res); - }); - - this.httpClientModuleManager.get( - '/bid-suggestion', - (req, res) => { - this.bidSuggestionHttpApiControllerOld.handleBidSuggestionRequest(req, res); - }, - { requestSchema: await this.jsonSchemaService.bidSuggestionSchema('old') }, - ); - } + initializeRouters() { + for (const version of this.apiVersions) { + this.httpClientModuleManager.use(`/${version}`, this.routers[version]); + } - initializeBeforeMiddlewares() { - this.httpClientModuleManager.initializeBeforeMiddlewares(); + this.httpClientModuleManager.use('/latest', this.routers.latest); + this.httpClientModuleManager.use('/', this.routers.v0); } initializeAfterMiddlewares() { this.httpClientModuleManager.initializeAfterMiddlewares(); } + + async _executeFunctionFromConfigRef(context, reference) { + const parts = reference.split('.'); + const fnName = parts.pop(); + const objRef = parts.reduce((acc, part) => acc[part], context); + + if (objRef && typeof objRef[fnName] === 'function') { + const result = objRef[fnName](); + + if (result instanceof Promise) { + // eslint-disable-next-line no-return-await + return await result; + } + + return result; + } + + throw new Error(`Function ${reference} not found.`); + } } export default HttpApiRouter; diff --git a/src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js b/src/controllers/http-api/v0/bid-suggestion-http-api-controller-v0.js similarity index 97% rename from src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js rename to src/controllers/http-api/v0/bid-suggestion-http-api-controller-v0.js index 3fbc054e19..e41932c32b 100644 --- a/src/controllers/http-api/old/bid-suggestion-http-api-controller-old.js +++ b/src/controllers/http-api/v0/bid-suggestion-http-api-controller-v0.js @@ -8,7 +8,7 @@ class BidSuggestionController extends BaseController { this.shardingTableService = ctx.shardingTableService; } - async handleBidSuggestionRequest(req, res) { + async handleRequest(req, res) { if ((await this.repositoryModuleManager.getPeersCount(req.query.blockchain)) === 0) this.returnResponse(res, 400, { code: 400, diff --git a/src/controllers/http-api/old/get-http-api-controller-old.js b/src/controllers/http-api/v0/get-http-api-controller-v0.js similarity index 98% rename from src/controllers/http-api/old/get-http-api-controller-old.js rename to src/controllers/http-api/v0/get-http-api-controller-v0.js index b34e541a7c..b14dbc5e17 100644 --- a/src/controllers/http-api/old/get-http-api-controller-old.js +++ b/src/controllers/http-api/v0/get-http-api-controller-v0.js @@ -18,7 +18,7 @@ class GetController extends BaseController { this.validationService = ctx.validationService; } - async handleGetRequest(req, res) { + async handleRequest(req, res) { const operationId = await this.operationIdService.generateOperationId( OPERATION_ID_STATUS.GET.GET_START, ); diff --git a/src/controllers/http-api/old/info-http-api-controller-old.js b/src/controllers/http-api/v0/info-http-api-controller-v0.js similarity index 91% rename from src/controllers/http-api/old/info-http-api-controller-old.js rename to src/controllers/http-api/v0/info-http-api-controller-v0.js index e6c316ee0e..61dbb514ed 100644 --- a/src/controllers/http-api/old/info-http-api-controller-old.js +++ b/src/controllers/http-api/v0/info-http-api-controller-v0.js @@ -5,7 +5,7 @@ const require = createRequire(import.meta.url); const { version } = require('../../../../package.json'); class InfoController extends BaseController { - handleInfoRequest(_, res) { + handleRequest(_, res) { this.returnResponse(res, 200, { version, }); diff --git a/src/controllers/http-api/old/local-store-http-api-controller-old.js b/src/controllers/http-api/v0/local-store-http-api-controller-v0.js similarity index 98% rename from src/controllers/http-api/old/local-store-http-api-controller-old.js rename to src/controllers/http-api/v0/local-store-http-api-controller-v0.js index a0609d4814..fb94771785 100644 --- a/src/controllers/http-api/old/local-store-http-api-controller-old.js +++ b/src/controllers/http-api/v0/local-store-http-api-controller-v0.js @@ -9,7 +9,7 @@ class LocalStoreController extends BaseController { this.dataService = ctx.dataService; } - async handleLocalStoreRequest(req, res) { + async handleRequest(req, res) { const operationId = await this.operationIdService.generateOperationId( OPERATION_ID_STATUS.LOCAL_STORE.LOCAL_STORE_INIT_START, ); diff --git a/src/controllers/http-api/old/publish-http-api-controller-old.js b/src/controllers/http-api/v0/publish-http-api-controller-v0.js similarity index 98% rename from src/controllers/http-api/old/publish-http-api-controller-old.js rename to src/controllers/http-api/v0/publish-http-api-controller-v0.js index 2fd11d9b8b..91cce81b6b 100644 --- a/src/controllers/http-api/old/publish-http-api-controller-old.js +++ b/src/controllers/http-api/v0/publish-http-api-controller-v0.js @@ -16,7 +16,7 @@ class PublishController extends BaseController { this.repositoryModuleManager = ctx.repositoryModuleManager; } - async handlePublishRequest(req, res) { + async handleRequest(req, res) { const operationId = await this.operationIdService.generateOperationId( OPERATION_ID_STATUS.PUBLISH.PUBLISH_START, ); diff --git a/src/controllers/http-api/old/query-http-api-controller-old.js b/src/controllers/http-api/v0/query-http-api-controller-v0.js similarity index 96% rename from src/controllers/http-api/old/query-http-api-controller-old.js rename to src/controllers/http-api/v0/query-http-api-controller-v0.js index dd4e6c77ad..0a66186e38 100644 --- a/src/controllers/http-api/old/query-http-api-controller-old.js +++ b/src/controllers/http-api/v0/query-http-api-controller-v0.js @@ -9,7 +9,7 @@ class QueryController extends BaseController { this.operationIdService = ctx.operationIdService; } - async handleQueryRequest(req, res) { + async handleRequest(req, res) { const { query, type: queryType } = req.body; const operationId = await this.operationIdService.generateOperationId( diff --git a/src/controllers/http-api/old/request-schema/bid-suggestion-schema-old.js b/src/controllers/http-api/v0/request-schema/bid-suggestion-schema-v0.js similarity index 88% rename from src/controllers/http-api/old/request-schema/bid-suggestion-schema-old.js rename to src/controllers/http-api/v0/request-schema/bid-suggestion-schema-v0.js index 4bf997b84b..f9259aa3ef 100644 --- a/src/controllers/http-api/old/request-schema/bid-suggestion-schema-old.js +++ b/src/controllers/http-api/v0/request-schema/bid-suggestion-schema-v0.js @@ -1,4 +1,4 @@ -export default (blockchainImplementationNames) => ({ +export default (argumentsObject) => ({ type: 'object', required: [ 'blockchain', @@ -10,7 +10,7 @@ export default (blockchainImplementationNames) => ({ ], properties: { blockchain: { - enum: blockchainImplementationNames, + enum: argumentsObject.blockchainImplementationNames, }, epochsNumber: { type: 'number', diff --git a/src/controllers/http-api/old/request-schema/get-schema-old.js b/src/controllers/http-api/v0/request-schema/get-schema-v0.js similarity index 100% rename from src/controllers/http-api/old/request-schema/get-schema-old.js rename to src/controllers/http-api/v0/request-schema/get-schema-v0.js diff --git a/src/controllers/http-api/old/request-schema/local-store-schema-old.js b/src/controllers/http-api/v0/request-schema/local-store-schema-v0.js similarity index 90% rename from src/controllers/http-api/old/request-schema/local-store-schema-old.js rename to src/controllers/http-api/v0/request-schema/local-store-schema-v0.js index 6cf8268cd2..65aab92c27 100644 --- a/src/controllers/http-api/old/request-schema/local-store-schema-old.js +++ b/src/controllers/http-api/v0/request-schema/local-store-schema-v0.js @@ -1,6 +1,6 @@ import { LOCAL_STORE_TYPES } from '../../../../constants/constants.js'; -export default (blockchainImplementationNames) => ({ +export default (argumentsObject) => ({ type: 'array', items: { type: 'object', @@ -19,7 +19,7 @@ export default (blockchainImplementationNames) => ({ minItems: 1, }, blockchain: { - enum: blockchainImplementationNames, + enum: argumentsObject.blockchainImplementationNames, }, contract: { type: 'string', diff --git a/src/controllers/http-api/old/request-schema/update-schema-old.js b/src/controllers/http-api/v0/request-schema/publish-schema-v0.js similarity index 87% rename from src/controllers/http-api/old/request-schema/update-schema-old.js rename to src/controllers/http-api/v0/request-schema/publish-schema-v0.js index 068e5018a2..236db2ea5d 100644 --- a/src/controllers/http-api/old/request-schema/update-schema-old.js +++ b/src/controllers/http-api/v0/request-schema/publish-schema-v0.js @@ -1,4 +1,4 @@ -export default (blockchainImplementationNames) => ({ +export default (argumentsObject) => ({ type: 'object', required: ['assertionId', 'assertion', 'blockchain', 'contract', 'tokenId'], properties: { @@ -15,7 +15,7 @@ export default (blockchainImplementationNames) => ({ minItems: 1, }, blockchain: { - enum: blockchainImplementationNames, + enum: argumentsObject.blockchainImplementationNames, }, contract: { type: 'string', diff --git a/src/controllers/http-api/old/request-schema/query-schema-old.js b/src/controllers/http-api/v0/request-schema/query-schema-v0.js similarity index 100% rename from src/controllers/http-api/old/request-schema/query-schema-old.js rename to src/controllers/http-api/v0/request-schema/query-schema-v0.js diff --git a/src/controllers/http-api/old/request-schema/publish-schema-old.js b/src/controllers/http-api/v0/request-schema/update-schema-v0.js similarity index 87% rename from src/controllers/http-api/old/request-schema/publish-schema-old.js rename to src/controllers/http-api/v0/request-schema/update-schema-v0.js index 068e5018a2..236db2ea5d 100644 --- a/src/controllers/http-api/old/request-schema/publish-schema-old.js +++ b/src/controllers/http-api/v0/request-schema/update-schema-v0.js @@ -1,4 +1,4 @@ -export default (blockchainImplementationNames) => ({ +export default (argumentsObject) => ({ type: 'object', required: ['assertionId', 'assertion', 'blockchain', 'contract', 'tokenId'], properties: { @@ -15,7 +15,7 @@ export default (blockchainImplementationNames) => ({ minItems: 1, }, blockchain: { - enum: blockchainImplementationNames, + enum: argumentsObject.blockchainImplementationNames, }, contract: { type: 'string', diff --git a/src/controllers/http-api/old/result-http-api-controller-old.js b/src/controllers/http-api/v0/result-http-api-controller-v0.js similarity index 92% rename from src/controllers/http-api/old/result-http-api-controller-old.js rename to src/controllers/http-api/v0/result-http-api-controller-v0.js index 72ca09313f..83f0d92f3b 100644 --- a/src/controllers/http-api/old/result-http-api-controller-old.js +++ b/src/controllers/http-api/v0/result-http-api-controller-v0.js @@ -1,4 +1,4 @@ -import { OPERATION_ID_STATUS } from '../../../constants/constants.js'; +import { HTTP_API_ROUTES, OPERATION_ID_STATUS } from '../../../constants/constants.js'; import BaseController from '../base-http-api-controller.js'; class ResultController extends BaseController { @@ -6,10 +6,10 @@ class ResultController extends BaseController { super(ctx); this.operationIdService = ctx.operationIdService; - this.availableOperations = ctx.httpApiService.getAvailableOperations('old'); + this.availableOperations = HTTP_API_ROUTES.v0.map((route) => route.name); } - async handleOperationResultRequest(req, res) { + async handleRequest(req, res) { if (!this.availableOperations.includes(req.params.operation)) { return this.returnResponse(res, 400, { code: 400, diff --git a/src/controllers/http-api/old/update-http-api-controller-old.js b/src/controllers/http-api/v0/update-http-api-controller-v0.js similarity index 98% rename from src/controllers/http-api/old/update-http-api-controller-old.js rename to src/controllers/http-api/v0/update-http-api-controller-v0.js index ed79327aee..17ecfffcb7 100644 --- a/src/controllers/http-api/old/update-http-api-controller-old.js +++ b/src/controllers/http-api/v0/update-http-api-controller-v0.js @@ -16,7 +16,7 @@ class UpdateController extends BaseController { this.repositoryModuleManager = ctx.repositoryModuleManager; } - async handleUpdateRequest(req, res) { + async handleRequest(req, res) { const operationId = await this.operationIdService.generateOperationId( OPERATION_ID_STATUS.UPDATE.UPDATE_START, ); diff --git a/src/controllers/http-api/v1/info-http-api-controller-v1.js b/src/controllers/http-api/v1/info-http-api-controller-v1.js index 241f65d465..5a960deed7 100644 --- a/src/controllers/http-api/v1/info-http-api-controller-v1.js +++ b/src/controllers/http-api/v1/info-http-api-controller-v1.js @@ -5,7 +5,7 @@ const require = createRequire(import.meta.url); const { version } = require('../../../../package.json'); class InfoControllerV1 extends BaseController { - handleInfoRequest(_, res) { + handleRequest(_, res) { this.returnResponse(res, 200, { version, ...this.filterConfig(), diff --git a/src/modules/http-client/http-client-module-manager.js b/src/modules/http-client/http-client-module-manager.js index a2bede9b12..c76b85ed95 100644 --- a/src/modules/http-client/http-client-module-manager.js +++ b/src/modules/http-client/http-client-module-manager.js @@ -23,7 +23,7 @@ class HttpClientModuleManager extends BaseModuleManager { } } - use(route, callback, options) { + use(route, callback, options = {}) { if (this.initialized) { return this.getImplementation().module.use(route, callback, options); } @@ -47,6 +47,12 @@ class HttpClientModuleManager extends BaseModuleManager { } } + selectMiddlewares(options) { + if (this.initialized) { + return this.getImplementation().module.selectMiddlewares(options); + } + } + initializeBeforeMiddlewares() { if (this.initialized) { return this.getImplementation().module.initializeBeforeMiddlewares(this.authService); diff --git a/src/modules/http-client/implementation/express-http-client.js b/src/modules/http-client/implementation/express-http-client.js index 345cc5339c..cd37b698c2 100644 --- a/src/modules/http-client/implementation/express-http-client.js +++ b/src/modules/http-client/implementation/express-http-client.js @@ -25,7 +25,7 @@ class ExpressHttpClient { } use(route, callback, options) { - this.app.use(route, callback, options); + this.app.use(route, ...this.selectMiddlewares(options), callback); } createRouterInstance() { diff --git a/src/service/http-api-service.js b/src/service/http-api-service.js deleted file mode 100644 index db1309a2c2..0000000000 --- a/src/service/http-api-service.js +++ /dev/null @@ -1,54 +0,0 @@ -import fs from 'fs'; -import path from 'path'; -import stringUtil from './util/string-util.js'; - -class HttpApiService { - constructor(ctx) { - this.fileService = ctx.fileService; - } - - getApiVersions(sort = false) { - const httpControllersPath = this.fileService.getHttpControllersFolderPath(); - const versions = fs.readdirSync(httpControllersPath).filter((folder) => { - if (!fs.statSync(path.join(httpControllersPath, folder)).isDirectory()) return false; - if (folder === 'old') return true; - return /^v\d+$/.test(folder); - }); - - if (sort) { - return versions.sort((a, b) => { - if (a === 'old') return 1; - if (b === 'old') return -1; - - return parseInt(b.substring(1), 10) - parseInt(a.substring(1), 10); - }); - } - - return versions; - } - - getAvailableOperations(version, camelCase = false) { - const versionFolder = path.join(this.fileService.getHttpControllersFolderPath(), version); - - const operations = []; - for (const controller of fs.readdirSync(versionFolder)) { - let operation; - - if (!controller.endsWith(`-http-api-controller-${version}.js`)) { - continue; - } else { - operation = controller.replace(`-http-api-controller-${version}.js`, ''); - } - - if (camelCase) { - operations.push(stringUtil.toCamelCase(operation)); - } else { - operations.push(operation); - } - } - - return operations; - } -} - -export default HttpApiService; diff --git a/src/service/json-schema-service.js b/src/service/json-schema-service.js index 555fe10a5c..53059969c5 100644 --- a/src/service/json-schema-service.js +++ b/src/service/json-schema-service.js @@ -6,7 +6,7 @@ class JsonSchemaService { this.blockchainModuleManager = ctx.blockchainModuleManager; } - async loadSchema(version, schemaName) { + async loadSchema(version, schemaName, argumentsObject = {}) { const schemaPath = path.resolve( appRootPath.path, `src/controllers/http-api/${version}/request-schema/${schemaName}-schema-${version}.js`, @@ -14,35 +14,35 @@ class JsonSchemaService { const schemaModule = await import(schemaPath); const schemaFunction = schemaModule.default; - if (schemaFunction.length >= 1) { - return schemaFunction(this.blockchainModuleManager.getImplementationNames()); + if (schemaFunction.length !== 0) { + return schemaFunction(argumentsObject); } return schemaFunction(); } - async bidSuggestionSchema(version) { - return this.loadSchema(version, 'bid-suggestion'); + async bidSuggestionSchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'bid-suggestion', argumentsObject); } - async publishSchema(version) { - return this.loadSchema(version, 'publish'); + async publishSchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'publish', argumentsObject); } - async updateSchema(version) { - return this.loadSchema(version, 'update'); + async updateSchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'update', argumentsObject); } - async getSchema(version) { - return this.loadSchema(version, 'get'); + async getSchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'get', argumentsObject); } - async querySchema(version) { - return this.loadSchema(version, 'query'); + async querySchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'query', argumentsObject); } - async localStoreSchema(version) { - return this.loadSchema(version, 'local-store'); + async localStoreSchema(version, argumentsObject = {}) { + return this.loadSchema(version, 'local-store', argumentsObject); } } From 2273369799c3ffff4453b45910cfe63756108e12 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 16 Aug 2023 13:30:04 +0100 Subject: [PATCH 05/18] Added missing schema args to the HTTP API routes config --- src/constants/constants.js | 46 +++++++++++++++++++++++++++++++++----- 1 file changed, 41 insertions(+), 5 deletions(-) diff --git a/src/constants/constants.js b/src/constants/constants.js index 28c3836f2a..948f61311b 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -441,28 +441,56 @@ export const HTTP_API_ROUTES = { name: 'update', path: '/update', controller: 'updateHttpApiControllerV0', - options: { rateLimit: true, schema: { name: 'updateSchema', args: {} } }, + options: { + rateLimit: true, + schema: { + name: 'updateSchema', + args: { + blockchainImplementationNames: + 'blockchainModuleManager.getImplementationNames', + }, + }, + }, }, { method: 'post', name: 'query', path: '/query', controller: 'queryHttpApiControllerV0', - options: { schema: { name: 'querySchema', args: {} } }, + options: { + schema: { + name: 'querySchema', + args: {}, + }, + }, }, { method: 'post', name: 'local-store', path: '/local-store', controller: 'localStoreHttpApiControllerV0', - options: { schema: { name: 'localStoreSchema', args: {} } }, + options: { + schema: { + name: 'localStoreSchema', + args: { + blockchainImplementationNames: + 'blockchainModuleManager.getImplementationNames', + }, + }, + }, }, { method: 'post', name: 'get', path: '/get', controller: 'getHttpApiControllerV0', - options: { rateLimit: true, schema: { name: 'getSchema', args: {} } }, + options: { + rateLimit: true, + schema: { + name: 'getSchema', + args: {}, + }, + }, }, { method: 'get', @@ -483,7 +511,15 @@ export const HTTP_API_ROUTES = { name: 'bid-suggestion', path: '/bid-suggestion', controller: 'bidSuggestionHttpApiControllerV0', - options: { schema: { name: 'bidSuggestionSchema', args: {} } }, + options: { + schema: { + name: 'bidSuggestionSchema', + args: { + blockchainImplementationNames: + 'blockchainModuleManager.getImplementationNames', + }, + }, + }, }, ], v1: [ From 12ff02ebcaab1a74c2734406c4476e48024d17e0 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 16 Aug 2023 13:44:37 +0100 Subject: [PATCH 06/18] Changed HTTP API Routes config description --- src/constants/constants.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/constants/constants.js b/src/constants/constants.js index 948f61311b..a277338122 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -416,7 +416,7 @@ export const COMMAND_QUEUE_PARALLELISM = 100; /** * @constant {object} HTTP_API_ROUTES - - * Network protocols + * HTTP API Routes with parameters */ export const HTTP_API_ROUTES = { v0: [ From 9de28fa1794cef9ac7ea163b20cab71cb5e83484 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 16 Aug 2023 13:48:45 +0100 Subject: [PATCH 07/18] Removed redundant function --- src/service/file-service.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/src/service/file-service.js b/src/service/file-service.js index 74cc66e24c..aa1c5be91b 100644 --- a/src/service/file-service.js +++ b/src/service/file-service.js @@ -104,10 +104,6 @@ class FileService { } } - getHttpControllersFolderPath() { - return path.join(appRootPath.path, 'src/controllers/http-api'); - } - getDataFolderPath() { if (process.env.NODE_ENV === 'testnet' || process.env.NODE_ENV === 'mainnet') { return path.join(appRootPath.path, '..', this.config.appDataPath); From 3f6b496d014c3a9d5ca6bd65ba92edb88ac57ae3 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Wed, 16 Aug 2023 15:33:03 +0100 Subject: [PATCH 08/18] Shortened HTTP API Routes config, reworked generic listeners initialization and jsonSchemaService --- src/constants/constants.js | 101 ++++-------------- src/controllers/http-api/http-api-router.js | 52 +++------ .../v0/result-http-api-controller-v0.js | 4 +- .../v1/info-http-api-controller-v1.js | 10 +- src/service/json-schema-service.js | 86 ++++++++++++--- 5 files changed, 116 insertions(+), 137 deletions(-) diff --git a/src/constants/constants.js b/src/constants/constants.js index a277338122..9aa8f14b6e 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -419,118 +419,55 @@ export const COMMAND_QUEUE_PARALLELISM = 100; * HTTP API Routes with parameters */ export const HTTP_API_ROUTES = { - v0: [ - { + v0: { + publish: { method: 'post', - name: 'publish', path: '/publish', - controller: 'publishHttpApiControllerV0', - options: { - rateLimit: true, - schema: { - name: 'publishSchema', - args: { - blockchainImplementationNames: - 'blockchainModuleManager.getImplementationNames', - }, - }, - }, + options: { rateLimit: true }, }, - { + update: { method: 'post', - name: 'update', path: '/update', - controller: 'updateHttpApiControllerV0', - options: { - rateLimit: true, - schema: { - name: 'updateSchema', - args: { - blockchainImplementationNames: - 'blockchainModuleManager.getImplementationNames', - }, - }, - }, + options: { rateLimit: true }, }, - { + query: { method: 'post', - name: 'query', path: '/query', - controller: 'queryHttpApiControllerV0', - options: { - schema: { - name: 'querySchema', - args: {}, - }, - }, + options: {}, }, - { + 'local-store': { method: 'post', - name: 'local-store', path: '/local-store', - controller: 'localStoreHttpApiControllerV0', - options: { - schema: { - name: 'localStoreSchema', - args: { - blockchainImplementationNames: - 'blockchainModuleManager.getImplementationNames', - }, - }, - }, + options: { schema: 'localStoreSchema' }, }, - { + get: { method: 'post', - name: 'get', path: '/get', - controller: 'getHttpApiControllerV0', - options: { - rateLimit: true, - schema: { - name: 'getSchema', - args: {}, - }, - }, + options: { rateLimit: true }, }, - { + result: { method: 'get', - name: 'result', path: '/:operation/:operationId', - controller: 'resultHttpApiControllerV0', options: {}, }, - { + info: { method: 'get', - name: 'info', path: '/info', - controller: 'infoHttpApiControllerV0', options: {}, }, - { + 'bid-suggestion': { method: 'get', - name: 'bid-suggestion', path: '/bid-suggestion', - controller: 'bidSuggestionHttpApiControllerV0', - options: { - schema: { - name: 'bidSuggestionSchema', - args: { - blockchainImplementationNames: - 'blockchainModuleManager.getImplementationNames', - }, - }, - }, + options: {}, }, - ], - v1: [ - { + }, + v1: { + info: { method: 'get', - name: 'info', path: '/info', - controller: 'infoHttpApiControllerV1', options: {}, }, - ], + }, }; /** diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index f992783abd..c512822bfe 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -13,7 +13,7 @@ class HttpApiRouter { for (const version of this.apiVersions) { this.routers[version] = this.httpClientModuleManager.createRouterInstance(); - const operations = this.apiRoutes[version].map((route) => route.name); + const operations = Object.keys(this.apiRoutes[version]); for (const operation of operations) { const versionedOperation = `${stringUtil.toCamelCase( @@ -45,25 +45,20 @@ class HttpApiRouter { const mountedLatestRoutes = new Set(); for (const version of descendingOrderedVersions) { - for (const route of this.apiRoutes[version]) { - const { method, path, controller, options } = route; - - if (options.schema) { - const argumentsObject = {}; - - for (const [argName, argFuncRef] of Object.entries(options.schema.args)) { - // eslint-disable-next-line no-await-in-loop - argumentsObject[argName] = await this._executeFunctionFromConfigRef( - this, - argFuncRef, - ); - } - + for (const [name, route] of Object.entries(this.apiRoutes[version])) { + const { method, path, options } = route; + const camelRouteName = stringUtil.toCamelCase(name); + const controller = `${camelRouteName}HttpApiController${stringUtil.capitalize( + version, + )}`; + const schema = `${camelRouteName}Schema`; + + if ( + schema in this.jsonSchemaService && + typeof this.jsonSchemaService[schema] === 'function' + ) { // eslint-disable-next-line no-await-in-loop - options.requestSchema = await this.jsonSchemaService[options.schema.name]( - version, - argumentsObject, - ); + options.requestSchema = await this.jsonSchemaService[schema](version); } const middlewares = this.httpClientModuleManager.selectMiddlewares(options); @@ -93,25 +88,6 @@ class HttpApiRouter { initializeAfterMiddlewares() { this.httpClientModuleManager.initializeAfterMiddlewares(); } - - async _executeFunctionFromConfigRef(context, reference) { - const parts = reference.split('.'); - const fnName = parts.pop(); - const objRef = parts.reduce((acc, part) => acc[part], context); - - if (objRef && typeof objRef[fnName] === 'function') { - const result = objRef[fnName](); - - if (result instanceof Promise) { - // eslint-disable-next-line no-return-await - return await result; - } - - return result; - } - - throw new Error(`Function ${reference} not found.`); - } } export default HttpApiRouter; diff --git a/src/controllers/http-api/v0/result-http-api-controller-v0.js b/src/controllers/http-api/v0/result-http-api-controller-v0.js index 83f0d92f3b..de5999f05a 100644 --- a/src/controllers/http-api/v0/result-http-api-controller-v0.js +++ b/src/controllers/http-api/v0/result-http-api-controller-v0.js @@ -1,4 +1,4 @@ -import { HTTP_API_ROUTES, OPERATION_ID_STATUS } from '../../../constants/constants.js'; +import { OPERATION_ID_STATUS } from '../../../constants/constants.js'; import BaseController from '../base-http-api-controller.js'; class ResultController extends BaseController { @@ -6,7 +6,7 @@ class ResultController extends BaseController { super(ctx); this.operationIdService = ctx.operationIdService; - this.availableOperations = HTTP_API_ROUTES.v0.map((route) => route.name); + this.availableOperations = ['publish', 'get', 'query', 'local-store', 'update']; } async handleRequest(req, res) { diff --git a/src/controllers/http-api/v1/info-http-api-controller-v1.js b/src/controllers/http-api/v1/info-http-api-controller-v1.js index 5a960deed7..09cb3ceb00 100644 --- a/src/controllers/http-api/v1/info-http-api-controller-v1.js +++ b/src/controllers/http-api/v1/info-http-api-controller-v1.js @@ -5,6 +5,12 @@ const require = createRequire(import.meta.url); const { version } = require('../../../../package.json'); class InfoControllerV1 extends BaseController { + constructor(ctx) { + super(ctx); + + this.blockchainModuleManager = ctx.blockchainModuleManager; + } + handleRequest(_, res) { this.returnResponse(res, 200, { version, @@ -17,9 +23,7 @@ class InfoControllerV1 extends BaseController { tripleStores: Object.entries(this.config.modules.tripleStore.implementation) .filter(([, value]) => value.enabled) .map(([key]) => key), - blockchains: Object.entries(this.config.modules.blockchain.implementation) - .filter(([, value]) => value.enabled) - .map(([key]) => key), + blockchains: this.blockchainModuleManager.getImplementationNames(), }; return nodeConfigData; diff --git a/src/service/json-schema-service.js b/src/service/json-schema-service.js index 53059969c5..859d9edab2 100644 --- a/src/service/json-schema-service.js +++ b/src/service/json-schema-service.js @@ -21,28 +21,90 @@ class JsonSchemaService { return schemaFunction(); } - async bidSuggestionSchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'bid-suggestion', argumentsObject); + async bidSuggestionSchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + schemaArgs.blockchainImplementationNames = + this.blockchainModuleManager.getImplementationNames(); + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'bid-suggestion', schemaArgs); } - async publishSchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'publish', argumentsObject); + async publishSchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + schemaArgs.blockchainImplementationNames = + this.blockchainModuleManager.getImplementationNames(); + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'publish', schemaArgs); } - async updateSchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'update', argumentsObject); + async updateSchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + schemaArgs.blockchainImplementationNames = + this.blockchainModuleManager.getImplementationNames(); + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'update', schemaArgs); } - async getSchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'get', argumentsObject); + async getSchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'get', schemaArgs); } - async querySchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'query', argumentsObject); + async querySchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'query', schemaArgs); } - async localStoreSchema(version, argumentsObject = {}) { - return this.loadSchema(version, 'local-store', argumentsObject); + async localStoreSchema(version) { + const schemaArgs = {}; + + switch (version) { + case 'v0': + schemaArgs.blockchainImplementationNames = + this.blockchainModuleManager.getImplementationNames(); + break; + default: + throw Error(`HTTP API version: ${version} isn't supported.`); + } + + return this.loadSchema(version, 'local-store', schemaArgs); } } From fa23f6834af943d664ae805b9f5ec3cbdc76748b Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 17 Aug 2023 09:51:25 +0100 Subject: [PATCH 09/18] Removed redundant schema definition in the HTTP API Routes config --- src/constants/constants.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/constants/constants.js b/src/constants/constants.js index 9aa8f14b6e..3e394b8d18 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -438,7 +438,7 @@ export const HTTP_API_ROUTES = { 'local-store': { method: 'post', path: '/local-store', - options: { schema: 'localStoreSchema' }, + options: {}, }, get: { method: 'post', From 81095863d75f07789f61e924857aca14ad17e833 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 17 Aug 2023 09:53:08 +0100 Subject: [PATCH 10/18] Variable naming fix --- src/controllers/http-api/http-api-router.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index c512822bfe..e116ecbba2 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -16,10 +16,10 @@ class HttpApiRouter { const operations = Object.keys(this.apiRoutes[version]); for (const operation of operations) { - const versionedOperation = `${stringUtil.toCamelCase( + const versionedController = `${stringUtil.toCamelCase( operation, )}HttpApiController${stringUtil.capitalize(version)}`; - this[versionedOperation] = ctx[versionedOperation]; + this[versionedController] = ctx[versionedController]; } } this.routers.latest = this.httpClientModuleManager.createRouterInstance(); From 181ce0ff468cfad8fbcf769e1e9abded581cdacf Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 17 Aug 2023 09:54:17 +0100 Subject: [PATCH 11/18] Removed redundant module from http api router --- src/controllers/http-api/http-api-router.js | 1 - 1 file changed, 1 deletion(-) diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index e116ecbba2..3643850f1f 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -24,7 +24,6 @@ class HttpApiRouter { } this.routers.latest = this.httpClientModuleManager.createRouterInstance(); - this.blockchainModuleManager = ctx.blockchainModuleManager; this.jsonSchemaService = ctx.jsonSchemaService; } From 6338efd73f6417e31c1975ea8ac302246f67aba8 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 17 Aug 2023 11:29:16 +0100 Subject: [PATCH 12/18] Removed redundant module from http client module manager --- src/modules/http-client/http-client-module-manager.js | 1 - 1 file changed, 1 deletion(-) diff --git a/src/modules/http-client/http-client-module-manager.js b/src/modules/http-client/http-client-module-manager.js index c76b85ed95..aef322cf6d 100644 --- a/src/modules/http-client/http-client-module-manager.js +++ b/src/modules/http-client/http-client-module-manager.js @@ -4,7 +4,6 @@ class HttpClientModuleManager extends BaseModuleManager { constructor(ctx) { super(ctx); this.authService = ctx.authService; - this.fileService = ctx.fileService; } getName() { From 03370f122f878cbaedad814f45ef4c281d3e0262 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 17 Aug 2023 15:12:57 +0100 Subject: [PATCH 13/18] Added new Postman API collection --- postman/DKGv6.postman_collection.json | 2180 +++++++++++++++++++------ 1 file changed, 1667 insertions(+), 513 deletions(-) diff --git a/postman/DKGv6.postman_collection.json b/postman/DKGv6.postman_collection.json index 0b358e7617..bd257955e4 100644 --- a/postman/DKGv6.postman_collection.json +++ b/postman/DKGv6.postman_collection.json @@ -1,620 +1,1774 @@ { "info": { - "_postman_id": "de092a3d-311c-4c22-9fdb-1f1b777c8bbb", + "_postman_id": "550b0443-cd47-482a-9c56-2b1229422426", "name": "DKGv6", + "description": "DKG v6 API Collection.", "schema": "https://schema.getpostman.com/json/collection/v2.1.0/collection.json" }, "item": [ { - "name": "Asset API", + "name": "old", "item": [ { - "name": "Provision", + "name": "Node Info", "request": { - "auth": { - "type": "noauth" + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "url": { + "raw": "{{host}}:{{port}}/info", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "info" + ] + }, + "description": "Get the node information." + }, + "response": [ + { + "name": "Node Info", + "originalRequest": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "url": { + "raw": "{{host}}:{{port}}/info", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "info" + ] + } + }, + "status": "OK", + "code": 200, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "20" + }, + { + "key": "ETag", + "value": "W/\"14-Rq/28W5aGKCGXmXfM1+eW1LAbb4\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 12:43:07 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"version\": \"6.0.13\"\n}" + } + ] + }, + { + "name": "Get Bid Suggestion", + "protocolProfileBehavior": { + "disableBodyPruning": true + }, + "request": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "body": { + "mode": "raw", + "raw": "" + }, + "url": { + "raw": "{{host}}:{{port}}/bid-suggestion?blockchain={{blockchain}}&epochsNumber={{epochsNumber}}&assertionSize={{assertionSize}}&contentAssetStorageAddress={{contentAssetStorageAddress}}&firstAssertionId={{firstAssertionId}}&hashFunctionId={{hashFunctionId}}", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "bid-suggestion" + ], + "query": [ + { + "key": "blockchain", + "value": "{{blockchain}}" + }, + { + "key": "epochsNumber", + "value": "{{epochsNumber}}" + }, + { + "key": "assertionSize", + "value": "{{assertionSize}}" + }, + { + "key": "contentAssetStorageAddress", + "value": "{{contentAssetStorageAddress}}" + }, + { + "key": "firstAssertionId", + "value": "{{firstAssertionId}}" + }, + { + "key": "hashFunctionId", + "value": "{{hashFunctionId}}" + } + ] + }, + "description": "Get bid suggestion based on provided parameters." + }, + "response": [ + { + "name": "Get Bid Suggestion", + "originalRequest": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "body": { + "mode": "raw", + "raw": "" + }, + "url": { + "raw": "{{host}}:{{port}}/bid-suggestion?blockchain={{blockchain}}&epochsNumber={{epochsNumber}}&assertionSize={{assertionSize}}&contentAssetStorageAddress={{contentAssetStorageAddress}}&firstAssertionId={{firstAssertionId}}&hashFunctionId={{hashFunctionId}}", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "bid-suggestion" + ], + "query": [ + { + "key": "blockchain", + "value": "{{blockchain}}" + }, + { + "key": "epochsNumber", + "value": "{{epochsNumber}}" + }, + { + "key": "assertionSize", + "value": "{{assertionSize}}" + }, + { + "key": "contentAssetStorageAddress", + "value": "{{contentAssetStorageAddress}}" + }, + { + "key": "firstAssertionId", + "value": "{{firstAssertionId}}" + }, + { + "key": "hashFunctionId", + "value": "{{hashFunctionId}}" + } + ] + } + }, + "status": "OK", + "code": 200, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "38" + }, + { + "key": "ETag", + "value": "W/\"26-UrjseieOcIBnowM9obJae/FG7xc\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 12:42:31 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"bidSuggestion\": \"903051579928002449\"\n}" + } + ] + }, + { + "name": "Local Store", + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{{assertions}}" + }, + "url": { + "raw": "{{host}}:{{port}}/local-store", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "local-store" + ] + }, + "description": "Store locally." + }, + "response": [ + { + "name": "Local Store", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{{assertions}}" + }, + "url": { + "raw": "{{host}}:{{port}}/local-store", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "local-store" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-uF3l7SNXwSBVObRCAJxOmp8OJGc\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 12:49:45 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"7d499975-ce42-4d84-9092-0ac2a62f5151\"\n}" + } + ] + }, + { + "name": "Publish Knowledge Asset", + "protocolProfileBehavior": { + "disabledSystemHeaders": { + "content-type": true + } + }, + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf\",\n \"assertion\": [\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/publish", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "publish" + ] + }, + "description": "Publish assertion." + }, + "response": [ + { + "name": "Publish Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf\",\n \"assertion\": [\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/publish", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "publish" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, + { + "key": "RateLimit-Reset", + "value": "22" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-SQS1f7vf+HLSUHZ6wvE9UUwksSY\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:07:57 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"8270c131-91b8-4573-a69e-504ff388a8b6\"\n}" + } + ] + }, + { + "name": "Get Knowledge Asset", + "protocolProfileBehavior": { + "disabledSystemHeaders": {} + }, + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"id\": \"did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0\",\n \"state\": \"LATEST\",\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/get", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "get" + ] + }, + "description": "Get an assertion." + }, + "response": [ + { + "name": "Get Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"id\": \"did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0\",\n \"state\": \"LATEST\",\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/get", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "get" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, + { + "key": "RateLimit-Reset", + "value": "12" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-tXDgcL88Mx02VotKK9H3zPuWwf8\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:16:39 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"3a6df062-b3ce-4cac-aefa-77b1e8b9a4db\"\n}" + } + ] + }, + { + "name": "Update Knowledge Asset", + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0\",\n \"assertion\": [\n \" .\",\n \" 'TL' .\",\n \" .\",\n \"_:c14n0 '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" }, + "url": { + "raw": "{{host}}:{{port}}/update", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "update" + ] + }, + "description": "Update assertion." + }, + "response": [ + { + "name": "Update Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0\",\n \"assertion\": [\n \" .\",\n \" 'TL' .\",\n \" .\",\n \"_:c14n0 '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/update", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "update" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, + { + "key": "RateLimit-Reset", + "value": "57" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-CjvPRlFINYIIcvR2H5gFBcOkNH8\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:17:54 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"0d4c3efc-0f0b-435d-b9a3-402748dbbb2f\"\n}" + } + ] + }, + { + "name": "Query DKG", + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"query\": \"CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH { ?s ?p ?o . }}}\",\n \"type\": \"CONSTRUCT\",\n \"repository\": \"privateCurrent\"\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/query", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "query" + ] + }, + "description": "Execute a query." + }, + "response": [ + { + "name": "Query DKG", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"query\": \"CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH { ?s ?p ?o . }}}\",\n \"type\": \"CONSTRUCT\",\n \"repository\": \"privateCurrent\"\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/query", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "query" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-WRBDN6AcKKCbVi3DGfI6FvESm5w\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:20:16 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"746992ba-e607-4858-8deb-5cffc2541859\"\n}" + } + ] + }, + { + "name": "Get Operation Result", + "request": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "url": { + "raw": "{{host}}:{{port}}/{{operation}}/{{operationId}}", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "{{operation}}", + "{{operationId}}" + ] + }, + "description": "Get result of a specific operation by its ID." + }, + "response": [] + } + ] + }, + { + "name": "v0", + "item": [ + { + "name": "[v0] Node Info", + "request": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "url": { + "raw": "{{host}}:{{port}}/v0/info", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "info" + ] + }, + "description": "Get the node information." + }, + "response": [ + { + "name": "[v0] Node Info", + "originalRequest": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "url": { + "raw": "{{host}}:{{port}}/v0/info", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "info" + ] + } + }, + "status": "OK", + "code": 200, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "20" + }, + { + "key": "ETag", + "value": "W/\"14-Rq/28W5aGKCGXmXfM1+eW1LAbb4\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:27:58 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"version\": \"6.0.13\"\n}" + } + ] + }, + { + "name": "[v0] Get Bid Suggestion", + "protocolProfileBehavior": { + "disableBodyPruning": true + }, + "request": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "body": { + "mode": "raw", + "raw": "" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/bid-suggestion?blockchain={{blockchain}}&epochsNumber={{epochsNumber}}&assertionSize={{assertionSize}}&contentAssetStorageAddress={{contentAssetStorageAddress}}&firstAssertionId={{firstAssertionId}}&hashFunctionId={{hashFunctionId}}", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "bid-suggestion" + ], + "query": [ + { + "key": "blockchain", + "value": "{{blockchain}}" + }, + { + "key": "epochsNumber", + "value": "{{epochsNumber}}" + }, + { + "key": "assertionSize", + "value": "{{assertionSize}}" + }, + { + "key": "contentAssetStorageAddress", + "value": "{{contentAssetStorageAddress}}" + }, + { + "key": "firstAssertionId", + "value": "{{firstAssertionId}}" + }, + { + "key": "hashFunctionId", + "value": "{{hashFunctionId}}" + } + ] + }, + "description": "Get bid suggestion based on provided parameters." + }, + "response": [ + { + "name": "[v0] Get Bid Suggestion", + "originalRequest": { + "method": "GET", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], + "body": { + "mode": "raw", + "raw": "" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/bid-suggestion?blockchain={{blockchain}}&epochsNumber={{epochsNumber}}&assertionSize={{assertionSize}}&contentAssetStorageAddress={{contentAssetStorageAddress}}&firstAssertionId={{firstAssertionId}}&hashFunctionId={{hashFunctionId}}", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "bid-suggestion" + ], + "query": [ + { + "key": "blockchain", + "value": "{{blockchain}}" + }, + { + "key": "epochsNumber", + "value": "{{epochsNumber}}" + }, + { + "key": "assertionSize", + "value": "{{assertionSize}}" + }, + { + "key": "contentAssetStorageAddress", + "value": "{{contentAssetStorageAddress}}" + }, + { + "key": "firstAssertionId", + "value": "{{firstAssertionId}}" + }, + { + "key": "hashFunctionId", + "value": "{{hashFunctionId}}" + } + ] + } + }, + "status": "OK", + "code": 200, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "39" + }, + { + "key": "ETag", + "value": "W/\"27-ieFm/6t4DZwm0kFCMq71s37uy/g\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:59:02 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"bidSuggestion\": \"1122511549276000025\"\n}" + } + ] + }, + { + "name": "[v0] Local Store", + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{{assertions}}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/local-store", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "local-store" + ] + }, + "description": "Store locally." + }, + "response": [ + { + "name": "[v0] Local Store", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{{assertions}}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/local-store", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "local-store" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-fpQtTlhbbWO7tqbMGm3CkKmOqaI\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 13:59:11 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"0a4ee669-95bb-41cd-a2e8-3382361e80d9\"\n}" + } + ] + }, + { + "name": "[v0] Publish Knowledge Asset", + "protocolProfileBehavior": { + "disabledSystemHeaders": { + "content-type": true + } + }, + "request": { "method": "POST", - "header": [], + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], "body": { - "mode": "formdata", - "formdata": [ + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf\",\n \"assertion\": [\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/publish", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "publish" + ] + }, + "description": "Publish assertion." + }, + "response": [ + { + "name": "[v0] Publish Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf\",\n \"assertion\": [\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/publish", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "publish" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, + { + "key": "RateLimit-Reset", + "value": "52" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-wKIhHpa0/tdVYh1Y8D2yINolruA\"" + }, { - "key": "file", - "type": "file", - "src": "/Users/nikolatodorovic/v6/ot-node/demo-data/Feynman.json" + "key": "Date", + "value": "Thu, 17 Aug 2023 13:59:54 GMT" }, { - "key": "keywords", - "value": "[\"Feynman\",\"Physics\", \"Scientist\"]", - "type": "text" + "key": "Connection", + "value": "keep-alive" }, { - "key": "visibility", - "value": "public", - "type": "text" + "key": "Keep-Alive", + "value": "timeout=5" } - ] - }, - "url": { - "raw": "{{HOST}}:8900/provision", - "host": [ - "{{HOST}}" ], - "port": "8900", - "path": [ - "provision" - ] + "cookie": [], + "body": "{\n \"operationId\": \"476fb996-db1a-47b8-8da4-80d71411feb3\"\n}" } - }, - "response": [] + ] }, { - "name": "Provision Result", + "name": "[v0] Get Knowledge Asset", "protocolProfileBehavior": { - "disableBodyPruning": true + "disabledSystemHeaders": {} }, "request": { - "method": "GET", - "header": [], + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], "body": { - "mode": "formdata", - "formdata": [] + "mode": "raw", + "raw": "{\n \"id\": \"did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0\",\n \"state\": \"LATEST\",\n \"hashFunctionId\": 1\n}" }, "url": { - "raw": "{{HOST}}:8900/provision/result/7f3c1fef-2588-45e6-b6f6-72f115da6553", + "raw": "{{host}}:{{port}}/v0/get", "host": [ - "{{HOST}}" + "{{host}}" ], - "port": "8900", + "port": "{{port}}", "path": [ - "provision", - "result", - "7f3c1fef-2588-45e6-b6f6-72f115da6553" + "v0", + "get" ] - } - }, - "response": [] - }, - { - "name": "Update", - "request": { - "auth": { - "type": "noauth" }, - "method": "POST", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ + "description": "Get an assertion." + }, + "response": [ + { + "name": "[v0] Get Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"id\": \"did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0\",\n \"state\": \"LATEST\",\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/get", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "get" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, { - "key": "file", - "type": "file", - "src": "/Users/nikolatodorovic/v6/ot-node/demo-data/Feynman.json" + "key": "RateLimit-Reset", + "value": "44" }, { - "key": "keywords", - "value": "[\"Feynman\",\"Physics\", \"Scientist\"]", - "type": "text" + "key": "Content-Type", + "value": "application/json; charset=utf-8" }, { - "key": "visibility", - "value": "public", - "type": "text" + "key": "Content-Length", + "value": "54" }, { - "key": "ual", - "value": "c37c86b59ba64ab269850860621b634feaab9f500a73ef5620000b8b55dcb29a", - "type": "text" + "key": "ETag", + "value": "W/\"36-/27PH/ZH74wwVBrYDxWSzCk4yA0\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 14:00:02 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" } - ] + ], + "cookie": [], + "body": "{\n \"operationId\": \"5b34c048-2d08-4696-b3c4-c37c831b89ce\"\n}" + } + ] + }, + { + "name": "[v0] Update Knowledge Asset", + "request": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0\",\n \"assertion\": [\n \" .\",\n \" 'TL' .\",\n \" .\",\n \"_:c14n0 '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" }, "url": { - "raw": "{{HOST}}:8900/update", + "raw": "{{host}}:{{port}}/v0/update", "host": [ - "{{HOST}}" + "{{host}}" ], - "port": "8900", + "port": "{{port}}", "path": [ + "v0", "update" ] - } + }, + "description": "Update assertion." }, - "response": [] + "response": [ + { + "name": "[v0] Update Knowledge Asset", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"assertionId\": \"0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0\",\n \"assertion\": [\n \" .\",\n \" 'TL' .\",\n \" .\",\n \"_:c14n0 '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' .\"\n ],\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"hashFunctionId\": 1\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/update", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "update" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "RateLimit-Limit", + "value": "10" + }, + { + "key": "RateLimit-Remaining", + "value": "9" + }, + { + "key": "RateLimit-Reset", + "value": "38" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-77qAdgCc/SEN47aETAww86PM04w\"" + }, + { + "key": "Date", + "value": "Thu, 17 Aug 2023 14:00:09 GMT" + }, + { + "key": "Connection", + "value": "keep-alive" + }, + { + "key": "Keep-Alive", + "value": "timeout=5" + } + ], + "cookie": [], + "body": "{\n \"operationId\": \"f0d34032-6910-49b4-a2a8-71c9f58feb58\"\n}" + } + ] }, { - "name": "Update Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, + "name": "[v0] Query DKG", "request": { - "method": "GET", - "header": [], + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], "body": { - "mode": "formdata", - "formdata": [] + "mode": "raw", + "raw": "{\n \"query\": \"CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH { ?s ?p ?o . }}}\",\n \"type\": \"CONSTRUCT\",\n \"repository\": \"privateCurrent\"\n}" }, "url": { - "raw": "{{HOST}}:8900/update/result/36f9c131-130f-4d41-86e4-7cc6781bb51c", + "raw": "{{host}}:{{port}}/v0/query", "host": [ - "{{HOST}}" + "{{host}}" ], - "port": "8900", + "port": "{{port}}", "path": [ - "update", - "result", - "36f9c131-130f-4d41-86e4-7cc6781bb51c" + "v0", + "query" ] - } - }, - "response": [] - } - ] - }, - { - "name": "Low level API", - "item": [ - { - "name": "Publish", - "request": { - "auth": { - "type": "noauth" }, - "method": "POST", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ + "description": "Execute a query." + }, + "response": [ + { + "name": "[v0] Query DKG", + "originalRequest": { + "method": "POST", + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + }, + { + "key": "Content-Type", + "value": "application/json" + } + ], + "body": { + "mode": "raw", + "raw": "{\n \"query\": \"CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH { ?s ?p ?o . }}}\",\n \"type\": \"CONSTRUCT\",\n \"repository\": \"privateCurrent\"\n}" + }, + "url": { + "raw": "{{host}}:{{port}}/v0/query", + "host": [ + "{{host}}" + ], + "port": "{{port}}", + "path": [ + "v0", + "query" + ] + } + }, + "status": "Accepted", + "code": 202, + "_postman_previewlanguage": "json", + "header": [ + { + "key": "X-Powered-By", + "value": "Express" + }, + { + "key": "Access-Control-Allow-Origin", + "value": "*" + }, + { + "key": "Content-Type", + "value": "application/json; charset=utf-8" + }, + { + "key": "Content-Length", + "value": "54" + }, + { + "key": "ETag", + "value": "W/\"36-kqaRe64EoJygoEadXJWRekiCs4s\"" + }, { - "key": "file", - "type": "file", - "src": "/Users/nikolatodorovic/v6/ot-node/demo-data/Galileo.json" + "key": "Date", + "value": "Thu, 17 Aug 2023 14:00:19 GMT" }, { - "key": "keywords", - "value": "[\"Galileo\",\"Scientist\", \"Astronomer\"]", - "type": "text" + "key": "Connection", + "value": "keep-alive" }, { - "key": "visibility", - "value": "public", - "type": "text" + "key": "Keep-Alive", + "value": "timeout=5" } - ] - }, - "url": { - "raw": "{{HOST}}:8900/publish", - "host": [ - "{{HOST}}" ], - "port": "8900", - "path": [ - "publish" - ] + "cookie": [], + "body": "{\n \"operationId\": \"4d371ffb-a620-452f-8d16-3e427bafeae2\"\n}" } - }, - "response": [] + ] }, { - "name": "Publish Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, + "name": "[v0] Get Operation Result", "request": { "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, + "header": [ + { + "key": "Authorization", + "value": "Bearer {{authToken}}" + } + ], "url": { - "raw": "{{HOST}}:8900/publish/result/c6c3b9af-0f3c-4324-b5bf-0181d49baa04", + "raw": "{{host}}:{{port}}/{{operation}}/{{operationId}}", "host": [ - "{{HOST}}" + "{{host}}" ], - "port": "8900", + "port": "{{port}}", "path": [ - "publish", - "result", - "c6c3b9af-0f3c-4324-b5bf-0181d49baa04" + "{{operation}}", + "{{operationId}}" ] - } + }, + "description": "Get result of a specific operation by its ID." }, "response": [] } ] + } + ], + "auth": { + "type": "bearer", + "bearer": [ + { + "key": "token", + "value": "{{authToken}}", + "type": "string" + } + ] + }, + "event": [ + { + "listen": "prerequest", + "script": { + "type": "text/javascript", + "exec": [ + "" + ] + } }, { - "name": "Resolve", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/resolve?ids=c37c86b59ba64ab269850860621b634feaab9f500a73ef5620000b8b55dcb29a&load=true", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "resolve" - ], - "query": [ - { - "key": "ids", - "value": "c37c86b59ba64ab269850860621b634feaab9f500a73ef5620000b8b55dcb29a" - }, - { - "key": "load", - "value": "true" - } - ] - } - }, - "response": [] + "listen": "test", + "script": { + "type": "text/javascript", + "exec": [ + "" + ] + } + } + ], + "variable": [ + { + "key": "host", + "value": "localhost" }, { - "name": "Resolve Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/resolve/result/22419c1a-d41d-4235-9849-e7e1a22edf4f", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "resolve", - "result", - "22419c1a-d41d-4235-9849-e7e1a22edf4f" - ] - } - }, - "response": [] + "key": "port", + "value": "8900", + "type": "number" }, { - "name": "Assertions Search", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ - { - "key": "topic", - "value": "blazard1", - "type": "text", - "disabled": true - }, - { - "key": "limit", - "value": "100", - "type": "text", - "disabled": true - }, - { - "key": "offset", - "value": "0", - "type": "text", - "disabled": true - } - ] - }, - "url": { - "raw": "{{HOST}}:8900/assertions:search?query=scientist", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "assertions:search" - ], - "query": [ - { - "key": "query", - "value": "scientist" - }, - { - "key": "prefix", - "value": "true", - "disabled": true - }, - { - "key": "limit", - "value": "20", - "disabled": true - } - ] - } - }, - "response": [] + "key": "authToken", + "value": "", + "type": "string" }, { - "name": "Assertions Search Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/assertions:search/result/ccf90eba-4a45-4c47-81e0-1a2e1e679f70", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "assertions:search", - "result", - "ccf90eba-4a45-4c47-81e0-1a2e1e679f70" - ] - } - }, - "response": [] + "key": "blockchain", + "value": "hardhat" }, { - "name": "Search", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ - { - "key": "topic", - "value": "blazard1", - "type": "text", - "disabled": true - }, - { - "key": "limit", - "value": "100", - "type": "text", - "disabled": true - }, - { - "key": "offset", - "value": "0", - "type": "text", - "disabled": true - } - ] - }, - "url": { - "raw": "{{HOST}}:8900/entities:search?query=feynman", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "entities:search" - ], - "query": [ - { - "key": "prefix", - "value": "true", - "disabled": true - }, - { - "key": "ids", - "value": "", - "disabled": true - }, - { - "key": "types", - "value": "gs1-epcis", - "disabled": true - }, - { - "key": "limit", - "value": "20", - "disabled": true - }, - { - "key": "issuers", - "value": null, - "disabled": true - }, - { - "key": "query", - "value": "feynman" - } - ] - } - }, - "response": [] + "key": "epochsNumber", + "value": "5" }, { - "name": "Search Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/entities:search/result/b18a819d-d546-4bc2-95c1-242d78c094e7", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "entities:search", - "result", - "b18a819d-d546-4bc2-95c1-242d78c094e7" - ] - } - }, - "response": [] + "key": "assertionSize", + "value": "299" }, { - "name": "Query", - "request": { - "method": "POST", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ - { - "key": "query", - "value": "PREFIX schema: \nCONSTRUCT { ?s schema:name \"Richard Feynman\" }\nWHERE {\n GRAPH ?g { \n ?s schema:name \"Richard Feynman\" .\n }\n}", - "type": "text" - } - ] - }, - "url": { - "raw": "{{HOST}}:8900/query?type=construct", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "query" - ], - "query": [ - { - "key": "type", - "value": "construct" - } - ] - } - }, - "response": [] + "key": "contentAssetStorageAddress", + "value": "0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07" }, { - "name": "Query Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/query/result/d3480867-d5f7-4f10-9686-8c658c102dcf", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "query", - "result", - "d3480867-d5f7-4f10-9686-8c658c102dcf" - ] - } - }, - "response": [] + "key": "hashFunctionId", + "value": "1" }, { - "name": "Proofs", - "request": { - "method": "POST", - "header": [], - "body": { - "mode": "formdata", - "formdata": [ - { - "key": "nquads", - "value": "[ \"_:t1253 \\\"Richard Feynman\\\" .\"\n]", - "type": "text" - } - ] - }, - "url": { - "raw": "{{HOST}}:8900/proofs:get", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "proofs:get" - ] - } - }, - "response": [] + "key": "firstAssertionId", + "value": "0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf" }, { - "name": "Proofs Result", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/proofs:get/result/72d7c0b3-a41e-4f90-91d5-082579f25b65", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "proofs:get", - "result", - "72d7c0b3-a41e-4f90-91d5-082579f25b65" - ] - } - }, - "response": [] + "key": "assertions", + "value": "[\n {\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"assertionId\": \"0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf\",\n \"assertion\": [\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n ],\n \"storeType\": \"TRIPLE\"\n },\n {\n \"blockchain\": \"hardhat\",\n \"contract\": \"0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07\",\n \"tokenId\": 0,\n \"assertionId\": \"0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9\",\n \"assertion\": [\n \" '11000' .\",\n \" 'Belgrade' .\",\n \" 'Smith' .\",\n \" 'Adam' .\"\n ],\n \"storeType\": \"TRIPLE\"\n }\n]", + "type": "string" }, { - "name": "Info", - "protocolProfileBehavior": { - "disableBodyPruning": true - }, - "request": { - "method": "GET", - "header": [], - "body": { - "mode": "formdata", - "formdata": [] - }, - "url": { - "raw": "{{HOST}}:8900/info", - "host": [ - "{{HOST}}" - ], - "port": "8900", - "path": [ - "info" - ] - } - }, - "response": [] + "key": "assertionId", + "value": "0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf" + }, + { + "key": "assertion", + "value": "[\n \" .\",\n \" 'OT' .\",\n \" .\",\n \"_:c14n0 '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' .\"\n]", + "type": "string" + }, + { + "key": "contract", + "value": "0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07" + }, + { + "key": "tokenId", + "value": "1" + }, + { + "key": "UAL", + "value": "did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0" + }, + { + "key": "state", + "value": "LATEST" + }, + { + "key": "query", + "value": "CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH { ?s ?p ?o . }}}" + }, + { + "key": "type", + "value": "CONSTRUCT" + }, + { + "key": "repository", + "value": "privateCurrent" } ] } \ No newline at end of file From 2336220778ebb0af0222a184cdfedb4e5bac89e8 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Fri, 18 Aug 2023 13:00:21 +0100 Subject: [PATCH 14/18] Added HTTP API Router unit test --- .eslintrc.cjs | 1 + src/controllers/http-api/http-api-router.js | 2 +- test/unit/api/http-api-router.test.js | 80 +++++++++++++++++++ .../mock/http-client-module-manager-mock.js | 25 ++++++ test/unit/mock/json-schema-service-mock.js | 3 + 5 files changed, 110 insertions(+), 1 deletion(-) create mode 100644 test/unit/api/http-api-router.test.js create mode 100644 test/unit/mock/http-client-module-manager-mock.js create mode 100644 test/unit/mock/json-schema-service-mock.js diff --git a/.eslintrc.cjs b/.eslintrc.cjs index 32d9cc8d05..5c5e1b1db3 100644 --- a/.eslintrc.cjs +++ b/.eslintrc.cjs @@ -29,6 +29,7 @@ module.exports = { { files: ['*-mock.js', '*.test.js'], rules: { + 'no-empty-function': 'off', 'no-unused-vars': 'off', }, }, diff --git a/src/controllers/http-api/http-api-router.js b/src/controllers/http-api/http-api-router.js index 3643850f1f..cadf110dfd 100644 --- a/src/controllers/http-api/http-api-router.js +++ b/src/controllers/http-api/http-api-router.js @@ -3,7 +3,6 @@ import { HTTP_API_ROUTES } from '../../constants/constants.js'; class HttpApiRouter { constructor(ctx) { - this.config = ctx.config; this.httpClientModuleManager = ctx.httpClientModuleManager; this.apiRoutes = HTTP_API_ROUTES; @@ -19,6 +18,7 @@ class HttpApiRouter { const versionedController = `${stringUtil.toCamelCase( operation, )}HttpApiController${stringUtil.capitalize(version)}`; + this[versionedController] = ctx[versionedController]; } } diff --git a/test/unit/api/http-api-router.test.js b/test/unit/api/http-api-router.test.js new file mode 100644 index 0000000000..0c8e3af4d8 --- /dev/null +++ b/test/unit/api/http-api-router.test.js @@ -0,0 +1,80 @@ +import { beforeEach, describe, it } from 'mocha'; +import { expect } from 'chai'; +import sinon from 'sinon'; +import HttpApiRouter from '../../../src/controllers/http-api/http-api-router.js'; +import JsonSchemaServiceMock from '../mock/json-schema-service-mock.js'; +import HttpClientModuleManagerMock from '../mock/http-client-module-manager-mock.js'; +import { HTTP_API_ROUTES } from '../../../src/constants/constants.js'; + +describe('HTTP API Router test', async () => { + let httpApiRouter; + const controllerMocks = {}; + + beforeEach(() => { + // Mock Controllers + Object.keys(HTTP_API_ROUTES).forEach((version) => { + Object.keys(HTTP_API_ROUTES[version]).forEach((operation) => { + const versionedController = `${operation}HttpApiController${ + version.charAt(1).toUpperCase() + version.slice(2) + }`; + controllerMocks[versionedController] = { handleRequest: sinon.stub() }; + }); + }); + + // Mock context + const ctx = { + httpClientModuleManager: new HttpClientModuleManagerMock(), + jsonSchemaService: new JsonSchemaServiceMock(), + ...controllerMocks, + }; + + // Initialize HttpApiRouter with mocks + httpApiRouter = new HttpApiRouter(ctx); + }); + + it('Router has all defined routes', async () => { + // Extract unique HTTP methods present across all versions + const httpMethods = new Set(); + Object.values(HTTP_API_ROUTES).forEach((routes) => { + Object.values(routes).forEach((route) => { + httpMethods.add(route.method); + }); + }); + + // Create spies for each extracted HTTP method on each router instance and httpClientModuleManager + const spies = {}; + Object.keys(HTTP_API_ROUTES).forEach((version) => { + spies[version] = {}; + Array.from(httpMethods).forEach((method) => { + spies[version][method] = sinon.spy(httpApiRouter.routers[version], method); + }); + }); + const httpClientModuleManagerUseSpy = sinon.spy( + httpApiRouter.httpClientModuleManager, + 'use', + ); + + // Initialize the routes + await httpApiRouter.initialize(); + + // Validate each route + Object.entries(HTTP_API_ROUTES).forEach(([version, routes]) => { + expect(httpClientModuleManagerUseSpy.calledWith(`/${version}`)).to.equal(true); + + Object.values(routes).forEach((routeDetails) => { + const { method, path } = routeDetails; + expect(spies[version][method].calledWith(path)).to.equal(true); + }); + }); + expect(httpClientModuleManagerUseSpy.calledWith('/latest')).to.equal(true); + expect(httpClientModuleManagerUseSpy.calledWith('/')).to.equal(true); + + // Restore all spies + Object.values(spies).forEach((versionSpies) => { + Object.values(versionSpies).forEach((spy) => { + spy.restore(); + }); + }); + httpClientModuleManagerUseSpy.restore(); + }); +}); diff --git a/test/unit/mock/http-client-module-manager-mock.js b/test/unit/mock/http-client-module-manager-mock.js new file mode 100644 index 0000000000..7a98216032 --- /dev/null +++ b/test/unit/mock/http-client-module-manager-mock.js @@ -0,0 +1,25 @@ +import express from 'express'; + +class HttpClientModuleManagerMock { + createRouterInstance() { + return express.Router(); + } + + initializeBeforeMiddlewares() {} + + async listen() {} + + use(path, callback) {} + + get() {} + + post() {} + + selectMiddlewares(options) { + return []; + } + + initializeAfterMiddlewares() {} +} + +export default HttpClientModuleManagerMock; diff --git a/test/unit/mock/json-schema-service-mock.js b/test/unit/mock/json-schema-service-mock.js new file mode 100644 index 0000000000..45e16b0ff7 --- /dev/null +++ b/test/unit/mock/json-schema-service-mock.js @@ -0,0 +1,3 @@ +class JsonSchemaServiceMock {} + +export default JsonSchemaServiceMock; From 236252082f386dcc5c62f4faf0e4cbee3a7652ef Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Fri, 18 Aug 2023 13:04:44 +0100 Subject: [PATCH 15/18] Removed redundant function mocks from httpClientModuleManagerMock --- test/unit/mock/http-client-module-manager-mock.js | 4 ---- 1 file changed, 4 deletions(-) diff --git a/test/unit/mock/http-client-module-manager-mock.js b/test/unit/mock/http-client-module-manager-mock.js index 7a98216032..434fe0fe08 100644 --- a/test/unit/mock/http-client-module-manager-mock.js +++ b/test/unit/mock/http-client-module-manager-mock.js @@ -11,10 +11,6 @@ class HttpClientModuleManagerMock { use(path, callback) {} - get() {} - - post() {} - selectMiddlewares(options) { return []; } From b66114d80509050f94bf454692f5e0757ccfc4a8 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Fri, 18 Aug 2023 14:22:53 +0100 Subject: [PATCH 16/18] Added OpenAPI collection --- docs/openapi/DKGv6.yaml | 1369 +++++++++++++++++ .../postman}/DKGv6.postman_collection.json | 0 2 files changed, 1369 insertions(+) create mode 100644 docs/openapi/DKGv6.yaml rename {postman => docs/postman}/DKGv6.postman_collection.json (100%) diff --git a/docs/openapi/DKGv6.yaml b/docs/openapi/DKGv6.yaml new file mode 100644 index 0000000000..5964ab8356 --- /dev/null +++ b/docs/openapi/DKGv6.yaml @@ -0,0 +1,1369 @@ +openapi: 3.0.3 +info: + title: DKGv6 + description: DKG v6 API Collection. + version: 1.0.0 + contact: {} +servers: + - url: localhost +paths: + /info: + get: + tags: + - old + summary: Node Info + description: Get the node information. + operationId: nodeInfo + responses: + '200': + description: Node Info + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '20' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 12:43:07 GMT + ETag: + schema: + type: string + example: W/"14-Rq/28W5aGKCGXmXfM1+eW1LAbb4" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + version: + type: string + example: 6.0.13 + examples: + Node Info: + value: + version: 6.0.13 + /bid-suggestion: + get: + tags: + - old + summary: Get Bid Suggestion + description: Get bid suggestion based on provided parameters. + operationId: getBidSuggestion + parameters: + - name: blockchain + in: query + schema: + type: string + example: hardhat + - name: epochsNumber + in: query + schema: + type: string + example: '5' + - name: assertionSize + in: query + schema: + type: string + example: '299' + - name: contentAssetStorageAddress + in: query + schema: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + - name: firstAssertionId + in: query + schema: + type: string + example: '0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf' + - name: hashFunctionId + in: query + schema: + type: string + example: '1' + requestBody: + content: + text/plain: + example: '' + responses: + '200': + description: Get Bid Suggestion + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '38' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 12:42:31 GMT + ETag: + schema: + type: string + example: W/"26-UrjseieOcIBnowM9obJae/FG7xc" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + bidSuggestion: + type: string + example: '903051579928002449' + examples: + Get Bid Suggestion: + value: + bidSuggestion: '903051579928002449' + /local-store: + post: + tags: + - old + summary: Local Store + description: Store locally. + operationId: localStore + requestBody: + content: + application/json: + schema: + type: array + items: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: + type: string + example: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: + type: string + example: TRIPLE + tokenId: + type: number + example: 0 + example: + - assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + - assertion: + - '11000' . + - 'Belgrade' . + - 'Smith' . + - 'Adam' . + assertionId: >- + 0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + example: + - assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + - assertion: + - '11000' . + - 'Belgrade' . + - 'Smith' . + - 'Adam' . + assertionId: >- + 0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + responses: + '202': + description: Local Store + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 12:49:45 GMT + ETag: + schema: + type: string + example: W/"36-uF3l7SNXwSBVObRCAJxOmp8OJGc" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 7d499975-ce42-4d84-9092-0ac2a62f5151 + examples: + Local Store: + value: + operationId: 7d499975-ce42-4d84-9092-0ac2a62f5151 + /publish: + post: + tags: + - old + summary: Publish Knowledge Asset + description: Publish assertion. + operationId: publishKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: + type: string + example: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: + type: number + example: 1 + tokenId: + type: number + example: 0 + example: + assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: 1 + tokenId: 0 + responses: + '202': + description: Publish Knowledge Asset + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:07:57 GMT + ETag: + schema: + type: string + example: W/"36-SQS1f7vf+HLSUHZ6wvE9UUwksSY" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '22' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 8270c131-91b8-4573-a69e-504ff388a8b6 + examples: + Publish Knowledge Asset: + value: + operationId: 8270c131-91b8-4573-a69e-504ff388a8b6 + /get: + post: + tags: + - old + summary: Get Knowledge Asset + description: Get an assertion. + operationId: getKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + hashFunctionId: + type: number + example: 1 + id: + type: string + example: did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0 + state: + type: string + example: LATEST + example: + hashFunctionId: 1 + id: did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0 + state: LATEST + responses: + '202': + description: Get Knowledge Asset + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:16:39 GMT + ETag: + schema: + type: string + example: W/"36-tXDgcL88Mx02VotKK9H3zPuWwf8" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '12' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 3a6df062-b3ce-4cac-aefa-77b1e8b9a4db + examples: + Get Knowledge Asset: + value: + operationId: 3a6df062-b3ce-4cac-aefa-77b1e8b9a4db + /update: + post: + tags: + - old + summary: Update Knowledge Asset + description: Update assertion. + operationId: updateKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'TL' . + - . + - >- + _:c14n0 + + '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' + . + assertionId: + type: string + example: >- + 0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0 + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: + type: number + example: 1 + tokenId: + type: number + example: 0 + example: + assertion: + - . + - 'TL' . + - . + - >- + _:c14n0 + + '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' + . + assertionId: >- + 0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: 1 + tokenId: 0 + responses: + '202': + description: Update Knowledge Asset + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:17:54 GMT + ETag: + schema: + type: string + example: W/"36-CjvPRlFINYIIcvR2H5gFBcOkNH8" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '57' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 0d4c3efc-0f0b-435d-b9a3-402748dbbb2f + examples: + Update Knowledge Asset: + value: + operationId: 0d4c3efc-0f0b-435d-b9a3-402748dbbb2f + /query: + post: + tags: + - old + summary: Query DKG + description: Execute a query. + operationId: queryDkg + requestBody: + content: + application/json: + schema: + type: object + properties: + query: + type: string + example: >- + CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH + + { ?s ?p ?o . }}} + repository: + type: string + example: privateCurrent + type: + type: string + example: CONSTRUCT + example: + query: >- + CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH + + { ?s ?p ?o . }}} + repository: privateCurrent + type: CONSTRUCT + responses: + '202': + description: Query DKG + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:20:16 GMT + ETag: + schema: + type: string + example: W/"36-WRBDN6AcKKCbVi3DGfI6FvESm5w" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 746992ba-e607-4858-8deb-5cffc2541859 + examples: + Query DKG: + value: + operationId: 746992ba-e607-4858-8deb-5cffc2541859 + /{operation}/{operationId}: + get: + tags: + - v0 + summary: '[v0] Get Operation Result' + description: Get result of a specific operation by its ID. + operationId: v0GetOperationResult + responses: + '200': + description: '' + parameters: + - name: operation + in: path + required: true + schema: + type: string + - name: operationId + in: path + required: true + schema: + type: string + /v0/info: + get: + tags: + - v0 + summary: '[v0] Node Info' + description: Get the node information. + operationId: v0NodeInfo + responses: + '200': + description: '[v0] Node Info' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '20' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:27:58 GMT + ETag: + schema: + type: string + example: W/"14-Rq/28W5aGKCGXmXfM1+eW1LAbb4" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + version: + type: string + example: 6.0.13 + examples: + '[v0] Node Info': + value: + version: 6.0.13 + /v0/bid-suggestion: + get: + tags: + - v0 + summary: '[v0] Get Bid Suggestion' + description: Get bid suggestion based on provided parameters. + operationId: v0GetBidSuggestion + parameters: + - name: blockchain + in: query + schema: + type: string + example: hardhat + - name: epochsNumber + in: query + schema: + type: string + example: '5' + - name: assertionSize + in: query + schema: + type: string + example: '299' + - name: contentAssetStorageAddress + in: query + schema: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + - name: firstAssertionId + in: query + schema: + type: string + example: '0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf' + - name: hashFunctionId + in: query + schema: + type: string + example: '1' + requestBody: + content: + text/plain: + example: '' + responses: + '200': + description: '[v0] Get Bid Suggestion' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '39' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:59:02 GMT + ETag: + schema: + type: string + example: W/"27-ieFm/6t4DZwm0kFCMq71s37uy/g" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + bidSuggestion: + type: string + example: '1122511549276000025' + examples: + '[v0] Get Bid Suggestion': + value: + bidSuggestion: '1122511549276000025' + /v0/local-store: + post: + tags: + - v0 + summary: '[v0] Local Store' + description: Store locally. + operationId: v0LocalStore + requestBody: + content: + application/json: + schema: + type: array + items: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: + type: string + example: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: + type: string + example: TRIPLE + tokenId: + type: number + example: 0 + example: + - assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + - assertion: + - '11000' . + - 'Belgrade' . + - 'Smith' . + - 'Adam' . + assertionId: >- + 0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + example: + - assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + - assertion: + - '11000' . + - 'Belgrade' . + - 'Smith' . + - 'Adam' . + assertionId: >- + 0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + storeType: TRIPLE + tokenId: 0 + responses: + '202': + description: '[v0] Local Store' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:59:11 GMT + ETag: + schema: + type: string + example: W/"36-fpQtTlhbbWO7tqbMGm3CkKmOqaI" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 0a4ee669-95bb-41cd-a2e8-3382361e80d9 + examples: + '[v0] Local Store': + value: + operationId: 0a4ee669-95bb-41cd-a2e8-3382361e80d9 + /v0/publish: + post: + tags: + - v0 + summary: '[v0] Publish Knowledge Asset' + description: Publish assertion. + operationId: v0PublishKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: + type: string + example: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: + type: number + example: 1 + tokenId: + type: number + example: 0 + example: + assertion: + - . + - 'OT' . + - . + - >- + _:c14n0 + + '0xcfab2d364fe01757d7a83d3b32284395d87b1c379adabb1e28a16666e0a4fca9' + . + assertionId: >- + 0xe3a6733d7b999ca6f0d141afe3e38ac59223a4dfde7a5458932d2094ed4193cf + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: 1 + tokenId: 0 + responses: + '202': + description: '[v0] Publish Knowledge Asset' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 13:59:54 GMT + ETag: + schema: + type: string + example: W/"36-wKIhHpa0/tdVYh1Y8D2yINolruA" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '52' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 476fb996-db1a-47b8-8da4-80d71411feb3 + examples: + '[v0] Publish Knowledge Asset': + value: + operationId: 476fb996-db1a-47b8-8da4-80d71411feb3 + /v0/get: + post: + tags: + - v0 + summary: '[v0] Get Knowledge Asset' + description: Get an assertion. + operationId: v0GetKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + hashFunctionId: + type: number + example: 1 + id: + type: string + example: did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0 + state: + type: string + example: LATEST + example: + hashFunctionId: 1 + id: did:dkg:hardhat/0xb0d4afd8879ed9f52b28595d31b441d079b2ca07/0 + state: LATEST + responses: + '202': + description: '[v0] Get Knowledge Asset' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 14:00:02 GMT + ETag: + schema: + type: string + example: W/"36-/27PH/ZH74wwVBrYDxWSzCk4yA0" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '44' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 5b34c048-2d08-4696-b3c4-c37c831b89ce + examples: + '[v0] Get Knowledge Asset': + value: + operationId: 5b34c048-2d08-4696-b3c4-c37c831b89ce + /v0/update: + post: + tags: + - v0 + summary: '[v0] Update Knowledge Asset' + description: Update assertion. + operationId: v0UpdateKnowledgeAsset + requestBody: + content: + application/json: + schema: + type: object + properties: + assertion: + type: array + items: + type: string + example: . + example: + - . + - 'TL' . + - . + - >- + _:c14n0 + + '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' + . + assertionId: + type: string + example: >- + 0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0 + blockchain: + type: string + example: hardhat + contract: + type: string + example: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: + type: number + example: 1 + tokenId: + type: number + example: 0 + example: + assertion: + - . + - 'TL' . + - . + - >- + _:c14n0 + + '0xa3acb6d57097f316b973e9e33d303cf411b8d62d7d589576e348d0d7049e3b63' + . + assertionId: >- + 0xef0adc464c3dcb1d353567db5972de8d47f44d6621326645324f9730f2c83cf0 + blockchain: hardhat + contract: '0xB0D4afd8879eD9F52b28595d31B441D079B2Ca07' + hashFunctionId: 1 + tokenId: 0 + responses: + '202': + description: '[v0] Update Knowledge Asset' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 14:00:09 GMT + ETag: + schema: + type: string + example: W/"36-77qAdgCc/SEN47aETAww86PM04w" + Keep-Alive: + schema: + type: string + example: timeout=5 + RateLimit-Limit: + schema: + type: string + example: '10' + RateLimit-Remaining: + schema: + type: string + example: '9' + RateLimit-Reset: + schema: + type: string + example: '38' + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: f0d34032-6910-49b4-a2a8-71c9f58feb58 + examples: + '[v0] Update Knowledge Asset': + value: + operationId: f0d34032-6910-49b4-a2a8-71c9f58feb58 + /v0/query: + post: + tags: + - v0 + summary: '[v0] Query DKG' + description: Execute a query. + operationId: v0QueryDkg + requestBody: + content: + application/json: + schema: + type: object + properties: + query: + type: string + example: >- + CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH + + { ?s ?p ?o . }}} + repository: + type: string + example: privateCurrent + type: + type: string + example: CONSTRUCT + example: + query: >- + CONSTRUCT { ?s ?p ?o } WHERE {{GRAPH + + { ?s ?p ?o . }}} + repository: privateCurrent + type: CONSTRUCT + responses: + '202': + description: '[v0] Query DKG' + headers: + Access-Control-Allow-Origin: + schema: + type: string + example: '*' + Connection: + schema: + type: string + example: keep-alive + Content-Length: + schema: + type: string + example: '54' + Date: + schema: + type: string + example: Thu, 17 Aug 2023 14:00:19 GMT + ETag: + schema: + type: string + example: W/"36-kqaRe64EoJygoEadXJWRekiCs4s" + Keep-Alive: + schema: + type: string + example: timeout=5 + X-Powered-By: + schema: + type: string + example: Express + content: + application/json: + schema: + type: object + properties: + operationId: + type: string + example: 4d371ffb-a620-452f-8d16-3e427bafeae2 + examples: + '[v0] Query DKG': + value: + operationId: 4d371ffb-a620-452f-8d16-3e427bafeae2 +tags: + - name: old + - name: v0 diff --git a/postman/DKGv6.postman_collection.json b/docs/postman/DKGv6.postman_collection.json similarity index 100% rename from postman/DKGv6.postman_collection.json rename to docs/postman/DKGv6.postman_collection.json From 070a529591f27b79727d8247638d8bddd4970b0b Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 24 Aug 2023 12:21:57 +0100 Subject: [PATCH 17/18] Removed test v1/info route, bumped version to 6.0.14 --- package-lock.json | 4 +-- package.json | 2 +- src/controllers/http-api/v1/.gitkeep | 0 .../v1/info-http-api-controller-v1.js | 33 ------------------- .../http-api/v1/request-schema/.gitkeep | 0 5 files changed, 3 insertions(+), 36 deletions(-) create mode 100644 src/controllers/http-api/v1/.gitkeep delete mode 100644 src/controllers/http-api/v1/info-http-api-controller-v1.js create mode 100644 src/controllers/http-api/v1/request-schema/.gitkeep diff --git a/package-lock.json b/package-lock.json index 175adb0e38..cf09c0f316 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,12 +1,12 @@ { "name": "origintrail_node", - "version": "6.0.12", + "version": "6.0.14", "lockfileVersion": 2, "requires": true, "packages": { "": { "name": "origintrail_node", - "version": "6.0.12", + "version": "6.0.14", "license": "ISC", "dependencies": { "@comunica/query-sparql": "^2.4.3", diff --git a/package.json b/package.json index 5ce51dfe14..c10bb71d29 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "origintrail_node", - "version": "6.0.13", + "version": "6.0.14", "description": "OTNode V6", "main": "index.js", "type": "module", diff --git a/src/controllers/http-api/v1/.gitkeep b/src/controllers/http-api/v1/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 diff --git a/src/controllers/http-api/v1/info-http-api-controller-v1.js b/src/controllers/http-api/v1/info-http-api-controller-v1.js deleted file mode 100644 index 09cb3ceb00..0000000000 --- a/src/controllers/http-api/v1/info-http-api-controller-v1.js +++ /dev/null @@ -1,33 +0,0 @@ -import { createRequire } from 'module'; -import BaseController from '../base-http-api-controller.js'; - -const require = createRequire(import.meta.url); -const { version } = require('../../../../package.json'); - -class InfoControllerV1 extends BaseController { - constructor(ctx) { - super(ctx); - - this.blockchainModuleManager = ctx.blockchainModuleManager; - } - - handleRequest(_, res) { - this.returnResponse(res, 200, { - version, - ...this.filterConfig(), - }); - } - - filterConfig() { - const nodeConfigData = { - tripleStores: Object.entries(this.config.modules.tripleStore.implementation) - .filter(([, value]) => value.enabled) - .map(([key]) => key), - blockchains: this.blockchainModuleManager.getImplementationNames(), - }; - - return nodeConfigData; - } -} - -export default InfoControllerV1; diff --git a/src/controllers/http-api/v1/request-schema/.gitkeep b/src/controllers/http-api/v1/request-schema/.gitkeep new file mode 100644 index 0000000000..e69de29bb2 From ed1c5e97a294f52edc3b60a015ac16ae1730d880 Mon Sep 17 00:00:00 2001 From: Uladzislau Hubar Date: Thu, 24 Aug 2023 12:37:03 +0100 Subject: [PATCH 18/18] Removed v1/info route from the API config --- src/constants/constants.js | 8 +------- 1 file changed, 1 insertion(+), 7 deletions(-) diff --git a/src/constants/constants.js b/src/constants/constants.js index 3e394b8d18..6b92211067 100644 --- a/src/constants/constants.js +++ b/src/constants/constants.js @@ -461,13 +461,7 @@ export const HTTP_API_ROUTES = { options: {}, }, }, - v1: { - info: { - method: 'get', - path: '/info', - options: {}, - }, - }, + v1: {}, }; /**