示例#1
0
    def _mergeInvitaion(self, invitationData):
        linkInvitation = invitationData.get('link-invitation')
        linkName = linkInvitation['name']
        link = self.wallet.getLink(linkName)
        invitationProofRequests = invitationData.get('proof-requests', None)
        if invitationProofRequests:
            for icr in invitationProofRequests:
                # match is found if name and version are same
                matchedProofRequest = next(
                    (cr for cr in link.proofRequests
                     if (cr.name == icr[NAME] and cr.version == icr[VERSION])),
                    None)

                # if link.requestedProofs contains any claim request
                if matchedProofRequest:
                    # merge 'attributes' and 'verifiableAttributes'
                    matchedProofRequest.attributes = {
                        **matchedProofRequest.attributes,
                        **icr[ATTRIBUTES]
                    }
                    matchedProofRequest.verifiableAttributes = list(
                        set(matchedProofRequest.verifiableAttributes).union(
                            icr[VERIFIABLE_ATTRIBUTES]))
                else:
                    # otherwise append proof request to link
                    link.proofRequests.append(
                        ProofRequest(icr[NAME], icr[VERSION], icr[ATTRIBUTES],
                                     icr[VERIFIABLE_ATTRIBUTES]))

            return link
        else:
            raise LinkAlreadyExists
示例#2
0
    def loadInvitation(self, invitationData):
        linkInvitation = invitationData["link-invitation"]
        remoteIdentifier = linkInvitation[f.IDENTIFIER.nm]
        # TODO signature should be validated!
        signature = invitationData["sig"]
        linkInvitationName = linkInvitation[NAME]
        remoteEndPoint = linkInvitation.get("endpoint", None)
        remote_verkey = linkInvitation.get("verkey", None)
        linkNonce = linkInvitation[NONCE]
        proofRequestsJson = invitationData.get("proof-requests", None)

        proofRequests = []
        if proofRequestsJson:
            for cr in proofRequestsJson:
                proofRequests.append(
                    ProofRequest(cr[NAME], cr[VERSION], cr[ATTRIBUTES],
                                 cr[VERIFIABLE_ATTRIBUTES]))

        self.notifyMsgListener("1 link invitation found for {}.".
                               format(linkInvitationName))

        self.notifyMsgListener("Creating Link for {}.".
                               format(linkInvitationName))
        # TODO: Would we always have a trust anchor corresponding to a link?

        li = Link(name=linkInvitationName,
                  trustAnchor=linkInvitationName,
                  remoteIdentifier=remoteIdentifier,
                  remoteEndPoint=remoteEndPoint,
                  invitationNonce=linkNonce,
                  proofRequests=proofRequests,
                  remote_verkey=remote_verkey)

        self.wallet.addLink(li)
        return li
示例#3
0
    def handleProofRequest(self, msg):
        body, _ = msg
        link = self._getLinkByTarget(getCryptonym(body.get(IDENTIFIER)))
        proofReqName = body.get(NAME)
        proofReqExist = False

        for request in link.proofRequests:
            if request.name == proofReqName:
                proofReqExist = True
                break

        self.notifyMsgListener(
            '    Proof request {} received from {}.\n'.format(
                proofReqName, link.name))

        if not proofReqExist:
            link.proofRequests.append(
                ProofRequest(
                    name=proofReqName,
                    version=body.get(VERSION),
                    attributes=body.get(ATTRIBUTES),
                    verifiableAttributes=body.get(VERIFIABLE_ATTRIBUTES)))
        else:
            self.notifyMsgListener(
                '    Proof request {} already exist.\n'.format(proofReqName))
    def sendProofReq(self, link: Link, proofReqSchemaKey):
        if self._proofRequestsSchema and (proofReqSchemaKey
                                          in self._proofRequestsSchema):
            proofRequest = self._proofRequestsSchema[proofReqSchemaKey]

            proofRequest = ProofRequest(
                proofRequest[NAME], proofRequest[VERSION],
                getNonceForProof(link.invitationNonce),
                proofRequest[ATTRIBUTES], proofRequest[VERIFIABLE_ATTRIBUTES]
                if VERIFIABLE_ATTRIBUTES in proofRequest else [],
                proofRequest[PREDICATES] if PREDICATES in proofRequest else [])

            op = {
                TYPE: PROOF_REQUEST,
                PROOF_REQUEST_FIELD: proofRequest.to_str_dict()
            }

            self.signAndSendToLink(msg=op, linkName=link.name)
        else:
            return ERR_NO_PROOF_REQUEST_SCHEMA_FOUND
