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

Add credential presentation from held credential to verifier #166

Merged
merged 11 commits into from
Dec 7, 2023
6 changes: 5 additions & 1 deletion .github/workflows/main.yml
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,10 @@ jobs:
- name: Build
run: npm run build
- name: Start dependencies
run: docker compose up deps
run: docker compose up deps --pull always
- name: Run integration test
run: npm run test:integration
- name: Print logs
run: docker compose logs
if: always()

28 changes: 12 additions & 16 deletions examples/integration-scripts/credentials.test.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
import { strict as assert } from 'assert';
import signify from 'signify-ts';

const url = 'http://127.0.0.1:3901';
const boot_url = 'http://127.0.0.1:3903';
const WAN_WITNESS_AID = 'BBilc4-L3tFUnfM_wJr4S4OJanAv_VmF_dJNN6vkf2Ha';
const WIL_WITNESS_AID = 'BLskRTInXnMxWaGqcpSyMgo0nYbalW99cGZESrz3zapM';
const WES_WITNESS_AID = 'BIKKuvBwpmDVA4Ds-EpL5bt9OqPzWPja2LigFYZN2YfX';
const WITNESS_HOST = 'witness-demo';
import { resolveEnvironment } from './utils/resolve-env';
const { url, bootUrl, vleiServerUrl, witnessIds, witnessUrls } =
resolveEnvironment();

const boot_url = bootUrl;
const WAN_WITNESS_AID = witnessIds[0];
const WIL_WITNESS_AID = witnessIds[1];
const WES_WITNESS_AID = witnessIds[2];
const WITNESS_OOBIS = [
`http://${WITNESS_HOST}:5642/oobi/${WAN_WITNESS_AID}/controller?name=Wan&tag=witness`,
`http://${WITNESS_HOST}:5643/oobi/${WIL_WITNESS_AID}/controller?name=Wil&tag=witness`,
`http://${WITNESS_HOST}:5644/oobi/${WES_WITNESS_AID}/controller?name=Wes&tag=witness`,
`${witnessUrls[0]}/oobi/${WAN_WITNESS_AID}/controller?name=Wan&tag=witness`,
`${witnessUrls[1]}/oobi/${WIL_WITNESS_AID}/controller?name=Wil&tag=witness`,
`${witnessUrls[2]}/oobi/${WES_WITNESS_AID}/controller?name=Wes&tag=witness`,
];

