diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/OfferJsonLdCredentialDialogStore.ts b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/OfferJsonLdCredentialDialogStore.ts new file mode 100644 index 0000000000000000000000000000000000000000..a2eb771119686942c174ad65f512fc5ecd821a6f --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/OfferJsonLdCredentialDialogStore.ts @@ -0,0 +1,131 @@ +import { makeAutoObservable, runInAction } from "mobx"; +import api, { W3cCredentialDto } from "@dashboard/engine-api"; +import { toast } from "react-toastify"; +import displayError from "@dashboard/utils/displayError"; +import { + FormType, + LegalParticipantFormData, + PrivatePersonFormData, +} from "./interfaces"; + +class OfferJsonLdCredentialDialogStore { + public formType: FormType | null = null; + + public connectionId: string | undefined; + public signing = false; + public offerSending = false; + + constructor(connectionId: string | undefined) { + this.connectionId = connectionId; + makeAutoObservable(this); + } + + private buildPrivatePersonJsonLd(data: PrivatePersonFormData) { + return { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://www.vereign.com/.well-known/vereign-schema", + ], + type: ["VerifiableCredential"], + id: "", + issuer: "", + issuanceDate: "", + credentialSubject: { + type: "vereign:PrivatePerson", + "vereign:name": data.name, + "vereign:dateOfBirth": data.dateOfBirth, + "vereign:address": { + "vereign:street": data.street, + "vereign:building": data.building, + "vereign:city": data.city, + "vereign:country": data.country, + }, + }, + }; + } + private buildLegalParticipantJsonLd(data: LegalParticipantFormData) { + return { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://www.vereign.com/.well-known/vereign-schema", + ], + type: ["VerifiableCredential"], + id: "", + issuer: "", + issuanceDate: "", + credentialSubject: { + type: "vereign:LegalParticipant", + "vereign:companyName": data.companyName, + "vereign:taxID": data.taxID, + "vereign:gleiCode": data.gleiCode, + "vereign:address": { + "vereign:street": data.street, + "vereign:building": data.building, + "vereign:city": data.city, + "vereign:country": data.country, + }, + }, + }; + } + + public offerPrivatePersonCreds = async (data: PrivatePersonFormData) => { + return this.offerCredential(this.buildPrivatePersonJsonLd(data)); + }; + + public offerLegalParticipantCreds = async ( + data: LegalParticipantFormData, + ) => { + return this.offerCredential(this.buildLegalParticipantJsonLd(data)); + }; + + public offerCustomJsonLdCreds = async (doc: unknown) => { + return this.offerCredential(doc); + }; + + private offerCredential = async (doc: unknown) => { + runInAction(() => (this.offerSending = true)); + try { + const cred = await api.offerJsonLdCredential({ + connectionId: this.connectionId, + doc: doc as W3cCredentialDto, + }); + toast("Credential offer sent"); + runInAction(() => { + this.offerSending = false; + }); + return cred; + } catch (e: unknown) { + displayError(e); + runInAction(() => { + this.offerSending = false; + }); + } + return null; + }; + + public signJsonLd = async (doc: unknown) => { + runInAction(() => (this.signing = true)); + try { + const cred = await api.signJsonLdCredential({ + doc: doc as W3cCredentialDto, + }); + toast("Credential signed"); + runInAction(() => { + this.signing = false; + }); + return cred; + } catch (e: unknown) { + displayError(e); + runInAction(() => { + this.signing = false; + }); + } + return null; + }; +} + +export type { OfferJsonLdCredentialDialogStore }; + +export default OfferJsonLdCredentialDialogStore; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/CustomForm.tsx b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/CustomForm.tsx new file mode 100644 index 0000000000000000000000000000000000000000..1797365ad48a9bcb6a8ea98e0ffc76eced18f98a --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/CustomForm.tsx @@ -0,0 +1,86 @@ +import React, { useEffect, useState } from "react"; +import { Button, Input, Select, Space } from "antd"; +import examples from "./examples"; +import { toast } from "react-toastify"; +import s from "./forms.module.scss"; + +export interface CustomFormProps { + isSendingOffer: boolean; + isSigningJsonLd: boolean; + onSendOffer: (doc: unknown) => void; + onSignJsonLd: (doc: unknown) => void; +} + +const selectOptions = examples.map(p => ({ + value: p.name, + label: p.name, +})); + +const CustomForm = ({ + isSendingOffer, + isSigningJsonLd, + onSendOffer, + onSignJsonLd, +}: CustomFormProps) => { + const [selectedValue, setSelectedValue] = useState(""); + const [doc, setDoc] = useState(""); + useEffect(() => { + const pair = examples.find((p) => p.name === selectedValue); + if (pair) { + setDoc(JSON.stringify(pair.doc, null, 2)); + } + }, [selectedValue]); + + const getParsedJsonLd = () => { + let parsed; + try { + parsed = JSON.parse(doc); + } catch (e) { + toast.error("Unable to parse JSON. Please check the document"); + throw e; + } + return parsed; + }; + + return ( + <div> + <div className={s.row}> + <Select + style={{ width: 300 }} + onChange={(val) => setSelectedValue(val)} + options={selectOptions} + /> + </div> + <div className={s.row}> + <Input.TextArea + rows={12} + value={doc} + onChange={(e) => setDoc(e.target.value)} + /> + </div> + + <Space direction="horizontal"> + <Button + type="primary" + htmlType="submit" + disabled={isSigningJsonLd || isSendingOffer} + loading={isSendingOffer} + onClick={() => onSendOffer(getParsedJsonLd())} + > + Send JSON-LD offer + </Button> + <Button + type="primary" + htmlType="submit" + disabled={isSigningJsonLd || isSendingOffer} + loading={isSigningJsonLd} + onClick={() => onSignJsonLd(getParsedJsonLd())} + > + Sign document + </Button> + </Space> + </div> + ); +}; + +export default CustomForm; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/Intro.tsx b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/Intro.tsx new file mode 100644 index 0000000000000000000000000000000000000000..9ddadd470bad310ca20209597e1ac1e2bfa2616b --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/Intro.tsx @@ -0,0 +1,33 @@ +import React from "react"; +import { Button, Space} from "antd"; +import { FormType } from "../interfaces"; + +export interface IntroProps { + onSelect: (value: FormType) => void; +} + +const Intro = ({ onSelect }: IntroProps) => { + return ( + <div> + Issuing JSON-LD Verifiable Credentials for a Participant. + <br /> + <br /> + Select a method to create your JSON-LD document: + <br /> + <br /> + <Space> + <Button onClick={() => onSelect("privatePerson")}> + Private Person + </Button> + <Button onClick={() => onSelect("legalParticipant")}> + Legal Participant + </Button> + <Button onClick={() => onSelect("custom")}> + Custom JSON-LD document + </Button> + </Space> + </div> + ); +}; + +export default Intro; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/LegalParticipantForm.tsx b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/LegalParticipantForm.tsx new file mode 100644 index 0000000000000000000000000000000000000000..af36bc8d69c8ea78b18da8e01c33b2317dd0a3a2 --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/LegalParticipantForm.tsx @@ -0,0 +1,96 @@ +import React from "react"; +import { Button, Form, Input, Space } from "antd"; +import { LegalParticipantFormData } from "../interfaces"; + +export interface LegalParticipantFormProps { + loading: boolean; + onSendOffer: (values: LegalParticipantFormData) => void; +} + +const LegalParticipantForm = ({ + loading, + onSendOffer, +}: LegalParticipantFormProps) => { + const initialValue: LegalParticipantFormData = { + companyName: "", + taxID: "", + gleiCode: "", + street: "", + building: "", + city: "", + country: "", + }; + return ( + <div> + <Form + layout="vertical" + initialValues={initialValue} + onFinish={onSendOffer} + autoComplete="off" + > + <Form.Item + label="CompanyName" + name="companyName" + rules={[{ required: true, message: "Please enter companyName!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="TaxID" + name="taxID" + rules={[{ required: true, message: "Please enter taxID!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="GleiCode" + name="gleiCode" + rules={[{ required: true, message: "Please enter gleiCode!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Street" + name="street" + rules={[{ required: true, message: "Please enter street!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Building" + name="building" + rules={[{ required: true, message: "Please enter building!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="City" + name="city" + rules={[{ required: true, message: "Please enter city!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Country" + name="country" + rules={[{ required: true, message: "Please enter country!" }]} + > + <Input /> + </Form.Item> + + <Space direction="horizontal"> + <Button + type="primary" + htmlType="submit" + disabled={loading} + loading={loading} + > + Send JSON-LD offer + </Button> + </Space> + </Form> + </div> + ); +}; + +export default LegalParticipantForm; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/PrivatePersonForm.tsx b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/PrivatePersonForm.tsx new file mode 100644 index 0000000000000000000000000000000000000000..10e2cc958a91b792d13d28dbc404601a1c7b642f --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/PrivatePersonForm.tsx @@ -0,0 +1,88 @@ +import React from "react"; +import { Button, Form, Input, Space } from "antd"; +import { PrivatePersonFormData } from "../interfaces"; + +export interface PrivatePersonFormProps { + loading: boolean; + onSendOffer: (value: PrivatePersonFormData) => void; +} + +const PrivatePersonForm = ({ + loading, + onSendOffer, +}: PrivatePersonFormProps) => { + const initialValue: PrivatePersonFormData = { + name: "", + dateOfBirth: "", + street: "", + building: "", + city: "", + country: "", + }; + return ( + <div> + <Form + layout="vertical" + initialValues={initialValue} + onFinish={onSendOffer} + autoComplete="off" + > + <Form.Item + label="Name" + name="name" + rules={[{ required: true, message: "Please enter name!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Date Of Birth" + name="dateOfBirth" + rules={[{ required: true, message: "Please enter date of birth!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Street" + name="street" + rules={[{ required: true, message: "Please enter street!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Building" + name="building" + rules={[{ required: true, message: "Please enter building!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="City" + name="city" + rules={[{ required: true, message: "Please enter city!" }]} + > + <Input /> + </Form.Item> + <Form.Item + label="Country" + name="country" + rules={[{ required: true, message: "Please enter country!" }]} + > + <Input /> + </Form.Item> + + <Space direction="horizontal"> + <Button + type="primary" + htmlType="submit" + disabled={loading} + loading={loading} + > + Send JSON-LD offer + </Button> + </Space> + </Form> + </div> + ); +}; + +export default PrivatePersonForm; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/examples.ts b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/examples.ts new file mode 100644 index 0000000000000000000000000000000000000000..5a51eea38b721064b8303f770c22faa650a707ae --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/examples.ts @@ -0,0 +1,480 @@ +const examples = [ + { + "name": "Vereign - PrivatePerson", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://www.vereign.com/.well-known/vereign-schema" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "type": [ + "VerifiableCredential" + ], + "credentialSubject": { + "type": "vereign:PrivatePerson", + "vereign:name": "Evelyn Parker", + "vereign:dateOfBirth": "12.06.1990", + "vereign:address": { + "vereign:street": "154 Maple Street, Apartment 3B", + "vereign:building": "154", + "vereign:city": "Sofia", + "vereign:country": "Bulgaria" + } + } + } + }, + { + "name": "Vereign - LegalParticipant", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://www.vereign.com/.well-known/vereign-schema" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "type": "vereign:LegalParticipant", + "vereign:companyName": "SolarTech Dynamics Inc.", + "vereign:taxID": "123-456-7890", + "vereign:gleiCode": "5500Z99QKFTV873N4X35", + "vereign:address": { + "vereign:street": "Innovation Boulevard", + "vereign:building": "No. 202", + "vereign:city": "New Eden", + "vereign:country": "Atlantis" + } + } + } + }, + { + "name": "XFSC - participant", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "type": "gx:LegalParticipant", + "gx:legalName": "Gaia-X European Association for Data and Cloud AISBL", + "gx:legalRegistrationNumber": { + "id": "https://gaia-x.eu/legalRegistrationNumberVC.json" + }, + "gx:headquarterAddress": { + "gx:countrySubdivisionCode": "BE-BRU" + }, + "gx:legalAddress": { + "gx:countrySubdivisionCode": "BE-BRU" + }, + "id": "" + } + } + }, + { + "name": "XFSC - service", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": ["VerifiableCredential"], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "type": "gx:ServiceOffering", + "gx:providedBy": { + "id": "https://wizard.lab.gaia-x.eu/api/credentials/2d37wbGvQzbAQ84yRouh2m2vBKkN8s5AfH9Q75HZRCUQmJW7yAVSNKzjJj6gcjE2mDNDUHCichXWdMH3S2c8AaDLm3kXmf5R8DFPWTYo5iRYkn8kvgU3AjMXc2qTbhuMHCpucKGgT1ZMkcHUygZkt11iD3T8VJNKYwsdk4MGoZwdqoFUuTKVcsXVTBA4ofD1Dtqzjavyng5WUpvJf4gRyfGkMvYYuHCgay8TK8Dayt6Rhcs3r2d1gRCg2UV419S9CpWZGwKQNEXdYbaB2eTiNbQ83KMd4mj1oSJgF7LLDZLJtKJbhwLzR3x35QUqEGevRxnRDKoPdHrEZN7r9TVAmvr9rt7Xq8eB4zGMTza59hisEAUaHsmWQNaVDorqFyZgN5bXswMK1irVQ5SVR9osCCRrKUKkntxfakjmSqapPfveMP39vkgTXfEhsfLUZXGwFcpgLpWxWRn1QLnJY11BVymS7DyaSvbSKotNFQxyV6vghfM2Jetw1mLxU5qsQqDYnDYJjPZQSmkwxjX3yenPVCz6N2ox83tj9AuuQrzg5p2iukNdunDd2QCsHaMEtTq9JVLzXtWs2eZbPkxCBEQwoKTGGVhKu5yxZjCtQGc#9894e9b0a38aa105b50bb9f4e7d0975641273416e70f166f4bd9fd1b00dfe81d" + }, + "gx:policy": "", + "gx:termsAndConditions": { + "gx:URL": "http://termsandconds.com", + "gx:hash": "d8402a23de560f5ab34b22d1a142feb9e13b3143" + }, + "gx:dataAccountExport": { + "gx:requestType": "API", + "gx:accessType": "digital", + "gx:formatType": "application/json" + }, + "id": "" + } + } + }, + { + "name": "XFSC - serviceLabelLevel1", + "doc": { + "credentialSubject": { + "id": "" + }, + "id": "", + "issuanceDate": "", + "issuer": "" + } + }, + { + "name": "XFSC - termsAndConditions", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": ["VerifiableCredential"], + "issuanceDate": "", + "credentialSubject": { + "@context": "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#", + "type": "gx:GaiaXTermsAndConditions", + "gx:termsAndConditions": "The PARTICIPANT signing the Self-Description agrees as follows:\n- to update its descriptions about any changes, be it technical, organizational, or legal - especially but not limited to contractual in regards to the indicated attributes present in the descriptions.\n\nThe keypair used to sign Verifiable Credentials will be revoked where Gaia-X Association becomes aware of any inaccurate statements in regards to the claims which result in a non-compliance with the Trust Framework and policy rules defined in the Policy Rules and Labelling Document (PRLD).", + "id": "" + }, + "issuer": "", + "id": "" + } + }, + { + "name": "XFSC - serviceWithResources", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": [ + { + "@type": "gx:ServiceOffering", + "@id": "https://lab.gaia-x.eu/lab.json", + "gx:providedBy": { + "@id": "did:web:wizard.lab.gaia-x.eu:development:api:credentials:2d37wbGvQzbAQ84yRouh2m2vBKkN8s5AfH9Q75HZRCUQmJW7yAVSNKzjJj6gcjE2mDNDUHCichXWdMH3S2c8AaDLm3kXmf5R8DQsEb24sbSenY4QHNVyrwjRTCZtrPHzTxGiHVtFohMXnmyScNcZHwcGDpEARdWXMVaVfmbfCfcmypHbC7Pxa8zzEtVtJyemWZyvsU66ndiqrg5b7a4VWUyvG8kh5ckH385QyL5i9vWL6w4rEM3rD56ZFzjKrRrZ8wz2nEQFfTFcFKD3mZdZrfnLntaQz6y7daWs9xX2dJ5d65EewDskcoXHuC3QqBJru45sHMjDBv5AAVopWg6sPdNPDdVPhk8ToPVtUzWnSEfqirHzzgrrGFvXuJ2PFV1h5RFWDvP6yFxn6dtcCdYVbqt45c8BH6zR7YrxZqhLNV7j9voKE6HdYMgz7NyeQ3mCYENAF2qtf6gHHx41Bu7ApSbQcNFCoEapFQaowg1rsU3L3oUxC51zT47wPoNU4sG71uKrLyuz56sH3fmx4wGCCPZsuqQNXH3brnubcYfdG39Rg2A89yawAN1g42kUMiuMcgL5Cu5L2TZtq9XhSRsV6gwYPW5g2FLoFSyNhxp#7eb7b2675ecb358920f8fba55e2445f547ea2a251d8eee50c9fb2a60bf6a7441" + }, + "gx:termsAndConditions": { + "@id": "https://lab.gaia-x.eu/soterms.json", + "@type": "gx:SOTermsAndConditions", + "gx:URL": "", + "gx:hash": "" + }, + "gx:policy": "", + "gx:dataAccountExport": { + "gx:requestType": "API", + "gx:accessType": "digital", + "gx:formatType": "application/json" + }, + "gx:aggregationOf": [ + { + "@id": "https://lab.gaia-x.eu/ces-software.json" + }, + { + "@id": "https://lab.gaia-x.eu/ovh-k8s.json" + } + ] + }, + { + "@id": "https://lab.gaia-x.eu/cesDataResource.json", + "@type": "gx:DataResource", + "gx:name": "CES Data", + "gx:description": "Contains GX compliant credentials", + "gx:containsPII": false, + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:copyrightOwnedBy": "original owner", + "gx:producedBy": { + "@id": "did:web:wizard.lab.gaia-x.eu:development:api:credentials:2d37wbGvQzbAQ84yRouh2m2vBKkN8s5AfH9Q75HZRCUQmJW7yAVSNKzjJj6gcjE2mDNDUHCichXWdMH3S2c8AaDLm3kXmf5R8DQsEb24sbSenY4QHNVyrwjRTCZtrPHzTxGiHVtFohMXnmyScNcZHwcGDpEARdWXMVaVfmbfCfcmypHbC7Pxa8zzEtVtJyemWZyvsU66ndiqrg5b7a4VWUyvG8kh5ckH385QyL5i9vWL6w4rEM3rD56ZFzjKrRrZ8wz2nEQFfTFcFKD3mZdZrfnLntaQz6y7daWs9xX2dJ5d65EewDskcoXHuC3QqBJru45sHMjDBv5AAVopWg6sPdNPDdVPhk8ToPVtUzWnSEfqirHzzgrrGFvXuJ2PFV1h5RFWDvP6yFxn6dtcCdYVbqt45c8BH6zR7YrxZqhLNV7j9voKE6HdYMgz7NyeQ3mCYENAF2qtf6gHHx41Bu7ApSbQcNFCoEapFQaowg1rsU3L3oUxC51zT47wPoNU4sG71uKrLyuz56sH3fmx4wGCCPZsuqQNXH3brnubcYfdG39Rg2A89yawAN1g42kUMiuMcgL5Cu5L2TZtq9XhSRsV6gwYPW5g2FLoFSyNhxp#7eb7b2675ecb358920f8fba55e2445f547ea2a251d8eee50c9fb2a60bf6a7441" + }, + "gx:exposedThrough": { + "@id": "https://lab.gaia-x.eu/lab.json" + } + }, + { + "@type": "gx:SoftwareResource", + "@id": "https://lab.gaia-x.eu/ces-software.json", + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:copyrightOwnedBy": "original owner" + }, + { + "@type": "gx:SoftwareResource", + "@id": "https://lab.gaia-x.eu/ovh-k8s.json", + "gx:policy": "default: allow", + "gx:license": "https://www.ovh.com/fr/support/documents_legaux/conditions%20generales%20de%20service.pdf", + "gx:copyrightOwnedBy": "OVH" + }, + { + "@type": "gx:InstantiatedVirtualResource", + "@id": "https://lab.gaia-x.eu/cesDevInstance.json", + "gx:instanceOf": { + "@id": "https://lab.gaia-x.eu/ces-software.json" + }, + "gx:hostedOn": { + "@id": "https://lab.gaia-x.eu/ovh-k8s.json" + }, + "gx:maintainedBy": { + "@id": "did:web:wizard.lab.gaia-x.eu:development:api:credentials:2d37wbGvQzbAQ84yRouh2m2vBKkN8s5AfH9Q75HZRCUQmJW7yAVSNKzjJj6gcjE2mDNDUHCichXWdMH3S2c8AaDLm3kXmf5R8DQsEb24sbSenY4QHNVyrwjRTCZtrPHzTxGiHVtFohMXnmyScNcZHwcGDpEARdWXMVaVfmbfCfcmypHbC7Pxa8zzEtVtJyemWZyvsU66ndiqrg5b7a4VWUyvG8kh5ckH385QyL5i9vWL6w4rEM3rD56ZFzjKrRrZ8wz2nEQFfTFcFKD3mZdZrfnLntaQz6y7daWs9xX2dJ5d65EewDskcoXHuC3QqBJru45sHMjDBv5AAVopWg6sPdNPDdVPhk8ToPVtUzWnSEfqirHzzgrrGFvXuJ2PFV1h5RFWDvP6yFxn6dtcCdYVbqt45c8BH6zR7YrxZqhLNV7j9voKE6HdYMgz7NyeQ3mCYENAF2qtf6gHHx41Bu7ApSbQcNFCoEapFQaowg1rsU3L3oUxC51zT47wPoNU4sG71uKrLyuz56sH3fmx4wGCCPZsuqQNXH3brnubcYfdG39Rg2A89yawAN1g42kUMiuMcgL5Cu5L2TZtq9XhSRsV6gwYPW5g2FLoFSyNhxp#7eb7b2675ecb358920f8fba55e2445f547ea2a251d8eee50c9fb2a60bf6a7441" + }, + "gx:serviceAccessPoint": [ + { + "@id": "https://lab.gaia-x.eu/cesDevInstanceAP.json" + } + ] + }, + { + "@type": "gx:ServiceAccessPoint", + "@id": "https://lab.gaia-x.eu/cesDevInstanceAP.json", + "gx:host": "ces-development.lab.gaia-x.eu", + "gx:port": "443", + "gx:protocol": "https", + "gx:version": "1.0.0", + "gx:openAPI": "https://ces-development.lab.gaia-x.eu/q/swagger-ui" + }, + { + "@type": "gx:LegitimateInterest", + "@id": "https://lab.gaia-x.eu/ces-interest.json", + "gx:legalBasis": "GDPR-6-1-a", + "gx:dataProtectionContact": "https://gaia-x.eu/privacy-policy/" + } + ] + } + }, + { + "name": "XFSC - sOTermsAndConditions", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@id": "https://lab.gaia-x.eu/soterms.json", + "@type": "gx:SOTermsAndConditions", + "gx:URL": "", + "gx:hash": "", + "id": "" + } + } + }, + { + "name": "XFSC - dataResource", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@id": "https://lab.gaia-x.eu/cesDataResource.json", + "@type": "gx:DataResource", + "gx:name": "CES Data", + "gx:description": "Contains GX compliant credentials", + "gx:containsPII": false, + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:copyrightOwnedBy": "original owner", + "gx:producedBy": { + "@id": "__id of the data provider participant CS__" + }, + "gx:exposedThrough": { + "@id": "__id of the service offering exposing this data__" + }, + "id": "" + } + } + }, + { + "name": "XFSC - physicalResource", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:PhysicalResource", + "@id": "https://lab.gaia-x.eu/ces-physical.json", + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:maintainedBy": "__id of the participant CS of the maintainer__", + "gx:ownedBy": "__id of the participant CS of the owner__", + "gx:manufacturedBy": "__id of the participant CS of the manufacturer__", + "gx:locationAddress": { + "@type": "vcard:Address", + "vcard:postal-code": "12345", + "vcard:street-address": "123 Main St", + "gx:countryCode": "US" + }, + "gx:location": "35.89421911 139.94637467", + "id": "" + } + } + }, + { + "name": "XFSC - softwareResource", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:SoftwareResource", + "@id": "https://lab.gaia-x.eu/ces-software.json", + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:copyrightOwnedBy": "original owner", + "id": "" + } + } + }, + { + "name": "XFSC - virtualResource", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:VirtualResource", + "@id": "https://lab.gaia-x.eu/ces-software.json", + "gx:policy": "default: allow", + "gx:license": "EPL-2.0", + "gx:copyrightOwnedBy": "original owner", + "id": "" + } + } + }, + { + "name": "XFSC - legitimateInterest", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:LegitimateInterest", + "@id": "https://lab.gaia-x.eu/ces-interest.json", + "gx:legalBasis": "GDPR-6-1-a", + "gx:dataProtectionContact": "https://gaia-x.eu/privacy-policy/", + "id": "" + } + } + }, + { + "name": "XFSC - serviceAccessPoint", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:ServiceAccessPoint", + "@id": "https://lab.gaia-x.eu/cesDevInstanceAP.json", + "gx:host": "ces-development.lab.gaia-x.eu", + "gx:port": "443", + "gx:protocol": "https", + "gx:version": "1.0.0", + "gx:openAPI": "https://ces-development.lab.gaia-x.eu/q/swagger-ui", + "id": "" + } + } + }, + { + "name": "XFSC - instantiatedVirtualResource", + "doc": { + "@context": [ + "https://www.w3.org/2018/credentials/v1", + "https://w3id.org/security/suites/jws-2020/v1", + "https://registry.lab.gaia-x.eu/development/api/trusted-shape-registry/v1/shapes/jsonld/trustframework#" + ], + "type": [ + "VerifiableCredential" + ], + "id": "", + "issuer": "", + "issuanceDate": "", + "credentialSubject": { + "@type": "gx:InstantiatedVirtualResource", + "@id": "https://lab.gaia-x.eu/cesDevInstance.json", + "gx:instanceOf": { + "@id": "__id of the cs of software resource this is an instance of__" + }, + "gx:hostedOn": { + "@id": "__id of the cs of the physical or virtual resource hosting this__" + }, + "gx:maintainedBy": { + "@id": "__id of the cs of the participant maintaining this__" + }, + "gx:serviceAccessPoint": [ + { + "@id": "__id of the cs of the service access point__" + } + ], + "id": "" + } + } + } +] + +export default examples; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/forms.module.scss b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/forms.module.scss new file mode 100644 index 0000000000000000000000000000000000000000..bc5028ee6e2f48a063774309cf7e6d2756bb6a7a --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/forms/forms.module.scss @@ -0,0 +1,3 @@ +.row { + margin-bottom: 8px; +} diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/index.tsx b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/index.tsx new file mode 100644 index 0000000000000000000000000000000000000000..8469854fcbc558e34b5376fdcda89b536190c007 --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/index.tsx @@ -0,0 +1,100 @@ +import React, { useEffect, useState } from "react"; +import { observer } from "mobx-react"; +import { Space } from "antd"; +import Modal, { FcProps } from "@dashboard/components/Modal"; +import { CredentialOfferResponseDto } from "@dashboard/engine-api"; +import OfferJsonLdCredentialDialogStore from "./OfferJsonLdCredentialDialogStore"; +import modalStore from "@dashboard/store/modalStore"; +import Intro from "./forms/Intro"; +import PrivatePersonForm from "./forms/PrivatePersonForm"; +import LegalParticipantForm from "./forms/LegalParticipantForm"; +import CustomForm from "./forms/CustomForm"; +import s from "./styles.module.scss"; + +export interface OfferJsonLdCredentialDialogProps { + connectionId: string | undefined; + onCredentialOffered: (cred: CredentialOfferResponseDto) => void; +} + +const OfferJsonLdCredentialDialog = observer( + ({ + setTitle, + setClassName, + setWidth, + onClose, + data, + }: FcProps<OfferJsonLdCredentialDialogProps>) => { + const [store] = useState( + () => new OfferJsonLdCredentialDialogStore(data.connectionId), + ); + + useEffect(() => { + setClassName(s.modal); + setWidth("80vw"); + if (data.connectionId) { + setTitle("Offer JSON-LD credential to " + data.connectionId); + } else { + setTitle("Offer connectionless JSON-LD credential"); + } + }, [setTitle, setClassName, setWidth, data, data.connectionId]); + + return ( + <Modal.Body className={s.body}> + <Space direction="vertical"> + {store.formType === null && ( + <Intro + onSelect={(value) => { + store.formType = value; + }} + /> + )} + {store.formType === "privatePerson" && ( + <PrivatePersonForm + loading={store.offerSending} + onSendOffer={async (formData) => { + const offer = await store.offerPrivatePersonCreds(formData); + if (offer) { + data.onCredentialOffered(offer); + onClose(); + } + }} + /> + )} + {store.formType === "legalParticipant" && ( + <LegalParticipantForm + loading={store.offerSending} + onSendOffer={async (formData) => { + const offer = await store.offerLegalParticipantCreds(formData); + if (offer) { + data.onCredentialOffered(offer); + onClose(); + } + }} + /> + )} + {store.formType === "custom" && ( + <CustomForm + isSendingOffer={store.offerSending} + isSigningJsonLd={store.signing} + onSendOffer={async (doc) => { + const offer = await store.offerCustomJsonLdCreds(doc); + if (offer) { + data.onCredentialOffered(offer); + onClose(); + } + }} + onSignJsonLd={async (doc) => { + const signedDoc = await store.signJsonLd(doc); + if (signedDoc) { + modalStore.openViewJsonDialog({ data: signedDoc }); + } + }} + /> + )} + </Space> + </Modal.Body> + ); + }, +); + +export default OfferJsonLdCredentialDialog; diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/interfaces.ts b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/interfaces.ts new file mode 100644 index 0000000000000000000000000000000000000000..67d25f0e9aee3be600d5dfeb3bbbff6ff4273fc3 --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/interfaces.ts @@ -0,0 +1,20 @@ +export type FormType = "privatePerson" | "legalParticipant" | "custom"; + +export interface PrivatePersonFormData { + name: string; + dateOfBirth: string; + street: string; + building: string; + city: string; + country: string; +} + +export interface LegalParticipantFormData { + companyName: string; + taxID: string; + gleiCode: string; + street: string; + building: string; + city: string; + country: string; +} diff --git a/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/styles.module.scss b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/styles.module.scss new file mode 100644 index 0000000000000000000000000000000000000000..59cefd5ec47e48720143bed96698bf899263b357 --- /dev/null +++ b/apps/dashboard/src/modals/OfferJsonLdCredentialDialog/styles.module.scss @@ -0,0 +1,7 @@ +.modal { + top: 40px; +} + +.body { + +} diff --git a/apps/dashboard/src/routes/pages/ConnectionViewPage/index.tsx b/apps/dashboard/src/routes/pages/ConnectionViewPage/index.tsx index a4ecedb5b51cb473e66ad84e0aa6a071a06e4d5a..8673f7efdb556650b5936e5efd0fa388a29004dc 100644 --- a/apps/dashboard/src/routes/pages/ConnectionViewPage/index.tsx +++ b/apps/dashboard/src/routes/pages/ConnectionViewPage/index.tsx @@ -39,6 +39,20 @@ const ConnectionViewPage = observer(() => { > Offer credential </Button> + <Button + onClick={() => { + modalStore.openOfferJsonLdCredentialDialog({ + connectionId: id, + onCredentialOffered: (cred) => { + setTimeout(() => { + window.location.reload(); + }, 3000); + }, + }); + }} + > + Offer JSON-LD credential + </Button> <Button onClick={() => { modalStore.openRequestProofDialog({ diff --git a/apps/dashboard/src/routes/pages/CredentialListPage/index.tsx b/apps/dashboard/src/routes/pages/CredentialListPage/index.tsx index 7adf872d2f4f1bb69b71a8dea8a649186ec93d03..d464a87b896f768d384a7c92978f63add0897b0d 100644 --- a/apps/dashboard/src/routes/pages/CredentialListPage/index.tsx +++ b/apps/dashboard/src/routes/pages/CredentialListPage/index.tsx @@ -34,6 +34,22 @@ const CredentialListPage = observer(() => { > Offer connectionless credential </Button> + <Button + onClick={() => { + modalStore.openOfferJsonLdCredentialDialog({ + connectionId: undefined, + onCredentialOffered: (offer) => { + modalStore.openViewConnectionlessCredentialOffer({ + credentialUrl: offer.credentialUrl, + credentialUrlShort: offer.shortCredentialUrl, + credentialRecord: offer.credentialRecord, + }); + }, + }); + }} + > + Offer connectionless JSON-LD credential + </Button> <Button onClick={() => { modalStore.openAcceptConnectionlessCredentialOfferDialog({ diff --git a/apps/dashboard/src/store/modalStore.tsx b/apps/dashboard/src/store/modalStore.tsx index e77cd3d52ce21c1755c32bcbc5292e2931bf7e55..3e4f47174885c0ed0a0cf77f2361a3b62bb17631 100644 --- a/apps/dashboard/src/store/modalStore.tsx +++ b/apps/dashboard/src/store/modalStore.tsx @@ -35,6 +35,9 @@ import ViewConnectionlessCredentialOffer, { import AcceptConnectionlessCredentialOfferDialog, { AcceptConnectionlessCredentialOfferDialogProps, } from "@dashboard/modals/AcceptConnectionlessCredentialOfferDialog"; +import OfferJsonLdCredentialDialog, { + OfferJsonLdCredentialDialogProps, +} from "@dashboard/modals/OfferJsonLdCredentialDialog"; class ModalStore { public modals: { id: string; modal: unknown }[] = []; @@ -92,6 +95,9 @@ class ModalStore { public openAcceptConnectionlessCredentialOfferDialog = ( data: AcceptConnectionlessCredentialOfferDialogProps, ) => this.open(AcceptConnectionlessCredentialOfferDialog, data); + public openOfferJsonLdCredentialDialog = ( + data: OfferJsonLdCredentialDialogProps, + ) => this.open(OfferJsonLdCredentialDialog, data); } export type { ModalStore }; diff --git a/libs/clients/src/frontend/agent_gen.ts b/libs/clients/src/frontend/agent_gen.ts index af5ab0b7fbadc4cf550a3954ffb7be0a7dac78a1..fa2103f72ba1ece8d1ba48050025be5a92ed2919 100644 --- a/libs/clients/src/frontend/agent_gen.ts +++ b/libs/clients/src/frontend/agent_gen.ts @@ -340,6 +340,42 @@ export class RestControllerClient { return Promise.resolve<ConnectionRecordDto[]>(null as any); } + pingConnection(id: string): Promise<BaseRecordDto> { + let url_ = this.baseUrl + "/api/v1/connections/ping/{id}"; + if (id === undefined || id === null) + throw new Error("The parameter 'id' must be defined."); + url_ = url_.replace("{id}", encodeURIComponent("" + id)); + url_ = url_.replace(/[?&]$/, ""); + + let options_: RequestInit = { + method: "POST", + headers: { + "Accept": "application/json" + } + }; + + return this.http.fetch(url_, options_).then((_response: Response) => { + return this.processPingConnection(_response); + }); + } + + protected processPingConnection(response: Response): Promise<BaseRecordDto> { + const status = response.status; + let _headers: any = {}; if (response.headers && response.headers.forEach) { response.headers.forEach((v: any, k: any) => _headers[k] = v); }; + if (status === 201) { + return response.text().then((_responseText) => { + let result201: any = null; + result201 = _responseText === "" ? null : JSON.parse(_responseText, this.jsonParseReviver) as BaseRecordDto; + return result201; + }); + } else if (status !== 200 && status !== 204) { + return response.text().then((_responseText) => { + return throwException("An unexpected server error occurred.", status, _responseText, _headers); + }); + } + return Promise.resolve<BaseRecordDto>(null as any); + } + createSchema(body: CreateSchemaRequestDto): Promise<SchemaRecordDto> { let url_ = this.baseUrl + "/api/v1/schemas"; url_ = url_.replace(/[?&]$/, ""); @@ -591,6 +627,116 @@ export class RestControllerClient { return Promise.resolve<CredentialOfferResponseDto>(null as any); } + offerJsonLdCredential(body: OfferJsonCredentialRequests): Promise<CredentialOfferResponseDto> { + let url_ = this.baseUrl + "/api/v1/credentials/jsonld/offers"; + url_ = url_.replace(/[?&]$/, ""); + + const content_ = JSON.stringify(body); + + let options_: RequestInit = { + body: content_, + method: "POST", + headers: { + "Content-Type": "application/json", + "Accept": "application/json" + } + }; + + return this.http.fetch(url_, options_).then((_response: Response) => { + return this.processOfferJsonLdCredential(_response); + }); + } + + protected processOfferJsonLdCredential(response: Response): Promise<CredentialOfferResponseDto> { + const status = response.status; + let _headers: any = {}; if (response.headers && response.headers.forEach) { response.headers.forEach((v: any, k: any) => _headers[k] = v); }; + if (status === 201) { + return response.text().then((_responseText) => { + let result201: any = null; + result201 = _responseText === "" ? null : JSON.parse(_responseText, this.jsonParseReviver) as CredentialOfferResponseDto; + return result201; + }); + } else if (status !== 200 && status !== 204) { + return response.text().then((_responseText) => { + return throwException("An unexpected server error occurred.", status, _responseText, _headers); + }); + } + return Promise.resolve<CredentialOfferResponseDto>(null as any); + } + + signJsonLdCredential(body: SignJsonCredentialRequests): Promise<W3cJsonLdVerifiableCredentialDto> { + let url_ = this.baseUrl + "/api/v1/jsonld/sign"; + url_ = url_.replace(/[?&]$/, ""); + + const content_ = JSON.stringify(body); + + let options_: RequestInit = { + body: content_, + method: "POST", + headers: { + "Content-Type": "application/json", + "Accept": "application/json" + } + }; + + return this.http.fetch(url_, options_).then((_response: Response) => { + return this.processSignJsonLdCredential(_response); + }); + } + + protected processSignJsonLdCredential(response: Response): Promise<W3cJsonLdVerifiableCredentialDto> { + const status = response.status; + let _headers: any = {}; if (response.headers && response.headers.forEach) { response.headers.forEach((v: any, k: any) => _headers[k] = v); }; + if (status === 201) { + return response.text().then((_responseText) => { + let result201: any = null; + result201 = _responseText === "" ? null : JSON.parse(_responseText, this.jsonParseReviver) as W3cJsonLdVerifiableCredentialDto; + return result201; + }); + } else if (status !== 200 && status !== 204) { + return response.text().then((_responseText) => { + return throwException("An unexpected server error occurred.", status, _responseText, _headers); + }); + } + return Promise.resolve<W3cJsonLdVerifiableCredentialDto>(null as any); + } + + signJsonLdPresentationByCredId(cred_id: string): Promise<W3cJsonLdVerifiablePresentationDto> { + let url_ = this.baseUrl + "/api/v1/jsonld/credentials/{cred_id}/prepare-verifiable-presentation"; + if (cred_id === undefined || cred_id === null) + throw new Error("The parameter 'cred_id' must be defined."); + url_ = url_.replace("{cred_id}", encodeURIComponent("" + cred_id)); + url_ = url_.replace(/[?&]$/, ""); + + let options_: RequestInit = { + method: "POST", + headers: { + "Accept": "application/json" + } + }; + + return this.http.fetch(url_, options_).then((_response: Response) => { + return this.processSignJsonLdPresentationByCredId(_response); + }); + } + + protected processSignJsonLdPresentationByCredId(response: Response): Promise<W3cJsonLdVerifiablePresentationDto> { + const status = response.status; + let _headers: any = {}; if (response.headers && response.headers.forEach) { response.headers.forEach((v: any, k: any) => _headers[k] = v); }; + if (status === 201) { + return response.text().then((_responseText) => { + let result201: any = null; + result201 = _responseText === "" ? null : JSON.parse(_responseText, this.jsonParseReviver) as W3cJsonLdVerifiablePresentationDto; + return result201; + }); + } else if (status !== 200 && status !== 204) { + return response.text().then((_responseText) => { + return throwException("An unexpected server error occurred.", status, _responseText, _headers); + }); + } + return Promise.resolve<W3cJsonLdVerifiablePresentationDto>(null as any); + } + fetchCredentials(states: States2[] | undefined, connectionId: string | undefined): Promise<CredentialRecordDto[]> { let url_ = this.baseUrl + "/api/v1/credentials?"; if (states === null) @@ -1331,6 +1477,14 @@ export interface ConnectionRecordDto { [key: string]: any; } +export interface BaseRecordDto { + id?: string; + createdAt?: Date; + updatedAt?: Date; + + [key: string]: any; +} + export interface CreateSchemaRequestDto { name: string; attributes: string[]; @@ -1340,14 +1494,14 @@ export interface CreateSchemaRequestDto { } export interface SchemaRecordDto { + id?: string; + createdAt?: Date; + updatedAt?: Date; name: string; attributes: string[]; version: string; issuerId?: string; methodName?: string; - id?: string; - createdAt?: Date; - updatedAt?: Date; [key: string]: any; } @@ -1359,12 +1513,12 @@ export interface IdReqDto { } export interface CreddefRecordDto { - schemaId: string; - issuerId: string; - tag: string; id?: string; createdAt?: Date; updatedAt?: Date; + schemaId: string; + issuerId: string; + tag: string; [key: string]: any; } @@ -1392,14 +1546,14 @@ export interface OfferCredentialRequestDto { } export interface CredentialRecordDto { + id?: string; + createdAt?: Date; + updatedAt?: Date; state: CredentialRecordDtoState; credentialRecordType: string; connectionId?: string; attributes?: OfferCredentialAttributes[]; tags: any; - id?: string; - createdAt?: Date; - updatedAt?: Date; [key: string]: any; } @@ -1412,6 +1566,66 @@ export interface CredentialOfferResponseDto { [key: string]: any; } +export interface W3cCredentialStatusDto { + id: string; + type: string; + + [key: string]: any; +} + +export interface W3cCredentialDto { + context: any[]; + id?: string; + type: string[]; + issuer: any; + issuanceDate: string; + expirationDate?: string; + credentialSubject: any; + credentialSchema?: any; + credentialStatus?: W3cCredentialStatusDto; + + [key: string]: any; +} + +export interface OfferJsonCredentialRequests { + connectionId?: string; + doc: W3cCredentialDto; + + [key: string]: any; +} + +export interface SignJsonCredentialRequests { + doc: W3cCredentialDto; + + [key: string]: any; +} + +export interface W3cJsonLdVerifiableCredentialDto { + context: any[]; + id?: string; + type: string[]; + issuer: any; + issuanceDate: string; + expirationDate?: string; + credentialSubject: any; + credentialSchema?: any; + credentialStatus?: W3cCredentialStatusDto; + proof: any; + + [key: string]: any; +} + +export interface W3cJsonLdVerifiablePresentationDto { + proof: any; + context: any[]; + id?: string; + type: string[]; + holder?: any; + verifiableCredential: any; + + [key: string]: any; +} + export interface CredentialFormatDataDto { proposalAttributes?: any[]; offerAttributes?: any[]; @@ -1419,6 +1633,7 @@ export interface CredentialFormatDataDto { anoncredsOffer?: any; anoncredsRequest?: any; anoncredsCredential?: any; + all?: any; [key: string]: any; } @@ -1438,26 +1653,26 @@ export interface MakeBasicMessageRequestDto { } export interface MessageRecordDto { + id?: string; + createdAt?: Date; + updatedAt?: Date; connectionId: string; role: MessageRecordDtoRole; sentTime: string; from?: string; to?: string; content: string; - id?: string; - createdAt?: Date; - updatedAt?: Date; [key: string]: any; } export interface ProofRecordDto { - connectionId?: string; - state: ProofRecordDtoState; - tags: any; id?: string; createdAt?: Date; updatedAt?: Date; + connectionId?: string; + state: ProofRecordDtoState; + tags: any; [key: string]: any; } @@ -1501,13 +1716,13 @@ export interface AcceptProofDto { } export interface DidRecordDto { + id?: string; + createdAt?: Date; + updatedAt?: Date; did: string; role: DidRecordDtoRole; method: string; tags: any; - id?: string; - createdAt?: Date; - updatedAt?: Date; [key: string]: any; } diff --git a/libs/clients/src/ocmengine-client.ts b/libs/clients/src/ocmengine-client.ts index e927c0621a5c4128569631fe8dce585d900c4ce1..42d2f94d0b16386c4a8445314137c4148079ae42 100644 --- a/libs/clients/src/ocmengine-client.ts +++ b/libs/clients/src/ocmengine-client.ts @@ -15,6 +15,10 @@ import { States2, States3, AcceptInvitationRequestDto, + OfferJsonCredentialRequests, + SignJsonCredentialRequests, + CredentialOfferResponseDto, + W3cJsonLdVerifiableCredentialDto, } from "./frontend/agent_gen"; export * from "./frontend/agent_gen"; @@ -102,6 +106,14 @@ class ApiClient { public declineProofRequest = (proof_record_id: string) => this._rest.declineProofRequest(proof_record_id); public resolveDid = (body: IdReqDto) => this._rest.resolveDid(body); + public offerJsonLdCredential = ( + body: OfferJsonCredentialRequests, + ): Promise<CredentialOfferResponseDto> => + this._rest.offerJsonLdCredential(body); + public signJsonLdCredential = ( + body: SignJsonCredentialRequests, + ): Promise<W3cJsonLdVerifiableCredentialDto> => + this._rest.signJsonLdCredential(body); public getCreatedDids = () => this._rest.getCreatedDids(); public initialize() {