{"record":{"id":"684c9477624d838d","repo":"micro/go-micro","slug":"ap2-mandate-signature-verification-failed","errorCode":null,"errorMessage":"ap2: mandate signature verification failed","messagePattern":"ap2: mandate signature verification failed","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"gateway/a2a/ap2.go","lineNumber":94,"sourceCode":"\tpayload, err := ap2Payload(m)\n\tif err != nil {\n\t\treturn AP2SignedMandate{}, err\n\t}\n\treturn AP2SignedMandate{Mandate: m, KeyID: keyID, Signature: base64.RawURLEncoding.EncodeToString(ed25519.Sign(private, payload))}, nil\n}\n\n// VerifyAP2Mandate verifies a signed mandate credential.\nfunc VerifyAP2Mandate(s AP2SignedMandate, public ed25519.PublicKey) error {\n\tsig, err := base64.RawURLEncoding.DecodeString(s.Signature)\n\tif err != nil {\n\t\treturn fmt.Errorf(\"ap2: invalid signature encoding: %w\", err)\n\t}\n\tpayload, err := ap2Payload(s.Mandate)\n\tif err != nil {\n\t\treturn err\n\t}\n\tif !ed25519.Verify(public, payload, sig) {\n\t\treturn errors.New(\"ap2: mandate signature verification failed\")\n\t}\n\treturn nil\n}\n\n// AP2BindMandateToMessage returns a copy of m bound to the A2A message's task/context.\nfunc AP2BindMandateToMessage(m AP2Mandate, msg Message) AP2Mandate {\n\tm.TaskID = msg.TaskID\n\tm.ContextID = msg.ContextID\n\treturn m\n}\n\n// AP2AttachMandate returns a copy of msg carrying the signed AP2 mandate.\nfunc AP2AttachMandate(msg Message, mandate AP2SignedMandate) Message {\n\tmsg.AP2Mandates = append(append([]AP2SignedMandate{}, msg.AP2Mandates...), mandate)\n\treturn msg\n}\n\n// VerifyAP2ForTask verifies signature, task binding, and optional settlement rail reference.","sourceCodeStart":76,"sourceCodeEnd":112,"githubUrl":"https://github.com/micro/go-micro/blob/24529f140421a11a33b6999ab7944f2021cfd69c/gateway/a2a/ap2.go#L76-L112","documentation":"VerifyAP2Mandate recomputes the canonical payload from the mandate and checks its Ed25519 signature with the supplied public key. This error is returned when ed25519.Verify fails, meaning the signature does not match the payload bytes — the credential is unauthenticated or has been altered in transit.","triggerScenarios":"Calling VerifyAP2Mandate with a signed mandate whose signature was computed over a different payload: the mandate was modified after signing, the wrong public key is used, or the payload serialization (ap2Payload) differs between signer and verifier.","commonSituations":"A tampered mandate passing through an untrusted intermediary; key rotation where the verifier holds the old public key; rebinding a mandate to a different A2A task/message after signing; version mismatches in payload canonicalization between services.","solutions":["Ensure the mandate is not modified between SignAP2Mandate and VerifyAP2Mandate; re-sign if any field (including bound task/context) changes.","Verify you are using the public key corresponding to the keyID the mandate was signed with (check key rotation/lookup).","Confirm both sides run compatible versions of the ap2Payload canonicalization code.","Treat verification failure as a security event: reject the credential and log/alert rather than retrying blindly."],"exampleFix":"// before\n// mandate fields mutated after signing\nm.Priority = \"high\"\nerr := ap2.VerifyAP2Mandate(signed, pub) // fails\n\n// after\nerr := ap2.VerifyAP2Mandate(signed, pub)\nif err != nil {\n\treturn fmt.Errorf(\"rejecting unverified mandate: %w\", err)\n}","handlingStrategy":"try-catch","validationCode":null,"typeGuard":null,"tryCatchPattern":"if err := ap2.VerifyAP2Mandate(signed, pub); err != nil {\n\tif strings.Contains(err.Error(), \"signature verification failed\") {\n\t\t// reject credential, log security event, do not retry\n\t\treturn ErrUntrustedMandate\n\t}\n\treturn err\n}","preventionTips":["Never mutate a mandate after signing; bind to task/message before signing (AP2BindMandateToMessage).","Resolve the public key via the mandate's keyID and keep key-rotation lookups current.","Keep signer and verifier on the same version of the payload canonicalization code.","Log verification failures with keyID and mandate ID for security auditing."],"tags":["ap2","signature","ed25519","security","tampering"],"backgroundTag":"signature-verification-failed","analyzedSha":"24529f140421a11a33b6999ab7944f2021cfd69c","analyzedAt":"2026-09-01T02:52:24.923Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T05:18:18.240Z"}