const KLI_WITNESS_DEMO_PREFIXES = [
Expand All @@ -21,7 +22,7 @@

// Credential Schema discovery through credential schema OOBI resolution
const qviSchemaSAID = 'EBfdlu8R27Fbx-ehrqwImnK-8Cm79sqbAQ4MmvEAYqao';
const vLEIServerHostUrl = 'http://vlei-server:7723/oobi';
const vLEIServerHostUrl = `${vleiServerUrl}/oobi`;
const schemaOobiUrl = `${vLEIServerHostUrl}/${qviSchemaSAID}`;

// Boots an agent and connects to it, returning the connected SignifyClient
Expand Down Expand Up @@ -56,7 +57,7 @@
route: string
): Promise<Notification[]> {
const awaitedNotifications = [];
while (true) {

Check warning on line 60 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

Unexpected constant condition

Check warning on line 60 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

Unexpected constant condition
const notifications = await client.notifications().list();
for (const note of notifications.notes) {
if (note.a.r === route) {
Expand All @@ -70,7 +71,7 @@
return awaitedNotifications;
}

async function resolveWitnesses(client: signify.SignifyClient) {

Check warning on line 74 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

'resolveWitnesses' is defined but never used

Check warning on line 74 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

'resolveWitnesses' is defined but never used
await Promise.all(
WITNESS_OOBIS.map((oobi) => client.oobis().resolve(oobi))
);
Expand All @@ -82,11 +83,6 @@
const issuerClient = await bootAndConnect(signify.randomPasscode());
const holderClient = await bootAndConnect(signify.randomPasscode());
const verifierClient = await bootAndConnect(signify.randomPasscode());
await Promise.all([
resolveWitnesses(issuerClient),
resolveWitnesses(holderClient),
resolveWitnesses(verifierClient),
]);

const state1 = await issuerClient.state();
const state2 = await holderClient.state();
Expand Down Expand Up @@ -349,7 +345,7 @@
await new Promise((resolve) => setTimeout(resolve, 250));
holderCreds = await holderClient.credentials().list();
}
const hldVleiAcdc: any = holderCreds[0];

Check warning on line 348 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

Unexpected any. Specify a different type

Check warning on line 348 in examples/integration-scripts/credentials.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

Unexpected any. Specify a different type
assert.equal(holderCreds.length, 1);
assert.equal(hldVleiAcdc.sad.s, schemaSAID);
assert.equal(hldVleiAcdc.sad.i, issuerAID);
Expand Down
12 changes: 2 additions & 10 deletions examples/integration-scripts/multisig.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,13 @@
} from 'signify-ts';
import { resolveEnvironment } from './utils/resolve-env';

const { url, bootUrl, witnessUrls, vleiServerUrl } = resolveEnvironment();
const { url, bootUrl, vleiServerUrl } = resolveEnvironment();
const WITNESS_AIDS = [
'BBilc4-L3tFUnfM_wJr4S4OJanAv_VmF_dJNN6vkf2Ha',
'BLskRTInXnMxWaGqcpSyMgo0nYbalW99cGZESrz3zapM',
'BIKKuvBwpmDVA4Ds-EpL5bt9OqPzWPja2LigFYZN2YfX',
];

const WITNESS_OOBIS = witnessUrls.map((url) => `${url}/oobi`);
const SCHEMA_SAID = 'EBfdlu8R27Fbx-ehrqwImnK-8Cm79sqbAQ4MmvEAYqao';
const SCHEMA_OOBI = `${vleiServerUrl}/oobi/${SCHEMA_SAID}`;

Expand All @@ -28,7 +27,7 @@
]);

// Create four identifiers, one for each client
let [aid1, aid2, aid3, aid4] = await Promise.all([

Check warning on line 30 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

'aid4' is never reassigned. Use 'const' instead

Check warning on line 30 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

'aid4' is never reassigned. Use 'const' instead
createAID(client1, 'member1', WITNESS_AIDS),
createAID(client2, 'member2', WITNESS_AIDS),
createAID(client3, 'member3', WITNESS_AIDS),
Expand Down Expand Up @@ -133,7 +132,7 @@
let serder = icpResult1.serder;

let sigs = icpResult1.sigs;
let sigers = sigs.map((sig: any) => new signify.Siger({ qb64: sig }));

Check warning on line 135 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

Unexpected any. Specify a different type

Check warning on line 135 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

Unexpected any. Specify a different type

let ims = signify.d(signify.messagize(serder, sigers));
let atc = ims.substring(serder.size);
Expand Down Expand Up @@ -179,7 +178,7 @@
op2 = await icpResult2.op();
serder = icpResult2.serder;
sigs = icpResult2.sigs;
sigers = sigs.map((sig: any) => new signify.Siger({ qb64: sig }));

Check warning on line 181 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

Unexpected any. Specify a different type

Check warning on line 181 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

Unexpected any. Specify a different type

ims = signify.d(signify.messagize(serder, sigers));
atc = ims.substring(serder.size);
Expand Down Expand Up @@ -223,7 +222,7 @@
op3 = await icpResult3.op();
serder = icpResult3.serder;
sigs = icpResult3.sigs;
sigers = sigs.map((sig: any) => new signify.Siger({ qb64: sig }));

Check warning on line 225 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and macOS-latest

Unexpected any. Specify a different type

Check warning on line 225 in examples/integration-scripts/multisig.test.ts

View workflow job for this annotation

GitHub Actions / Build, lint, and test on Node 18.12.1 and ubuntu-latest

Unexpected any. Specify a different type

ims = signify.d(signify.messagize(serder, sigers));
atc = ims.substring(serder.size);
Expand Down Expand Up @@ -1106,7 +1105,7 @@
console.log('Member1 received exchange message with the admit response');
const creds = await client4.credentials().list();
console.log(`Holder holds ${creds.length} credential`);
}, 240000);
}, 360000);

