Developer Docs

Argus is a permissionless on-chain RSA public key registry for Starknet. Keys from Google, Apple, and Firebase are registered via Reclaim Protocol zkTLS proofs — no admin, no trust.

Contract Addresses

sepolia

Argus0x07cd8487786091e4a2c1841cad4e16b815d61a068383c2a2b15dcb2415f1d767
JWKSRegistry0x0112c6a8a69e4d9a2e74b4638e1495d69266de9f6f796727d4a52a7ab0a48db2

mainnet

Argus0x00cbcd49655919c0628fd7d999f8aadcb167a0450a75f9dfffef8ad8175f1de4
JWKSRegistry0x076ff6853197538b4d4c925b2c775014fae9b5c14f63262b13f2e49f732e21f7

Class Hash

Latest declared class hash (Argus):

JWKSRegistry:

0x498906ddc9227cb1ed39b55690f6dd481e5c433e806793202a409d1ffba0834

Argus:

0x20396641b648fde866322051fde319af3455aff95a7b2c0e6c05728b621e2fe

JWKSRegistry ABI (relevant entries)

Use is_key_valid to check whether a JWT kid is registered and active on-chain. Use get_key_if_valid to retrieve the full RSA key struct for signature verification in a single call.

[
  {
    "type": "function",
    "name": "is_key_valid",
    "inputs": [{ "name": "kid", "type": "core::felt252" }],
    "outputs": [{ "type": "core::bool" }],
    "state_mutability": "view"
  },
  {
    "type": "function",
    "name": "get_key",
    "inputs": [{ "name": "kid", "type": "core::felt252" }],
    "outputs": [{ "type": "argus::jwks_registry::JWKSKey" }],
    "state_mutability": "view"
  },
  {
    "type": "function",
    "name": "get_key_if_valid",
    "inputs": [{ "name": "kid", "type": "core::felt252" }],
    "outputs": [{ "type": "argus::jwks_registry::JWKSKey" }],
    "state_mutability": "view"
  }
]

Argus ABI (relevant entries)

register_key is permissionless — any account can submit a Reclaim proof to register a new key. The proof is verified on-chain before writing.

[
  {
    "type": "function",
    "name": "register_key",
    "inputs": [
      { "name": "proof", "type": "argus::argus::Proof" },
      { "name": "kid", "type": "core::felt252" },
      { "name": "key", "type": "argus::jwks_registry::JWKSKey" }
    ],
    "outputs": [],
    "state_mutability": "external"
  },
  {
    "type": "function",
    "name": "get_upgrade_admin",
    "inputs": [],
    "outputs": [{ "type": "core::starknet::contract_address::ContractAddress" }],
    "state_mutability": "view"
  }
]

Reading a Key with starknet.js

Hash the JWT header kid field into a felt252 with Starknet's ByteArray Poseidon encoding, then call is_key_valid on the JWKSRegistry contract.

import { CallData, Contract, RpcProvider, byteArray, hash } from 'starknet';

// Hash a kid string to a felt252-compatible registry key
function kidToFelt(kid: string): string {
  return hash.computePoseidonHashOnElements(
    CallData.compile(byteArray.byteArrayFromString(kid))
  );
}

const provider = new RpcProvider({
  nodeUrl: 'https://free-rpc.nethermind.io/mainnet-juno/v0_7',
});

const contract = new Contract(
  [/* minimal ABI with is_key_valid */],
  '0x076ff6853197538b4d4c925b2c775014fae9b5c14f63262b13f2e49f732e21f7',
  provider,
);

// Check if a Google kid is registered on Mainnet
const kid = 'a3b1...'; // from jwt header
const isValid = await contract.is_key_valid(kidToFelt(kid));
console.log(isValid ? 'Key is active on-chain' : 'Key not registered');

JWKS Endpoints

ProviderJWKS URLOn-chain label
Googlehttps://www.googleapis.com/oauth2/v3/certs0x676f6f676c65
Applehttps://appleid.apple.com/auth/keys0x6170706c65
Firebasehttps://cavos.xyz/.well-known/jwks.json0x6669726562617365

Security Model

Argus verifies every key submission end-to-end on-chain, with no trusted intermediary:

  • Provider identity — verified by Poseidon hash of the JWKS endpoint URL extracted from the Reclaim proof parameters. The URL never changes; only hardcoded endpoints are accepted.
  • kid and RSA modulus n — parsed from the proof context and compared against the submitted key.
  • zkTLS proof — Reclaim Protocol cryptographically attests that the JWKS response was fetched over TLS from the declared URL.

Source Code

The Cairo contracts and this website are open source.

GitHub →