Skip to content

Commit 0f8ba6e

Browse files
zbarbutonextalias
authored andcommitted
Add support for resolving DID documents from IPFS
1 parent 30ab850 commit 0f8ba6e

14 files changed

+503
-69
lines changed

package-lock.json

Lines changed: 116 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@
3636
"devDependencies": {
3737
"@types/jest": "^27.4.0",
3838
"@types/node": "^16.7.7",
39+
"@types/node-fetch": "^2.6.4",
3940
"jest": "^27.5.0",
4041
"nodemon": "^2.0.7",
4142
"prettier": "2.5.1",
@@ -49,6 +50,7 @@
4950
"js-base64": "^3.7.5",
5051
"moment": "^2.29.1",
5152
"multiformats": "^9.6.2",
53+
"node-fetch": "^2.6.12",
5254
"varint": "^6.0.0"
5355
}
5456
}

src/identity/did-document.ts

Lines changed: 75 additions & 39 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,10 @@ import {
66
HcsDidMessage,
77
HcsDidUpdateDidOwnerEvent,
88
} from "..";
9+
import { IpfsDidDocumentDownloader } from "../utils/ipfs";
910
import { DidDocumentJsonProperties } from "./did-document-json-properties";
1011
import { DidSyntax } from "./did-syntax";
12+
import { HcsDidCreateDidDocumentEvent } from "./hcs/did/event/document/hcs-did-create-did-document-event";
1113
import { HcsDidEventTargetName } from "./hcs/did/event/hcs-did-event-target-name";
1214
import { HcsDidUpdateServiceEvent } from "./hcs/did/event/service/hcs-did-update-service-event";
1315
import { HcsDidCreateVerificationMethodEvent } from "./hcs/did/event/verification-method/hcs-did-create-verification-method-event";
@@ -24,6 +26,7 @@ export class DidDocument {
2426
private updated: Timestamp = null;
2527
private versionId: string = null;
2628
private deactivated: boolean = false;
29+
private downloader: IpfsDidDocumentDownloader = new IpfsDidDocumentDownloader();
2730

2831
private controller: any;
2932
private services: Map<string, any> = new Map();
@@ -37,11 +40,9 @@ export class DidDocument {
3740
capabilityDelegation: [],
3841
};
3942

40-
constructor(did: string, messages: HcsDidMessage[]) {
43+
constructor(did: string) {
4144
this.id = did;
4245
this.context = DidSyntax.DID_DOCUMENT_CONTEXT;
43-
44-
this.processMessages(messages);
4546
}
4647

4748
public hasOwner() {
@@ -72,14 +73,49 @@ export class DidDocument {
7273
return this.deactivated;
7374
}
7475

76+
public async processMessages(messages: HcsDidMessage[]): Promise<void> {
77+
for (const msg of messages) {
78+
if (
79+
!this.controller &&
80+
msg.getOperation() === DidMethodOperation.CREATE &&
81+
msg.getEvent().targetName !== HcsDidEventTargetName.DID_OWNER &&
82+
msg.getEvent().targetName !== HcsDidEventTargetName.DID_DOCUMENT
83+
) {
84+
console.warn("DID document owner is not registered. Event will be ignored...");
85+
return;
86+
}
87+
88+
switch (msg.getOperation()) {
89+
case DidMethodOperation.CREATE:
90+
await this.processCreateMessage(msg);
91+
return;
92+
case DidMethodOperation.UPDATE:
93+
await this.processUpdateMessage(msg);
94+
return;
95+
case DidMethodOperation.REVOKE:
96+
await this.processRevokeMessage(msg);
97+
return;
98+
case DidMethodOperation.DELETE:
99+
await this.processDeleteMessage(msg);
100+
return;
101+
default:
102+
console.warn(`Operation ${msg.getOperation()} is not supported. Event will be ignored...`);
103+
}
104+
}
105+
}
106+
107+
public setIpfsDownloader(downloader: IpfsDidDocumentDownloader) {
108+
this.downloader = downloader;
109+
}
110+
75111
public toJsonTree(): any {
76112
let rootObject = {};
77113

78114
rootObject[DidDocumentJsonProperties.CONTEXT] = this.context;
79115
rootObject[DidDocumentJsonProperties.ID] = this.id;
80116

81-
if (this.controller && this.id !== this.controller.controller) {
82-
rootObject[DidDocumentJsonProperties.CONTROLLER] = this.controller.controller;
117+
if (this.controller && this.id !== this.controller && this.id !== this.controller.controller) {
118+
rootObject[DidDocumentJsonProperties.CONTROLLER] = this.controller.controller ?? this.controller;
83119
}
84120

85121
rootObject[DidDocumentJsonProperties.VERIFICATION_METHOD] = Array.from(this.verificationMethods.values());
@@ -148,40 +184,40 @@ export class DidDocument {
148184
this.versionId = timestamp.toDate().getTime().toString();
149185
}
150186

151-
private processMessages(messages: HcsDidMessage[]): void {
152-
messages.forEach((msg) => {
153-
if (
154-
!this.controller &&
155-
msg.getOperation() === DidMethodOperation.CREATE &&
156-
msg.getEvent().targetName !== HcsDidEventTargetName.DID_OWNER
157-
) {
158-
console.warn("DID document owner is not registered. Event will be ignored...");
159-
return;
160-
}
161-
162-
switch (msg.getOperation()) {
163-
case DidMethodOperation.CREATE:
164-
this.processCreateMessage(msg);
165-
return;
166-
case DidMethodOperation.UPDATE:
167-
this.processUpdateMessage(msg);
168-
return;
169-
case DidMethodOperation.REVOKE:
170-
this.processRevokeMessage(msg);
171-
return;
172-
case DidMethodOperation.DELETE:
173-
this.processDeleteMessage(msg);
174-
return;
175-
default:
176-
console.warn(`Operation ${msg.getOperation()} is not supported. Event will be ignored...`);
177-
}
178-
});
179-
}
180-
181-
private processCreateMessage(message: HcsDidMessage): void {
187+
private async processCreateMessage(message: HcsDidMessage): Promise<void> {
182188
const event = message.getEvent();
183189

184190
switch (event.targetName) {
191+
case HcsDidEventTargetName.DID_DOCUMENT:
192+
const doc = await this.downloader.downloadDocument(event as HcsDidCreateDidDocumentEvent);
193+
if (doc[DidDocumentJsonProperties.ID] !== this.id) {
194+
throw new Error("Document ID does not match did");
195+
}
196+
this.controller = doc[DidDocumentJsonProperties.CONTROLLER];
197+
198+
this.services = new Map(
199+
(doc[DidDocumentJsonProperties.SERVICE] ?? []).map((service) => [service.id, service])
200+
);
201+
this.verificationMethods = new Map(
202+
(doc[DidDocumentJsonProperties.VERIFICATION_METHOD] ?? []).map((verificationMethod) => [
203+
verificationMethod.id,
204+
verificationMethod,
205+
])
206+
);
207+
208+
this.verificationRelationships[DidDocumentJsonProperties.ASSERTION_METHOD] =
209+
doc[DidDocumentJsonProperties.ASSERTION_METHOD] ?? [];
210+
this.verificationRelationships[DidDocumentJsonProperties.AUTHENTICATION] =
211+
doc[DidDocumentJsonProperties.AUTHENTICATION] ?? [];
212+
this.verificationRelationships[DidDocumentJsonProperties.KEY_AGREEMENT] =
213+
doc[DidDocumentJsonProperties.KEY_AGREEMENT] ?? [];
214+
this.verificationRelationships[DidDocumentJsonProperties.CAPABILITY_INVOCATION] =
215+
doc[DidDocumentJsonProperties.CAPABILITY_INVOCATION] ?? [];
216+
this.verificationRelationships[DidDocumentJsonProperties.CAPABILITY_DELEGATION] =
217+
doc[DidDocumentJsonProperties.CAPABILITY_DELEGATION] ?? [];
218+
219+
return;
220+
185221
case HcsDidEventTargetName.DID_OWNER:
186222
if (this.controller) {
187223
console.warn(`DID owner is already registered: ${this.controller}. Event will be ignored...`);
@@ -244,7 +280,7 @@ export class DidDocument {
244280
}
245281
}
246282

247-
private processUpdateMessage(message: HcsDidMessage): void {
283+
private async processUpdateMessage(message: HcsDidMessage): Promise<void> {
248284
const event = message.getEvent();
249285

250286
switch (event.targetName) {
@@ -303,7 +339,7 @@ export class DidDocument {
303339
}
304340
}
305341

306-
private processRevokeMessage(message: HcsDidMessage): void {
342+
private async processRevokeMessage(message: HcsDidMessage): Promise<void> {
307343
const event = message.getEvent();
308344

309345
switch (event.targetName) {
@@ -369,7 +405,7 @@ export class DidDocument {
369405
}
370406
}
371407

372-
private processDeleteMessage(message: HcsDidMessage): void {
408+
private async processDeleteMessage(message: HcsDidMessage): Promise<void> {
373409
const event = message.getEvent();
374410

375411
switch (event.targetName) {

src/identity/did-method-operation.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
export enum DidMethodOperation {
22
CREATE = "create",
3+
CREATE_DID_DOCUMENT = "create-did-document",
34
UPDATE = "update",
45
DELETE = "delete",
56
REVOKE = "revoke",

0 commit comments

Comments
 (0)