async function waitForOp(client: SignifyClient, op: any) {
while (!op['done']) {
Expand Down Expand Up @@ -1144,7 +1143,6 @@
state.agent.i
);

await resolveWitnesses(client);
return client;
}

Expand All @@ -1161,12 +1159,6 @@
return aid;
}

async function resolveWitnesses(client: SignifyClient) {
await Promise.all(
WITNESS_OOBIS.map((oobi) => client.oobis().resolve(oobi))
);
}

async function multisigIssue(
client: SignifyClient,
memberName: string,
Expand Down
106 changes: 105 additions & 1 deletion examples/integration-scripts/single-issuer-holder.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import signify, {
SignifyClient,
IssueCredentialArgs,
Operation,
Serder,
} from 'signify-ts';
import { resolveEnvironment } from './utils/resolve-env';

Expand Down Expand Up @@ -118,6 +119,34 @@ async function issueCredential(
return creds[0];
}

async function grantCredential(
client: SignifyClient,
issuerName: string,
recipient: string,
acdc: Serder,
acdcAttachment: string,
anc: Serder,
ancAttachment: string,
iss: Serder,
issAttachment: string
) {
const dt = createTimestamp();

const [grant, gsigs, end] = await client.ipex().grant({
senderName: issuerName,
recipient: recipient,
datetime: dt,
acdc: acdc,
acdcAttachment: acdcAttachment,
anc: anc,
ancAttachment: ancAttachment,
iss: iss,
issAttachment: issAttachment,
});

await client.ipex().submitGrant(issuerName, grant, gsigs, end, [recipient]);
}

interface Notification {
i: string;
dt: string;
Expand Down Expand Up @@ -207,9 +236,11 @@ test(
await signify.ready();
const issuerClient = await connect(url, bootUrl);
const holderClient = await connect(url, bootUrl);
const verifierClient = await connect(url, bootUrl);

await issuerClient.state();
await holderClient.state();
await verifierClient.state();

const issuerWits = await Promise.all(
witnessUrls.map(async (url, i) => {
Expand All @@ -233,6 +264,17 @@ test(
})
);

const verifierWits = await Promise.all(
witnessUrls.map(async (url, i) => {
const result = await resolveOobi(
verifierClient,
url + '/oobi',
`witness-${i}`
);
return result.i;
})
);

// Create two identifiers, one for each client
const issuerPrefix = await createIdentifier(
issuerClient,
Expand All @@ -244,10 +286,16 @@ test(
'holder',
holderWits
);
const verifierPrefix = await createIdentifier(
verifierClient,
'verifier',
verifierWits
);

// Exchange OOBIs
const issuerOobi = await getAgentOobi(issuerClient, 'issuer');
const holderOobi = await getAgentOobi(holderClient, 'holder');
const verifierOobi = await getAgentOobi(verifierClient, 'verifier');
await resolveOobi(issuerClient, holderOobi, 'holder');
await resolveOobi(
issuerClient,
Expand All @@ -260,6 +308,13 @@ test(
vleiServerUrl + '/oobi/' + SCHEMA_SAID,
'schema'
);
await resolveOobi(verifierClient, holderOobi, 'holder');
await resolveOobi(holderClient, verifierOobi, 'verifier');
await resolveOobi(
verifierClient,
vleiServerUrl + '/oobi/' + SCHEMA_SAID,
'schema'
);

await createRegistry(issuerClient, 'issuer', 'vLEI');

Expand Down Expand Up @@ -288,10 +343,59 @@ test(

await holderClient.notifications().mark(grantNotification.i);

await wait(async () => {
const c = await wait(async () => {
const creds = await holderClient.credentials().list();
assert(creds.length >= 1);
return creds[0];
});

console.log('Loading full credential');
const cred = await holderClient
.credentials()
.get('holder', c['sad']['d']);

const acdc = new Serder(cred['sad']);
const iss = new Serder(cred['iss']);
const anc = new Serder(cred['anc']);

console.log(`Presenting credential to verifier: ${c['sad']['d']}`);
await grantCredential(
holderClient,
'holder',
verifierPrefix,
acdc,
cred['atc'],
anc,
cred['ancatc'],
iss,
cred['issatc']
);

const verifierGrantNotification = await waitForNotification(
verifierClient,
'/exn/ipex/grant'
);

console.log(
`Notifcation of grant received by verifier ${verifierGrantNotification.a.d}`
);
await admitCredential(
verifierClient,
'verifier',
verifierGrantNotification.a.d!,
holderPrefix
);

await verifierClient.notifications().mark(verifierGrantNotification.i);

console.log('Checking for credential');
const p = await wait(async () => {
const creds = await verifierClient.credentials().list();
assert(creds.length >= 1);
return creds[0];
});

console.log(`Credential ${p.sad.d} received by Verifier`);
},
1000 * 60 * 5
);
4 changes: 2 additions & 2 deletions examples/integration-scripts/singlesig-ixn.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ describe('singlesig-ixn', () => {

// local and remote keystate sequence match
expect(keystate1[0].s).toEqual(keystate2[0].s);
});
}, 30000);
test('ixn1', async () => {
// local keystate before ixn
const keystate0: KeyState = (
Expand Down Expand Up @@ -75,5 +75,5 @@ describe('singlesig-ixn', () => {
const keystate3: KeyState = op.response;
// local and remote keystate match
expect(keystate3.s).toEqual(keystate1.s);
});
}, 30000);
});
4 changes: 2 additions & 2 deletions examples/integration-scripts/singlesig-rot.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ describe('singlesig-rot', () => {

// local and remote keystate sequence match
expect(keystate1[0].s).toEqual(keystate2[0].s);
});
}, 30000);
test('rot1', async () => {
// local keystate before rot
const keystate0: KeyState = (
Expand Down Expand Up @@ -86,5 +86,5 @@ describe('singlesig-rot', () => {
expect(keystate3.s).toEqual(keystate1.s);
expect(keystate3.k[0]).toEqual(keystate1.k[0]);
expect(keystate3.n[0]).toEqual(keystate1.n[0]);
});
}, 30000);
});
8 changes: 4 additions & 4 deletions examples/integration-scripts/test-setup-single-client.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -29,16 +29,16 @@ describe('test-setup-single-client', () => {
switch (env.preset) {
case 'local':
expect(name1_oobi).toEqual(
`http://localhost:3902/oobi/${name1_id}/agent/EC60ue9GOpQGrLBlS9T0dO6JkBTbv3V05Y4O730QBBoc`
`http://127.0.0.1:3902/oobi/${name1_id}/agent/EC60ue9GOpQGrLBlS9T0dO6JkBTbv3V05Y4O730QBBoc`
);
expect(oobi.oobis[0]).toEqual(
`http://localhost:5642/oobi/${name1_id}/witness/BBilc4-L3tFUnfM_wJr4S4OJanAv_VmF_dJNN6vkf2Ha`
`http://127.0.0.1:5642/oobi/${name1_id}/witness/BBilc4-L3tFUnfM_wJr4S4OJanAv_VmF_dJNN6vkf2Ha`
);
expect(oobi.oobis[1]).toEqual(
`http://localhost:5643/oobi/${name1_id}/witness/BLskRTInXnMxWaGqcpSyMgo0nYbalW99cGZESrz3zapM`
`http://127.0.0.1:5643/oobi/${name1_id}/witness/BLskRTInXnMxWaGqcpSyMgo0nYbalW99cGZESrz3zapM`
);
expect(oobi.oobis[2]).toEqual(
`http://localhost:5644/oobi/${name1_id}/witness/BIKKuvBwpmDVA4Ds-EpL5bt9OqPzWPja2LigFYZN2YfX`
`http://127.0.0.1:5644/oobi/${name1_id}/witness/BIKKuvBwpmDVA4Ds-EpL5bt9OqPzWPja2LigFYZN2YfX`
);
break;
case 'docker':
Expand Down
Loading
Loading