示例#5
0
    async def sendProofAsync(self, link: Link, proofRequest: ProofRequest):
        # TODO _F_ this nonce should be from the Proof Request, not from an
        # invitation
        proofInput = ProofInput(
            nonce=proofRequest.nonce,
            revealedAttrs=proofRequest.verifiableAttributes,
            predicates=proofRequest.predicates)
        # TODO rename presentProof to buildProof or generateProof

        proof = await self.prover.presentProof(proofInput)
        proof.requestedProof.self_attested_attrs.update(
            proofRequest.selfAttestedAttrs)

        op = {
            TYPE: PROOF,
            NONCE: link.invitationNonce,
            PROOF_FIELD: proof.to_str_dict(),
            PROOF_REQUEST_FIELD: proofRequest.to_str_dict()
        }

        self.signAndSendToLink(msg=op, linkName=link.name)
示例#6
0
    def handleProofRequest(self, msg):
        body, _ = msg
        link = self._getLinkByTarget(getCryptonym(body.get(IDENTIFIER)))
        proofRequest = body.get(PROOF_REQUEST_FIELD)
        proofRequest = ProofRequest.from_str_dict(proofRequest)
        proofReqExist = False

        for request in link.proofRequests:
            if request.name == proofRequest.name:
                proofReqExist = True
                break

        self.notifyMsgListener(
            '    Proof request {} received from {}.\n'.format(
                proofRequest.name, link.name))

        if not proofReqExist:
            link.proofRequests.append(proofRequest)
        else:
            self.notifyMsgListener(
                '    Proof request {} already exist.\n'.format(
                    proofRequest.name))
    async def verifyProof(self, msg: Any):
        body, (frm, _) = msg
        link = self.verifyAndGetLink(msg)
        if not link:
            raise NotImplementedError

        proof = body[PROOF_FIELD]
        proofRequest = ProofRequest.from_str_dict(body[PROOF_REQUEST_FIELD])
        nonce = getNonceForProof(body[NONCE])
        proofName = proofRequest.name

        proofs = {}

        for key, p in proof['proofs'].items():
            schema = await self.verifier.wallet.getSchema(
                ID(schemaId=int(p['schema_seq_no'])))
            pk = await self.verifier.wallet.getPublicKey(
                ID(schemaKey=schema.getKey()))
            proofs[key] = ProofInfo.from_str_dict(p, str(pk.N))

        proof = FullProof(
            proofs, AggregatedProof.from_str_dict(proof['aggregated_proof']),
            RequestedProof.from_str_dict(proof['requested_proof']))

        proofInput = ProofInput(
            nonce=int(proofRequest.nonce),
            revealedAttrs=proofRequest.verifiableAttributes,
            predicates=proofRequest.predicates)
        result = await self.verifier.verify(proofInput, proof)

        self.logger.info('Proof "{}" accepted with nonce {}'.format(
            proofName, nonce))
        self.logger.info('Verifying proof "{}" from {}'.format(
            proofName, link.name))
        status = 'verified' if result else 'failed verification'
        resp = {
            TYPE:
            PROOF_STATUS,
            DATA:
            '    Your Proof {} {} was received and {}\n'.format(
                proofRequest.name, proofRequest.version, status),
        }
        self.signAndSend(resp,
                         link.localIdentifier,
                         frm,
                         origReqId=body.get(f.REQ_ID.nm))

        if result:
            for uuid, attribute in proofInput.revealedAttrs.items():
                # Log attributes that were verified
                self.logger.info('verified {}: {}'.format(
                    attribute.name,
                    proof.requestedProof.revealed_attrs[uuid][1]))
            self.logger.info(
                'Verified that proof "{}" contains attributes '
                'from claim(s) issued by: {}'.format(
                    proofName, ", ".join(
                        sorted([v.issuer_did
                                for k, v in proof.proofs.items()]))))
            await self._postProofVerif(proofName, link, frm)
        else:
            self.logger.info(
                'Verification failed for proof {} from {} '.format(
                    proofName, link.name))