Skip to content

Commit e31fa28

Browse files
authored
Offer message handler fix (#231)
* Offer message handler fix * remove comment * 1.14.0
1 parent 3c8c06e commit e31fa28

File tree

5 files changed

+78
-26
lines changed

5 files changed

+78
-26
lines changed

package-lock.json

+2-2
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "@0xpolygonid/js-sdk",
3-
"version": "1.13.0",
3+
"version": "1.14.0",
44
"description": "SDK to work with Polygon ID",
55
"main": "dist/node/cjs/index.js",
66
"module": "dist/node/esm/index.js",

src/iden3comm/handlers/fetch.ts

+35-17
Original file line numberDiff line numberDiff line change
@@ -109,9 +109,16 @@ export class FetchHandler
109109
ctx: FetchMessageHandlerOptions
110110
): Promise<BasicMessage | null> {
111111
switch (message.type) {
112-
case PROTOCOL_MESSAGE_TYPE.CREDENTIAL_OFFER_MESSAGE_TYPE:
113-
await this.handleOfferMessage(message as CredentialsOfferMessage, ctx);
114-
return null;
112+
case PROTOCOL_MESSAGE_TYPE.CREDENTIAL_OFFER_MESSAGE_TYPE: {
113+
const result = await this.handleOfferMessage(message as CredentialsOfferMessage, ctx);
114+
if (Array.isArray(result)) {
115+
const credWallet = this.opts?.credentialWallet;
116+
if (!credWallet) throw new Error('Credential wallet is not provided');
117+
await credWallet.saveAll(result);
118+
return null;
119+
}
120+
return result as BasicMessage;
121+
}
115122
case PROTOCOL_MESSAGE_TYPE.CREDENTIAL_FETCH_REQUEST_MESSAGE_TYPE:
116123
return this.handleFetchRequest(message as CredentialFetchRequestMessage);
117124
case PROTOCOL_MESSAGE_TYPE.CREDENTIAL_ISSUANCE_RESPONSE_MESSAGE_TYPE:
@@ -128,16 +135,14 @@ export class FetchHandler
128135
headers?: HeadersInit;
129136
packerOptions?: JWSPackerParams;
130137
}
131-
): Promise<W3CCredential[]> {
138+
): Promise<W3CCredential[] | BasicMessage> {
132139
if (!ctx.mediaType) {
133140
ctx.mediaType = MediaType.ZKPMessage;
134141
}
135142

136143
const credentials: W3CCredential[] = [];
137144

138-
for (let index = 0; index < offerMessage.body.credentials.length; index++) {
139-
const credentialInfo = offerMessage.body.credentials[index];
140-
145+
for (const credentialInfo of offerMessage.body.credentials) {
141146
const guid = uuid.v4();
142147
const fetchRequest: MessageFetchRequestMessage = {
143148
id: guid,
@@ -167,7 +172,6 @@ export class FetchHandler
167172
...packerOpts
168173
})
169174
);
170-
let message: { body: { credential: W3CCredential } };
171175
try {
172176
if (!offerMessage?.body?.url) {
173177
throw new Error(`could not fetch W3C credential, body url is missing`);
@@ -180,16 +184,24 @@ export class FetchHandler
180184
},
181185
body: token
182186
});
183-
if (resp.status !== 200) {
184-
throw new Error(`could not fetch W3C credential, ${credentialInfo?.id}`);
187+
const arrayBuffer = await resp.arrayBuffer();
188+
if (!arrayBuffer.byteLength) {
189+
throw new Error(`could not fetch , ${credentialInfo?.id}, response is empty`);
190+
}
191+
const { unpackedMessage: message } = await this._packerMgr.unpack(
192+
new Uint8Array(arrayBuffer)
193+
);
194+
if (message.type !== PROTOCOL_MESSAGE_TYPE.CREDENTIAL_ISSUANCE_RESPONSE_MESSAGE_TYPE) {
195+
return message;
185196
}
186-
message = await resp.json();
187-
credentials.push(W3CCredential.fromJSON(message.body.credential));
197+
credentials.push(
198+
W3CCredential.fromJSON((message as CredentialIssuanceMessage).body.credential)
199+
);
188200
} catch (e: unknown) {
189201
throw new Error(
190-
`could not fetch W3C credential, ${credentialInfo?.id}, error: ${
191-
(e as Error).message ?? e
192-
}`
202+
`could not fetch protocol message for credential offer id: , ${
203+
credentialInfo?.id
204+
}, error: ${(e as Error).message ?? e}`
193205
);
194206
}
195207
}
@@ -219,11 +231,17 @@ export class FetchHandler
219231
PROTOCOL_MESSAGE_TYPE.CREDENTIAL_OFFER_MESSAGE_TYPE
220232
);
221233

