Title: ERC_7920__Composite_EIP_712_Signatures
Category: ERCs

Author: ogunsakin
Date: 2025-03-25T17:35:26.519Z

erc-7920577×360 35.9 KB
Pull Request


github.com/ethereum/ERCs








Add ERC: Composite EIP-712 Signatures


master ← sola92:master



          opened 05:03PM - 25 Mar 25 UTC




            sola92
          



+1057
-0






This EIP provides a standard for signing multiple typed-data messages with a sin…gle signature by encoding them into a Merkle tree. Allowing individual messages to be verified without requiring full knowledge of the others.

![eip-tbd](https://github.com/user-attachments/assets/8b73583d-3416-471c-ae4a-b4ce26176f80)






Reference Implementation


github.com




GitHub - sola92/composite-712: Reference implementation and tests for Composite...
Reference implementation and tests for Composite EIP-712 messages

Author: hellohanchen
Date: 2025-04-01T06:58:54.816Z

Very interesting proposal!
Can the data be composite at multiple layers, like [[x₁, x₂, ..., xₙ], [y₁, y₂, ..., yₙ]]?
And what’s the actual gas cost for a specific number of messages (n)?

Author: ogunsakin
Date: 2025-04-01T08:29:35.319Z

@hellohanchen thanks for the review!
Currently the messages must be flattened for signature: [x₁, x₂, ..., xₙ].
Gas cost for verification? Thats a good question I can run a test to find out. Runtime should be log(n) number of messages, if the tree is properly constructed.

Author: hellohanchen
Date: 2025-04-01T08:46:17.110Z

Thanks for replying. I currently don’t have a great use case for this but this is interesting. Signature and validation work should become more flexible to prepare for the future use cases.
I do have some use cases that the signatures need to be layered like
sig1 = sign(message, key_1)
sig2 = sign(sig1, key_2)

And both signatures need to be verified.

Author: dror
Date: 2025-05-06T08:28:27.235Z

Nice idea…
I noticed that signTypedData has a “backward compatibility”, to return a single result.
however, the sample solidity code only uses a merkle-proof, and doesn’t work with a single-entry proof returned by signTypedData_v5

Author: ogunsakin
Date: 2025-05-07T13:12:30.475Z

Hi @dror, thanks for reviewing.
The proposed schema for signedTypedData_v5 result is:
{
  signature: `0x${string}`; // Hex encoded 65 byte signature 
  merkleRoot: `0x${string}`; // 32 byte Merkle root as hex string
  proofs: Array<Array<`0x${string}`>>; // Array of Merkle proofs (one for each input message)
}

When N=1, the derivation path is an empty array as the sole message is root and signedTypedData_v5 returns:
{
  signature: `<< sign(keccak256(encode(m))) >>`;
  merkleRoot: `<< keccak256(encode(m)) >>`;
  proofs: [
   []
  ]
}

During verification
_verifyMerkleProof(N=1) = root == leaf
Simplifying check to
isVerified = isValidSignature && root == leaf

Here is a unit test for this case: ERCs/assets/erc-7920/test/solidity.test.ts at 5580d029fc43c7cffb1300788fe5db0bc7f386eb · ethereum/ERCs · GitHub

Author: dror
Date: 2025-05-07T14:42:46.996Z

ok, so just to verify:
I can take a “standard” signTypedData result, and pass it as “root” with an empty merkle proof, and it will succeed. right ?

Author: ogunsakin
Date: 2025-05-07T14:59:42.549Z

Hi @dror, here’s what verification would look like with a signedTypedData_v4 result
isVerified = isValidSignature(fullSig) && _verifyMerkleProof(messageHash, [], messageHash)

This would always evaluate as true
_verifyMerkleProof(messageHash, [], messageHash)

Leaving
isVerified = isValidSignature(fullSig)