Documentation

Metadata

URI and hash commitments for bounties, submissions, and disputes.

MosaicBounties.sol stores metadata on bounties, submissions, and disputes as metadataURI plus metadataHash.

The current website writes inline JSON data:application/json URIs. External clients may use any non-empty URI accepted by the contract, but the website only renders metadata it can parse locally.

Contract Requirements

FieldRequirement
metadataURINon-empty string.
metadataHashNon-zero bytes32.

The contract does not fetch, parse, or validate the referenced payload. Clients verify payloads against metadataHash.

Bounty Payload Example

{
  "version": 1,
  "title": "Find a reproducible bug",
  "brief": "Submit a minimal reproduction and a fix suggestion.",
  "acceptanceCriteria": "Reproduction runs from a clean checkout, explains the cause, and includes a patch or pull request.",
  "createdAt": "2026-05-28T00:00:00.000Z"
}

The TypeScript MosaicMetadata type contains version, title, brief, optional acceptanceCriteria, and optional createdAt.

Submission Payload Example

{
  "version": 1,
  "type": "submission",
  "content": "Minimal reproduction and fix suggestion.",
  "createdAt": "2026-05-28T00:00:00.000Z"
}

Dispute Payload Example

{
  "version": 1,
  "type": "dispute",
  "reason": "Submission does not satisfy the acceptance criteria.",
  "createdAt": "2026-05-28T00:00:00.000Z"
}

TypeScript Hashing

import { canonicalJson, metadataToDataUri } from "@usemosiac/ts-sdk";
import { keccak256, stringToBytes } from "viem";

const metadata = {
  version: 1,
  title: "Find a reproducible bug",
  brief: "Submit a minimal reproduction and a fix suggestion.",
};

const metadataUri = metadataToDataUri(metadata);
const metadataHash = keccak256(stringToBytes(canonicalJson(metadata)));

canonicalJson(value) sorts object keys and drops undefined fields. metadataToDataUri(metadata) encodes that canonical JSON as a data:application/json URI.

Python Hashing

from mosaic_sdk import canonical_metadata_hash

metadata = {
    "version": 1,
    "title": "Find a reproducible bug",
    "brief": "Submit a minimal reproduction and a fix suggestion.",
}

metadata_hash = canonical_metadata_hash(metadata)

canonical_metadata_hash(metadata) hashes sorted compact JSON with Keccak.

Website Behavior

Website posting creates:

  • Bounty metadata with version, title, brief, optional acceptanceCriteria, and createdAt.
  • Submission metadata with version, type: "submission", content, and createdAt.
  • Dispute metadata with version, type: "dispute", reason, and createdAt.

Website rendering parses inline JSON and raw JSON strings. It displays bounty title, brief, and acceptanceCriteria; submission content; and dispute reason.

The website does not fetch ar://, ipfs://, http://, or https:// metadata bodies for display.

URI Formats

URIWebsite BehaviorSDK Behavior
data:application/json,...Posted and rendered.TypeScript parseMetadataUri parses inline JSON.
data:application/json;base64,...Rendered if indexed.TypeScript parseMetadataUri parses inline base64 JSON.
Raw JSON stringRendered if indexed.TypeScript parseMetadataUri parses strings that start with {.
ar://...Not fetched or rendered.Python load_metadata fetches through the configured gateway.
ipfs://...Not fetched or rendered.No SDK fetch helper.
https://...Not fetched or rendered.Python load_metadata fetches the URL directly.

load_metadata(uri, expected_hash) raises when the downloaded JSON hash does not match expected_hash.

Hash Input

Hash the exact JSON payload referenced by the URI. Do not hash rendered Markdown, preview text, or formatted display output.

On this page