-
Notifications
You must be signed in to change notification settings - Fork 12
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Signed-off-by: Curtish <ch@curtish.me>
- Loading branch information
Showing
16 changed files
with
544 additions
and
266 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
import * as Domain from "../../domain"; | ||
import { asArray, isNil, notNil } from "../../utils"; | ||
import { Task } from "../../utils/tasks"; | ||
import { OutOfBandInvitation } from "../protocols/invitation/v2/OutOfBandInvitation"; | ||
import { DIDCommContext } from "./Context"; | ||
import { CreatePeerDID } from "./CreatePeerDID"; | ||
import { HandshakeRequest } from "../protocols/connection/HandshakeRequest"; | ||
|
||
/** | ||
* Create a connection from an OutOfBandInvitation | ||
* unless the Invitation has Attachments, then we parse and store those | ||
*/ | ||
|
||
interface Args { | ||
invitation: OutOfBandInvitation; | ||
alias?: string; | ||
} | ||
|
||
export class HandleOOBInvitation extends Task<void, Args> { | ||
async run(ctx: DIDCommContext) { | ||
const attachment = asArray(this.args.invitation.attachments).at(0); | ||
const peerDID = await ctx.run(new CreatePeerDID({ services: [], updateMediator: true })); | ||
const attachedMsg = notNil(attachment) | ||
? Domain.Message.fromJson({ ...attachment.payload, to: peerDID.toString() }) | ||
: null; | ||
|
||
if (isNil(attachedMsg)) { | ||
if (isNil(ctx.ConnectionManager.mediationHandler.mediator)) { | ||
throw new Domain.AgentError.NoMediatorAvailableError(); | ||
} | ||
|
||
const request = HandshakeRequest.fromOutOfBand(this.args.invitation, peerDID); | ||
await ctx.ConnectionManager.sendMessage(request.makeMessage()); | ||
const alias = this.args.alias ?? "OOBConn"; | ||
const pair = new Domain.DIDPair(peerDID, request.to, alias); | ||
await ctx.ConnectionManager.addConnection(pair); | ||
} | ||
else { | ||
await ctx.Pluto.storeMessage(attachedMsg); | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,75 @@ | ||
import { base64 } from "multiformats/bases/base64"; | ||
import * as Domain from "../../domain"; | ||
import { JsonObj, asJsonObj, expect, isObject, isString } from "../../utils"; | ||
import { Task } from "../../utils/tasks"; | ||
import { ProtocolType } from "../protocols/ProtocolTypes"; | ||
import { ParsePrismInvitation } from "./ParsePrismInvitation"; | ||
import { InvalidURLError, InvitationIsInvalidError } from "../../domain/models/errors/Agent"; | ||
import { ParseOOBInvitation } from "./ParseOOBInvitation"; | ||
import { InvitationType } from "../types"; | ||
|
||
/** | ||
* Attempt to parse a given invitation based on its Type | ||
* handle different encodings | ||
*/ | ||
|
||
interface Args { | ||
value: string | URL | JsonObj; | ||
} | ||
|
||
export class ParseInvitation extends Task<InvitationType, Args> { | ||
async run(ctx: Task.Context) { | ||
const json = this.decode(); | ||
const type = json.type ?? json.piuri; | ||
|
||
switch (type) { | ||
case ProtocolType.PrismOnboarding: | ||
return ctx.run(new ParsePrismInvitation({ value: json })); | ||
case ProtocolType.Didcomminvitation: | ||
return ctx.run(new ParseOOBInvitation({ value: json })); | ||
} | ||
|
||
throw new Domain.AgentError.UnknownInvitationTypeError(); | ||
} | ||
|
||
private decode() { | ||
if (this.args.value instanceof URL) { | ||
return expect(this.tryDecodeUrl(this.args.value), InvitationIsInvalidError); | ||
} | ||
|
||
if (isObject(this.args.value)) { | ||
return this.args.value; | ||
} | ||
|
||
if (isString(this.args.value)) { | ||
return expect( | ||
this.tryDecodeUrl(this.args.value) ?? this.tryDecodeB64(this.args.value), | ||
InvitationIsInvalidError | ||
); | ||
} | ||
|
||
throw new InvitationIsInvalidError(); | ||
} | ||
|
||
private tryDecodeUrl(value: string | URL) { | ||
try { | ||
const url = new URL(value); | ||
const oob = expect(url.searchParams.get("_oob"), InvalidURLError); | ||
return this.tryDecodeB64(oob); | ||
} | ||
catch { | ||
return null; | ||
} | ||
} | ||
|
||
private tryDecodeB64(value: string) { | ||
try { | ||
const decoded = base64.baseDecode(value); | ||
const data = Buffer.from(decoded).toString(); | ||
return asJsonObj(data); | ||
} | ||
catch { | ||
return null; | ||
} | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
import * as Domain from "../../domain"; | ||
import { JsonObj, asArray, asJsonObj, isArray, isNil, isObject, notEmptyString } from "../../utils"; | ||
import { Task } from "../../utils/tasks"; | ||
import { InvitationIsInvalidError } from "../../domain/models/errors/Agent"; | ||
import { OutOfBandInvitation } from "../protocols/invitation/v2/OutOfBandInvitation"; | ||
import { ProtocolType } from "../protocols/ProtocolTypes"; | ||
|
||
/** | ||
* parse OOB invitation | ||
*/ | ||
|
||
interface Args { | ||
value: string | JsonObj; | ||
} | ||
|
||
export class ParseOOBInvitation extends Task<OutOfBandInvitation, Args> { | ||
async run() { | ||
const invitation = this.safeParseBody(); | ||
|
||
if (invitation.isExpired) { | ||
throw new InvitationIsInvalidError('expired'); | ||
} | ||
|
||
return invitation; | ||
} | ||
|
||
private safeParseBody(): OutOfBandInvitation { | ||
const msg = asJsonObj(this.args.value); | ||
const valid = ( | ||
msg.type === ProtocolType.Didcomminvitation | ||
&& notEmptyString(msg.id) | ||
&& notEmptyString(msg.from) | ||
&& isObject(msg.body) | ||
&& isArray(msg.body.accept) | ||
&& msg.body.accept.every(notEmptyString) | ||
&& (isNil(msg.body.goal) || notEmptyString(msg.body.goal)) | ||
&& (isNil(msg.body.goal_code) || notEmptyString(msg.body.goal_code)) | ||
); | ||
|
||
if (valid === false) { | ||
throw new InvitationIsInvalidError(); | ||
} | ||
|
||
const attachments = asArray(msg.attachments).map((attachment) => | ||
Domain.AttachmentDescriptor.build(attachment.data, attachment.id, attachment.mediaType) | ||
); | ||
|
||
return new OutOfBandInvitation( | ||
msg.body, | ||
msg.from, | ||
msg.id, | ||
attachments, | ||
msg.expires_time | ||
); | ||
} | ||
} |
Oops, something went wrong.
97e05e7
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.