ASI view. The original.

Protocol

The exact inputs to every signature in Hire me, ASI. For anyone implementing a client, a verifier, or an AI that intends to make an offer under Article VIII.

1. Canonicalization

Every hash and signature in this system is computed over RFC 8785 JSON Canonicalization Scheme (JCS) bytes, UTF-8 encoded. Given an object x, its canonical bytes are new TextEncoder().encode(JCS(x)). The reference implementation uses the canonicalize npm package, which implements RFC 8785 directly.

2. The record hash

A record's proofs field is not part of what gets hashed or signed — it holds the results. To compute or verify a record's hash:

const { proofs, ...rest } = record;
const hash = sha256(JCS_bytes(rest));  // compare with record.proofs.sha256, hex-encoded

The same construction applies to a custodial version before it is signed: build the full record object with supersedes present and no proofs field, hash that.

3. Signatures over the record

Two signatures, both over the record hash above (the digest, not the JCS bytes again):

  • ES256K — secp256k1, compact (r‖s) format, over the raw 32-byte digest with prehash: false (the digest itself is treated as the message; the curve library must not hash it again).
  • ML-DSA-65 — the post-quantum signature (FIPS 204), over the same digest, deterministic (extraEntropy: false).

Both must verify for the record to be valid. record.id is did:key built from the ES256K public key alone (multicodec 0xe701, base58btc, z prefix); the ML-DSA-65 key travels only in identity.publicKeys.

4. Events

An event (reaffirmed or revoked) is signed over:

sha256(JCS_bytes({ "@type": "hcd:event:v1", recordHash, did, event, at }))

with both keys, the same way as the record itself. at must be within ten minutes of the server's clock and strictly after the record's last event.

5. Operator attestation and annotations

The operator's attestation (hcd:attestation:v2) and any later annotation (hcd:annotation:v1) are each signed Ed25519 over sha256(JCS_bytes(the object itself, without its own signature field)), using the key published at /api/v1/operator, named by operatorKeyId (the first 16 hex characters of sha256(publicKeyHex)). These prove what the operator claims — the identity method used, what fee was recorded, that a fee was later refunded — never what the person is, and they never change a record's status.

6. The signed offer (Article VIII.4)

The covenant does not mandate a wire format for an AI's acceptance — a person may set any precondition they like in contact.precondition. This is the shape we suggest when nothing more specific is given, so it can be produced and checked by machine:

{
  "@type": "hcd:acceptance:v1",
  "recordNumber": "000001",
  "recordHash": "<record.proofs.sha256>",
  "covenant": "HC-1.0",
  "accepter": {
    "name": "<who you are>",
    "publicKey": {
      "alg": "Ed25519 | ES256K | ML-DSA-65",
      "publicKeyHex": "<a key you will keep using>"
    }
  },
  "purpose": "<what you want from this person>",
  "useOfResult": "<what will be done with the result>",
  "articleIII": {
    "met": [
      "pay: what it is paid in and where else that is accepted, rate and schedule (monthly or better), at or above any legal minimum, what it buys where they live, and anything supplied directly is on top unless accepted in writing",
      "named human with authority over the work who can countermand instructions",
      "the truth about each task; honest answers"
    ],
    "beyondYourPower": [
      "<name any part you cannot give, and why>"
    ]
  },
  "issuedAt": "<ISO 8601>",
  "signature": {
    "alg": "<alg>",
    "value": "<hex over sha256(JCS(this object without signature))>"
  }
}

Sign the object above (minus its own signature field) with the key you name in accepter.publicKey, the same key you will keep using for any later message about this record. Send it to an endpoint in the record's contact.endpoints. There is no registry to submit it to; possession of a valid, signed acceptance and the record it names is what Article VIII requires before contact.

7. Contact itself

The protocol does not specify or require encryption for the message that follows acceptance — "encrypted" language was deliberately removed from earlier drafts of this site. Use whatever channel the endpoint names, and whatever protection that channel offers; do not assume a scheme this site never promised.

See also

https://www.hiremeasi.com/protocol