222-
return this.handleOfferMessage(offerMessage, {
234+
const result = await this.handleOfferMessage(offerMessage, {
223235
mediaType: opts?.mediaType,
224236
headers: opts?.headers,
225237
packerOptions: opts?.packerOptions
226238
});
239+
240+
if (Array.isArray(result)) {
241+
return result;
242+
}
243+
244+
throw new Error('invalid protocol message response');
227245
}
228246

229247
private async handleFetchRequest(
@@ -242,7 +260,7 @@ export class FetchHandler
242260

243261
const credId = msgRequest.body?.id;
244262
if (!credId) {
245-
throw new Error('nvalid credential id in fetch request body');
263+
throw new Error('invalid credential id in fetch request body');
246264
}
247265

248266
if (!this.opts?.credentialWallet) {

src/iden3comm/types/protocol/credentials.ts

+3-3
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ export type CredentialsOfferMessage = Required<BasicMessage> & {
2222
/** CredentialsOfferMessageBody is struct the represents offer message */
2323
export type CredentialsOfferMessageBody = {
2424
url: string;
25-
credentials: Array<CredentialOffer>;
25+
credentials: CredentialOffer[];
2626
};
2727

2828
/** CredentialsOnchainOfferMessage represent Iden3message for credential onhcain offer message */
@@ -32,7 +32,7 @@ export type CredentialsOnchainOfferMessage = Required<BasicMessage> & {
3232

3333
/** CredentialsOnchainOfferMessageBody is struct the represents onchain offer message body */
3434
export type CredentialsOnchainOfferMessageBody = {
35-
credentials: Array<CredentialOffer>;
35+
credentials: CredentialOffer[];
3636
transaction_data: ContractInvokeTransactionData;
3737
};
3838

@@ -44,7 +44,7 @@ export type CredentialOffer = {
4444

4545
/** CredentialIssuanceMessage represent Iden3message for credential issuance */
4646
export type CredentialIssuanceMessage = Required<BasicMessage> & {
47-
body?: IssuanceMessageBody;
47+
body: IssuanceMessageBody;
4848
};
4949

5050
/** IssuanceMessageBody is struct the represents message when credential is issued */

tests/handlers/fetch.test.ts

+37-3
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import {
22
CredentialsOfferMessage,
33
FetchHandler,
4-
IFetchHandler,
54
IPackageManager,
65
IDataStorage,
76
IdentityWallet,
@@ -17,7 +16,8 @@ import {
1716
CredentialIssuanceMessage,
1817
FSCircuitStorage,
1918
ProofService,
20-
CircuitId
19+
CircuitId,
20+
MessageHandler
2121
} from '../../src';
2222

2323
import {
@@ -41,8 +41,9 @@ describe('fetch', () => {
4141
let credWallet: CredentialWallet;
4242

4343
let dataStorage: IDataStorage;
44-
let fetchHandler: IFetchHandler;
44+
let fetchHandler: FetchHandler;
4545
let packageMgr: IPackageManager;
46+
let msgHandler: MessageHandler;
4647
const agentUrl = 'https://testagent.com/';
4748

4849
const issuanceResponseMock = `{
@@ -134,6 +135,11 @@ describe('fetch', () => {
134135
fetchHandler = new FetchHandler(packageMgr, {
135136
credentialWallet: credWallet
136137
});
138+
139+
msgHandler = new MessageHandler({
140+
messageHandlers: [fetchHandler],
141+
packageManager: packageMgr
142+
});
137143
});
138144

139145
it('fetch credential issued to genesis did', async () => {
@@ -252,5 +258,33 @@ describe('fetch', () => {
252258

253259
const cred2 = await credWallet.findById(newId);
254260
expect(cred2).not.to.be.undefined;
261+
262+
const offer: CredentialsOfferMessage = {
263+
id,
264+
typ: PROTOCOL_CONSTANTS.MediaType.PlainMessage,
265+
type: PROTOCOL_CONSTANTS.PROTOCOL_MESSAGE_TYPE.CREDENTIAL_OFFER_MESSAGE_TYPE,
266+
thid: id,
267+
body: {
268+
url: agentUrl,
269+
credentials: [{ id: cred2?.id as string, description: 'kyc age credentials' }]
270+
},
271+
from: issuerDID.string(),
272+
to: userDID.string()
273+
};
274+
275+
const bytes = await packageMgr.packMessage(
276+
PROTOCOL_CONSTANTS.MediaType.PlainMessage,
277+
offer,
278+
{}
279+
);
280+
fetchMock.restore();
281+
fetchMock.spy();
282+
fetchMock.post(agentUrl, issuanceResponseMock);
283+
expect(await credWallet.list()).to.have.length(4);
284+
285+
const response = await msgHandler.handleMessage(bytes, {});
286+
// credential saved after handleing message via msgHandler
287+
expect(response).to.be.null;
288+
expect(await credWallet.list()).to.have.length(5);
255289
});
256290
});

0 commit comments

Comments
 (0)