Charisma Metadata
A dead-simple JSON host for fungible-token and NFT metadata on the Stacks blockchain. No IPFS pinning, no SQL—just flat files served from our CDN.
Why Charisma Metadata?
- Flat-file speed→ served straight from edge storage.
- Wallet-signed writes→ only the contract owner can mutate records.
- Schema-light→ any JSON keys are accepted; we surface common ones in UI.
- No gas→ metadata lives off-chain; your on-chain contract stores only a URL.
Quick-start
- Connect your wallet in the Token Dashboard.
- Create or select a token entry.
- Edit the JSON; press Save → sign the message.
- Your metadata is now reachable at
/api/v1/metadata/<contractId>
Metadata Schema
We store raw JSON. Two informal shapes are recognised for nicer UI:
Fungible Token (FT)
{
"name": "B-CHA LP Token",
"symbol": "B-CHA-LP",
"decimals": 6,
"identifier": "B-CHA-LP",
"description": "Liquidity pool token for the B-CHA pair",
"image": "https://kghatiwehgh3dclz.public.blob.vercel-storage.com/SP2ZNGJ85ENDY6...",
"properties": {
"tokenAContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.beri",
"tokenBContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.charisma-token",
"swapFeePercent": 1
}
}
NFT
{
"name": "Wizard #123",
"symbol": "WZRD",
"description": "Hand-drawn pixel wizard.",
"image": "ipfs://bafy.../wizard-123.png",
"attributes": [
{ "trait_type": "Hat", "value": "Moonstone" },
{ "trait_type": "Staff", "value": "Oak" }
]
}
REST API
Base URL : https://charisma.app/api/v1/metadata/{contractId}
Method | Purpose | Headers |
---|---|---|
GET | Fetch metadata JSON | None |
POST | Create / replace JSON | x-signature , x-public-key or x-api-key |
DELETE | Delete record | x-signature , x-public-key |
Example POST (with Signature)
curl -X POST https://charisma.app/api/v1/metadata/SP2...XYZ.stkr -H 'content-type: application/json' -H 'x-signature: SIGNATURE' -H 'x-public-key: PUBKEY' --data '
{
"name": "B-CHA LP Token",
"symbol": "B-CHA-LP",
"decimals": 6,
"identifier": "B-CHA-LP",
"description": "Liquidity pool token for the B-CHA pair",
"image": "https://kghatiwehgh3dclz.public.blob.vercel-storage.com/SP2ZNGJ85ENDY6...",
"properties": {
"tokenAContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.beri",
"tokenBContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.charisma-token",
"swapFeePercent": 1
}
}'
Example POST (with API Key)
curl -X POST https://charisma.app/api/v1/metadata/SP2...XYZ.stkr -H 'content-type: application/json' -H 'x-api-key: YOUR_API_KEY' --data '
{
"name": "B-CHA LP Token",
"symbol": "B-CHA-LP",
"decimals": 6,
"identifier": "B-CHA-LP",
"description": "Liquidity pool token for the B-CHA pair",
"image": "https://kghatiwehgh3dclz.public.blob.vercel-storage.com/SP2ZNGJ85ENDY6...",
"properties": {
"tokenAContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.beri",
"tokenBContract": "SP2ZNGJ85ENDY6QRHQ5P2D4FXKGZWCKTB2T0Z55KS.charisma-token",
"swapFeePercent": 1
}
}'
Example GET
curl https://charisma.app/api/v1/metadata/SP2...XYZ.stkr
Signature Security
Every mutating request (POST, DELETE) must be authenticated. There are two methods:
1. Wallet Signature (Preferred for dApp Integrations)
Include an x-signature
header—an RSV signature of the contractId string—plus x-public-key
. On the server we:
- Verify the signature.
- Derive the Stacks address from the public key.
- Ensure it matches the contract address (
SP…
prefix before the dot).
If any step fails → 401 Unauthorized
.
2. API Key (Convenient for Server-to-Server)
Alternatively, for POST requests, you can use an API key. Include an x-api-key
header with your provisioned API key. If this header is present and the key is valid, the signature and ownership verification steps are bypassed. This method is useful for backend services or scripts where managing wallet signatures is cumbersome. The API key is configured via the METADATA_API_KEY
environment variable on the server.
Tips & Limits
- Max body size: 32 KB
- Images: uploaded and hosted directly by this app—no need for external hosting.
- Write cache: propagation to edge nodes ≤ 2 seconds.
- Versioning: coming soon (immutable URL per commit).