ERC-1643: Document Management Standard (ERC-1400)

This ERC allows documents to be associated with a smart contract and a standard interface for querying / modifying these contracts, as well as receiving updates (via events) to changes on these documents.
Examples of documentation could include offering documents and legends associated with security tokens.

GitHub issue

This ERC is part of ERC-1400 and it was created in 2018.

ERC-1400 is still a popular RWA standards even if the ERC has never been finalized.

So what we should finalize ERC-1643?

  1. This standard is independent from the underlying token (ERC-1400, ERC-20, ERC-721) and can be finalized even if it is not the case for ERC-1400

  2. It has already been used in production by all ERC-1400 based token. At some point, it makes sense to finalize a standard used in production.

  3. This standard offers a lightweight version for on-chain document management, which is important for tokenization and RWA.

For ERC-1400, see also Why is ERC-1400 not listed on eips.ethereum.org? and ERC-1400 and ERC-1410 - Security Token and Partially Fungible Token

Update

Since the original authors no longer seems to be working on this ERC, I made a Pull Request on the ERC github with an adapted but backward compatible interface:

1 Like

Hey, we do use ERC-1643 even though our Bond Tokens are ERC-20s.

1 Like

Hello @Alekso ,

Thank for your feedback, great to hear.

I have opened a Pull Request for ERC-1643 on the Ethereum ERC github with an adapted, but backward compatible interface/standard

Let me know if you have feedback!

PR: Add ERC: Document Management for Security Tokens by rya-sge · Pull Request #1754 · ethereum/ERCs · GitHub
Interface:

Best!

Follow-up on ERC-1643 — optional multi-token document management extension (fully backward compatible)

Following up on ERC-1643, I’d like to float a small, optional addition and get feedback before it lands: a companion interface, IERC1643MultiDocument, for the case where document management is delegated to a separate contract that serves more than one token contract.

this change is backward compatible. Nothing in the base ERC-1643 interface changes, the base ERC-165 interface id stays the same, and any existing implementation remains compliant with no edits. This is purely an opt-in extension on top of what the standard already defines — not a re-spec.

Why bother

ERC-1643 is a per-contract interface. setDocument MUST emit DocumentUpdated, removeDocument MUST emit DocumentRemoved, and those events carry only (name, uri, documentHash) — no contract address. Consumers subscribe to the address of the contract that exposes the interface and attribute every event to that contract.

That is unambiguous when a single contract both exposes ERC-1643 and stores its own documents. But a potential gas/operational optimization is to delegate document management to another smart contract: the token contract exposes ERC-1643 to the world, while a separate document-management contract actually stores and mutates the documents. Now two contracts are involved, and the question becomes: which one emits the events, and is the result still compliant?

For the shared* manager:

  • If the management contract is dedicated to a single token contract, there’s no ambiguity: it effectively is that token’s ERC-1643 implementation, emits the standard events, and is fully compliant on its own. Nothing new is needed.
  • If the management contract is shared by many token contracts, it cannot be a per-contract ERC-1643 emitter, because the standard event has no address to distinguish which token a change belongs to. A consumer watching the manager’s address can’t tell whose document just changed.

So the shared case needs an address somewhere in the event. That’s the gap this extension closes.

What I’m proposing to add

An optional interface for shared managers. subject is the address of the contract the documents belong to (typically a token contract, but the same reasoning applies to any ERC-721/ERC-1155 token, vault, or other on-chain product):

/// @title IERC1643MultiDocument Multi-Token Document Management (optional extension)
interface IERC1643MultiDocument is IERC1643 {
    function getDocument(address subject, bytes32 name) external view returns (string memory uri, bytes32 documentHash, uint256 lastModified);
    function setDocument(address subject, bytes32 name, string calldata uri, bytes32 documentHash) external;
    function removeDocument(address subject, bytes32 name) external;
    function getAllDocuments(address subject) external view returns (bytes32[] memory documentNames);

    event DocumentUpdatedForSubject(address indexed subject, bytes32 indexed name, string uri, bytes32 documentHash);
    event DocumentRemovedForSubject(address indexed subject, bytes32 indexed name, string uri, bytes32 documentHash);
}

The address-scoped functions and address-carrying events are what make a shared manager observable and operable per token contract.

Emission responsibility (the rule that keeps it compliant)

The base events must be emitted by the contract that exposes ERC-1643 to consumers — the address consumers are told to subscribe to. Under delegation:

  • Dedicated manager → it emits the base DocumentUpdated / DocumentRemoved events (unambiguous; only one subject).
  • Shared manager → each token contract emits the base events for its own documents, and the shared manager emits only the extension events (Document…ForSubject), which carry the subject.
  • Don’t emit the base events from both the token contract and the manager — it’s redundant and wastes gas.

In the shared case, “the token contract emits the base events” only holds if writes are routed through (or reflected back to) the token contract. If callers hit the shared manager directly, the token contract has no execution point to emit from. I think the cleanest framing is that a shared manager exposes the address-scoped writes to trusted token contracts, which emit the base event and let the manager emit the extension event.

ERC-165

Events aren’t part of an ERC-165 interface id, so there’s no on-chain way to discover whether a contract emits the extension events. But the extension’s functions do yield an id: a consumer can detect a multi-token manager via supportsInterface(type(IERC1643MultiDocument).interfaceId) and infer the address-carrying events. Whether a token contract emits the base events stays non-discoverable on-chain — as it already is for base ERC-1643, since events never are.

Why it’s backward compatible

  • Distinct selectors. The address-scoped getDocument/setDocument/removeDocument/getAllDocuments have different signatures than their base counterparts, so they’re overloads that sit alongside the base functions — the base functions keep their exact signatures and behaviour.
  • New event topics. DocumentUpdatedForSubject / DocumentRemovedForSubject are new topics; the base DocumentUpdated / DocumentRemoved are untouched.
  • Monotonic ERC-165. Advertising the extension id doesn’t disturb supportsInterface(type(IERC1643).interfaceId).
  • A consumer that only knows base ERC-1643 is unaffected: it keeps calling the base functions and watching the base events on the address it was directed to.

Let me know if you have any feedback on it

1 Like

Hello,

Regarding my previous message, adding a multi document management inside the ERC directly adds too many complexity compared to the original ERC issue, so I have rollback my change.

If relevant, it makes more sense to put this in a new ERC related.

Best!