Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(rest)!: update AFJ to 0.4.0 #222

Closed
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
16 changes: 14 additions & 2 deletions packages/rest/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -30,8 +30,18 @@
"test": "jest"
},
"dependencies": {
"@aries-framework/core": "^0.2.3",
"@aries-framework/node": "^0.2.3",
"@aries-framework/anoncreds": "^0.4.0",
"@aries-framework/anoncreds-rs": "^0.4.0",
"@aries-framework/askar": "^0.4.0",
"@aries-framework/core": "^0.4.0",
"@aries-framework/indy-vdr": "^0.4.0",
"@aries-framework/node": "^0.4.0",
"@hyperledger/anoncreds-nodejs": "^0.1.0",
"@hyperledger/anoncreds-shared": "^0.1.0",
"@hyperledger/aries-askar-nodejs": "^0.1.0",
"@hyperledger/aries-askar-shared": "^0.1.0",
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shared is being reexported by the nodejs and react-native, these can be omitted from the dependencies.

"@hyperledger/indy-vdr-nodejs": "^0.1.0",
"@hyperledger/indy-vdr-shared": "^0.1.0",
"@types/ws": "^7.4.7",
"body-parser": "^1.20.0",
"cors": "^2.8.5",
Expand All @@ -51,6 +61,8 @@
"@types/express": "^4.17.13",
"@types/multer": "^1.4.7",
"@types/node": "^16.7.10",
"@types/node-fetch": "^2.6.4",
"@types/ref-struct-di": "^1.1.9",
"@types/supertest": "^2.0.12",
"@types/swagger-ui-express": "^4.1.3",
"@types/uuid": "^8.3.4",
Expand Down
1 change: 0 additions & 1 deletion packages/rest/samples/sample.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ const run = async () => {

const agent = await setupAgent({
port: 3001,
publicDidSeed: 'testtesttesttesttesttesttesttest',
endpoints: [endpoint],
name: 'Aries Test Agent',
})
Expand Down
4 changes: 1 addition & 3 deletions packages/rest/samples/sampleWithApp.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import type { ServerConfig } from '../src/utils/ServerConfig'

import { AgentConfig } from '@aries-framework/core'
import bodyParser from 'body-parser'
import express from 'express'
import { connect } from 'ngrok'
Expand All @@ -13,7 +12,6 @@ const run = async () => {

const agent = await setupAgent({
port: 3001,
publicDidSeed: 'testtesttesttesttesttesttesttest',
endpoints: [endpoint],
name: 'Aries Test Agent',
})
Expand All @@ -22,7 +20,7 @@ const run = async () => {
const jsonParser = bodyParser.json()

app.post('/greeting', jsonParser, (req, res) => {
const config = agent.injectionContainer.resolve(AgentConfig)
const config = agent.config

res.send(`Hello, ${config.label}!`)
})
Expand Down
18 changes: 12 additions & 6 deletions packages/rest/src/cli.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,20 +24,21 @@ const parsed = yargs
default: [],
coerce: (items: unknown[]) => items.map((i) => (typeof i === 'string' ? JSON.parse(i) : i)),
})
.option('public-did-seed', {
string: true,
})
.option('endpoint', {
array: true,
})
.option('log-level', {
number: true,
default: 3,
})
.option('use-legacy-did-sov-prefix', {
.option('use-did-sov-prefix-where-allowed', {
boolean: true,
default: false,
})
.option('use-did-key-in-protocols', {
boolean: true,
default: true,
})
.option('outbound-transport', {
default: [],
choices: ['http', 'ws'],
Expand Down Expand Up @@ -88,6 +89,10 @@ const parsed = yargs
choices: ['always', 'never', 'contentApproved'],
default: 'never',
})
.option('auto-update-storage-on-startup', {
boolean: true,
default: true,
})
.option('connection-image-url', {
string: true,
})
Expand All @@ -110,13 +115,14 @@ export async function runCliServer() {
key: parsed['wallet-key'],
},
indyLedgers: parsed['indy-ledger'],
publicDidSeed: parsed['public-did-seed'],
endpoints: parsed.endpoint,
autoAcceptConnections: parsed['auto-accept-connections'],
autoAcceptCredentials: parsed['auto-accept-credentials'],
autoAcceptProofs: parsed['auto-accept-proofs'],
autoUpdateStorageOnStartup: parsed['auto-update-storage-on-startup'],
autoAcceptMediationRequests: parsed['auto-accept-mediation-requests'],
useLegacyDidSovPrefix: parsed['use-legacy-did-sov-prefix'],
useDidKeyInProtocols: parsed['use-did-key-in-protocols'],
useDidSovPrefixWhereAllowed: parsed['use-legacy-did-sov-prefix'],
logLevel: parsed['log-level'],
inboundTransports: parsed['inbound-transport'],
outboundTransports: parsed['outbound-transport'],
Expand Down
52 changes: 43 additions & 9 deletions packages/rest/src/cliAgent.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,19 @@
import type { IndyPoolConfig, InitConfig, AutoAcceptCredential, AutoAcceptProof } from '@aries-framework/core'
import type { WalletConfig } from '@aries-framework/core/build/types'

import { HttpOutboundTransport, WsOutboundTransport, LogLevel, Agent } from '@aries-framework/core'
import type { InitConfig, WalletConfig } from '@aries-framework/core'
import type { IndyVdrPoolConfig } from '@aries-framework/indy-vdr'

import {
HttpOutboundTransport,
WsOutboundTransport,
LogLevel,
Agent,
AutoAcceptCredential,
AutoAcceptProof,
} from '@aries-framework/core'
import { agentDependencies, HttpInboundTransport, WsInboundTransport } from '@aries-framework/node'
import { readFile } from 'fs/promises'

import { setupServer } from './server'
import { getAgentModules } from './utils/agent'
import { TsLogger } from './utils/logger'

export type Transports = 'ws' | 'http'
Expand All @@ -27,13 +35,14 @@ const outboundTransportMapping = {
export interface AriesRestConfig {
label: string
walletConfig: WalletConfig
indyLedgers?: IndyPoolConfig[]
publicDidSeed?: string
indyLedgers: IndyVdrPoolConfig[]
endpoints?: string[]
autoAcceptConnections?: boolean
autoAcceptCredentials?: AutoAcceptCredential
autoAcceptProofs?: AutoAcceptProof
useLegacyDidSovPrefix?: boolean
autoUpdateStorageOnStartup?: boolean
useDidKeyInProtocols?: boolean
useDidSovPrefixWhereAllowed?: boolean
logLevel?: LogLevel
inboundTransports?: InboundTransport[]
outboundTransports?: Transports[]
Expand All @@ -52,7 +61,19 @@ export async function readRestConfig(path: string) {
}

export async function runRestAgent(restConfig: AriesRestConfig) {
const { logLevel, inboundTransports = [], outboundTransports = [], webhookUrl, adminPort, ...afjConfig } = restConfig
const {
logLevel,
inboundTransports = [],
outboundTransports = [],
webhookUrl,
adminPort,
indyLedgers,
autoAcceptConnections = true,
autoAcceptCredentials = AutoAcceptCredential.ContentApproved,
autoAcceptMediationRequests = true,
autoAcceptProofs = AutoAcceptProof.ContentApproved,
...afjConfig
} = restConfig

const logger = new TsLogger(logLevel ?? LogLevel.error)

Expand All @@ -61,7 +82,20 @@ export async function runRestAgent(restConfig: AriesRestConfig) {
logger,
}

const agent = new Agent(agentConfig, agentDependencies)
const maybeLedgers = indyLedgers.length > 0 ? (indyLedgers as [IndyVdrPoolConfig, ...IndyVdrPoolConfig[]]) : undefined
const modules = getAgentModules({
autoAcceptConnections,
autoAcceptProofs,
autoAcceptCredentials,
autoAcceptMediationRequests,
indyLedgers: maybeLedgers,
})

const agent = new Agent({
config: agentConfig,
dependencies: agentDependencies,
modules,
})

// Register outbound transports
for (const outboundTransport of outboundTransports) {
Expand Down
1 change: 0 additions & 1 deletion packages/rest/src/controllers/agent/AgentController.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,6 @@ export class AgentController extends Controller {
label: this.agent.config.label,
endpoints: this.agent.config.endpoints,
isInitialized: this.agent.isInitialized,
publicDid: this.agent.publicDid,
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ export class ConnectionController extends Controller {
} else {
const connectionRepository = this.agent.dependencyManager.resolve(ConnectionRepository)

const connections = await connectionRepository.findByQuery({
const connections = await connectionRepository.findByQuery(this.agent.context, {
alias,
myDid,
theirDid,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import type { RestAgent } from '../../utils/agent'
import type { CredentialExchangeRecordProps } from '@aries-framework/core'

import { CredentialRepository, CredentialState, Agent, RecordNotFoundError } from '@aries-framework/core'
Expand All @@ -18,7 +19,7 @@ import {
@Route('/credentials')
@injectable()
export class CredentialController extends Controller {
private agent: Agent
private agent: RestAgent

public constructor(agent: Agent) {
super()
Expand All @@ -39,7 +40,7 @@ export class CredentialController extends Controller {
) {
const credentialRepository = this.agent.dependencyManager.resolve(CredentialRepository)

const credentials = await credentialRepository.findByQuery({
const credentials = await credentialRepository.findByQuery(this.agent.context, {
connectionId,
threadId,
state,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,10 +1,8 @@
import type { SchemaId } from '../examples'
import type { CredDef } from 'indy-sdk'
import type { RestAgent } from '../../utils/agent'
import type { Did, SchemaId } from '../examples'
import type { AnonCredsCredentialDefinitionResponse } from '../types'

import { Agent, IndySdkError } from '@aries-framework/core'
import { LedgerError } from '@aries-framework/core/build/modules/ledger/error/LedgerError'
import { LedgerNotFoundError } from '@aries-framework/core/build/modules/ledger/error/LedgerNotFoundError'
import { isIndyError } from '@aries-framework/core/build/utils/indyError'
import { Agent } from '@aries-framework/core'
import { Body, Controller, Example, Get, Path, Post, Res, Route, Tags, TsoaResponse } from 'tsoa'
import { injectable } from 'tsyringe'

Expand All @@ -14,7 +12,7 @@ import { CredentialDefinitionExample, CredentialDefinitionId } from '../examples
@Route('/credential-definitions')
@injectable()
export class CredentialDefinitionController extends Controller {
private agent: Agent
private agent: RestAgent

public constructor(agent: Agent) {
super()
Expand All @@ -25,68 +23,92 @@ export class CredentialDefinitionController extends Controller {
* Retrieve credential definition by credential definition id
*
* @param credentialDefinitionId
* @returns CredDef
* @returns AnonCredsCredentialDefinitionResponse
*/
@Example<CredDef>(CredentialDefinitionExample)
@Example<AnonCredsCredentialDefinitionResponse>(CredentialDefinitionExample)
@Get('/:credentialDefinitionId')
public async getCredentialDefinitionById(
@Path('credentialDefinitionId') credentialDefinitionId: CredentialDefinitionId,
@Res() badRequestError: TsoaResponse<400, { reason: string }>,
@Res() notFoundError: TsoaResponse<404, { reason: string }>,
@Res() internalServerError: TsoaResponse<500, { message: string }>
) {
try {
return await this.agent.ledger.getCredentialDefinition(credentialDefinitionId)
} catch (error) {
if (error instanceof IndySdkError && error.message === 'IndyError(LedgerNotFound): LedgerNotFound') {
return notFoundError(404, {
reason: `credential definition with credentialDefinitionId "${credentialDefinitionId}" not found.`,
})
} else if (error instanceof LedgerError && error.cause instanceof IndySdkError) {
if (isIndyError(error.cause.cause, 'CommonInvalidStructure')) {
return badRequestError(400, {
reason: `credentialDefinitionId "${credentialDefinitionId}" has invalid structure.`,
})
}
}
): Promise<AnonCredsCredentialDefinitionResponse> {
const {
credentialDefinition,
resolutionMetadata: { error },
} = await this.agent.modules.anoncreds.getCredentialDefinition(credentialDefinitionId)

if (error === 'notFound') {
return notFoundError(404, {
reason: `credential definition with credentialDefinitionId "${credentialDefinitionId}" not found.`,
})
}

if (error === 'invalid' || error === 'unsupportedAnonCredsMethod') {
return badRequestError(400, {
reason: `credentialDefinitionId "${credentialDefinitionId}" has invalid structure.`,
})
}

if (error !== undefined || credentialDefinition === undefined) {
return internalServerError(500, { message: `something went wrong: ${error}` })
}

return {
id: credentialDefinitionId,
...credentialDefinition,
}
}

/**
* Creates a new credential definition.
*
* @param credentialDefinitionRequest
* @returns CredDef
* @returns AnonCredsCredentialDefinitionResponse
*/
@Example<CredDef>(CredentialDefinitionExample)
@Example<AnonCredsCredentialDefinitionResponse & { id: string }>(CredentialDefinitionExample)
@Post('/')
public async createCredentialDefinition(
@Body()
credentialDefinitionRequest: {
issuerId: Did
schemaId: SchemaId
supportRevocation: boolean
tag: string
},
@Res() notFoundError: TsoaResponse<404, { reason: string }>,
@Res() internalServerError: TsoaResponse<500, { message: string }>
) {
try {
const schema = await this.agent.ledger.getSchema(credentialDefinitionRequest.schemaId)
): Promise<AnonCredsCredentialDefinitionResponse> {
const {
resolutionMetadata: { error },
} = await this.agent.modules.anoncreds.getSchema(credentialDefinitionRequest.schemaId)

return await this.agent.ledger.registerCredentialDefinition({
schema,
supportRevocation: credentialDefinitionRequest.supportRevocation,
tag: credentialDefinitionRequest.tag,
if (error === 'notFound' || error === 'invalid' || error === 'unsupportedAnonCredsMethod') {
return notFoundError(404, {
reason: `schema with schemaId "${credentialDefinitionRequest.schemaId}" not found.`,
})
} catch (error) {
if (error instanceof LedgerNotFoundError) {
return notFoundError(404, {
reason: `schema with schemaId "${credentialDefinitionRequest.schemaId}" not found.`,
})
}

}
if (error) {
return internalServerError(500, { message: `something went wrong: ${error}` })
}

const {
credentialDefinitionState: { state, credentialDefinitionId, credentialDefinition },
} = await this.agent.modules.anoncreds.registerCredentialDefinition({
credentialDefinition: {
issuerId: credentialDefinitionRequest.issuerId,
schemaId: credentialDefinitionRequest.schemaId,
tag: credentialDefinitionRequest.tag,
},
options: {},
})

if (state !== 'finished' || credentialDefinitionId === undefined || credentialDefinition === undefined) {
return internalServerError(500, { message: `something went wrong` })
}

return {
id: credentialDefinitionId,
...credentialDefinition,
}
}
}
Loading