Skip to content
📋

Ditto Nostr Reference

All Nostr event kinds that Ditto supports, including NIP extensions, community kinds, and Ditto-specific kinds.

For a complete list of all Nostr event kinds, see nostrbook.dev. The protocol is defined by NIPs (Nostr Implementation Possibilities), and community members can share custom NIP proposals on NostrHub.

📦

Supported kinds

Ditto-created kind whimsy
KindNameDescription
0Profile MetadataUser profile information: name, bio, avatar, and more (NIP-01)
1Short Text NoteThe core post type on Nostr (NIP-01)
3Follow ListThe user's list of followed pubkeys (NIP-02)
5DeletionDelete a previously published event (NIP-09)
17External Content ReactionReaction on external content like URLs or ISBNs (NIP-73)
20PhotoPhoto post displayed in the Photos feed (NIP-68)
21VideoVideo post displayed in the Videos feed (NIP-71)
22Short VideoShort-form vertical video, Reels/TikTok-style (NIP-71)
62Request to VanishRequest identity deletion from relays (NIP-62)
1018Poll VoteCast a vote on a kind 1068 poll
1063File MetadataFile metadata for uploads, including Webxdc apps (NIP-94)
1068PollCommunity poll with multiple-choice options
1111CommentThreaded comment on posts and external content (NIP-22)
1222Voice MessageRoot voice message post
1244Voice Message ReplyVoice message reply to a kind 1 note
1311Live Chat MessageChat message in a live stream (NIP-53)
1617PatchGit patch for code review (NIP-34)
1618Pull RequestGit pull request (NIP-34)
1984ReportFlag content or users for moderation
1985Trending LabelsTrending hashtags and posts published by the relay (NIP-32)
3367Color Moment Color palette post expressing a mood
7516Found Log Log entry recording a user finding a geocache
9735Zap ReceiptLightning zap receipt for payments (NIP-57)
10000Mute ListMuted users, threads, and words (NIP-51)
10001Pinned NotesPinned posts displayed on user profiles (NIP-51)
10002Relay ListUser's preferred relays for reading and writing (NIP-65)
10003Bookmark ListBookmarked events (NIP-51)
10015InterestsUser's followed hashtags and interests (NIP-51)
10030Custom Emoji ListUser's preferred custom emoji packs (NIP-30)
10063Blossom Server ListUser's Blossom file upload servers (BUD-03)
10073Read BooksBooks the user has finished reading (Bookstr)
10074Currently ReadingBooks the user is currently reading (Bookstr)
10075To Be ReadBooks the user wants to read (Bookstr)
16767Active Profile ThemeThe user's currently active profile theme
16769Profile TabsCustom profile tab configuration
30000People ListUser-defined lists of people (NIP-51)
30008Profile BadgesBadges a user has accepted and displayed (NIP-58)
30009Badge DefinitionBadge metadata and imagery (NIP-58)
30023ArticleLong-form blog post with Markdown content (NIP-23)
30030Emoji PackCustom emoji pack definition (NIP-30)
30054Podcast EpisodePodcast episode displayed in the Podcasts feed
30055Podcast TrailerPodcast trailer displayed in the Podcasts feed
30063Software ReleaseApp release metadata from Zapstore (NIP-82)
30078App SettingsEncrypted per-user Ditto settings (NIP-78)
30311StreamLive streaming event (NIP-53)
30315User StatusUser status displayed on profiles and posts (NIP-38)
30382User StatsFollower and post counts from the relay stats pubkey (NIP-85)
30383Event StatsEngagement counts for events from the relay stats pubkey (NIP-85)
30384Addressable Event StatsEngagement counts for addressable events (NIP-85)
30617Git RepositoryGit repository or app submission (NIP-34)
30817Custom NIPCustom NIP proposal on NostrHub
31922Date Calendar EventDate-based calendar event (NIP-52)
31923Time Calendar EventTime-based calendar event (NIP-52)
31925Calendar RSVPRSVP response to a calendar event (NIP-52)
31985Book ReviewBook review and rating (Bookstr)
32267AppSoftware application listing from Zapstore (NIP-82)
34139Music PlaylistMusic playlist displayed in the Music feed
34236Vine Short-form video post
34550Community DefinitionCommunity definition (NIP-72)
36767Theme DefinitionShareable custom UI theme with colors, font, and background
36787Music TrackMusic track displayed in the Music feed
37381Magic Deck Magic: The Gathering deck list
37516Geocache Geocache listing for real-world treasure hunting
39089Follow PackCurated follow recommendations (starter packs)

🔷

Avatar Shape

Kind 0 profile metadata (NIP-24) is extended with a shape property. The value is any emoji, which is used as a mask over the user’s avatar to set its shape.

json
{
  "kind": 0,
  "content": "{\"name\":\"alex\",\"picture\":\"https://example.com/avatar.jpg\",\"shape\":\"🔷\"}"
}

A NIP proposal has been submitted to standardize this field.


🎨

Ditto Profile Theme

Replaceable event representing the user’s currently active profile theme. Only one exists per user. When visiting a profile, clients query this kind to determine what theme to display.

The event uses the same c, f, and bg tags as theme definitions. An optional a tag references the source theme definition for attribution.

Event structure

json
{
  "kind": 16767,
  "content": "",
  "tags": [
    ["c", "#1a1a2e", "background"],
    ["c", "#e0e0e0", "text"],
    ["c", "#6c3ce0", "primary"],
    ["f", "Inter", "https://example.com/inter.woff2"],
    ["bg", "url https://example.com/bg.jpg", "mode cover", "m image/jpeg"],
    ["title", "MK Dark Theme"],
    ["a", "36767:<source-author-pubkey>:<source-d-tag>"],
    ["alt", "Active profile theme"]
  ]
}

Content

The content field is unused and MUST be an empty string ("").

Tags

TagRequiredDescription
cYes (x3)Hex color with role marker (same format as kind 36767).
fNoFont declaration.
bgNoBackground media.
titleNoHuman-readable name for the theme.
aNoReference to the source kind 36767 event (kind:pubkey:d-tag). Enables attribution (“Using X’s theme”).
altYesNIP-31 human-readable fallback

Client behavior

  • Query: { kinds: [16767], authors: [<pubkey>], limit: 1 } to get a user’s active theme.
  • Colors: Read the c tags to extract colors, f tags for fonts, and bg tag for the background.
  • Attribution: The a tag lets clients display “Using MK Dark Theme by @mk” with a link to the source theme.
  • Set: Publish a new kind 16767 event to change the active theme (replaces the previous one).
  • Clear: Publish a kind 5 deletion event targeting kind 16767 to remove the active theme.

🖌️

Ditto Theme

Addressable event for publishing shareable custom UI themes. A user can publish multiple themes, each identified by a unique d tag. Colors are stored in c tags, with optional font (f) and background (bg) tags.

Event structure

json
{
  "kind": 36767,
  "content": "",
  "tags": [
    ["d", "mk-dark-theme"],
    ["c", "#1a1a2e", "background"],
    ["c", "#e0e0e0", "text"],
    ["c", "#6c3ce0", "primary"],
    ["f", "Inter", "https://example.com/inter.woff2"],
    ["bg", "url https://example.com/bg.jpg", "mode cover", "m image/jpeg", "dim 1920x1080"],
    ["title", "MK Dark Theme"],
    ["description", "A sleek dark theme with purple and blue accents"],
    ["alt", "Custom theme: MK Dark Theme"],
    ["t", "theme"]
  ]
}

Content

The content field is unused and MUST be an empty string ("").

Tags

TagRequiredDescription
dYesUnique identifier (slug) for this theme
cYes (x3)Hex color with role marker. See Color tags.
fNoFont declaration. See Font tag.
bgNoBackground media. See Background tag.
titleYesHuman-readable theme name
descriptionNoBrief description of the theme
altYesNIP-31 human-readable fallback
tYesSet to "theme" for discoverability

Color tags

Format: ["c", "#rrggbb", "<marker>"]

Each theme requires exactly 3 color tags with these markers:

MarkerDescription
backgroundPage background color
textPrimary text/foreground color
primaryAccent color (buttons, links, focus rings)

Colors are lowercase 6-digit hex codes including the # sign. Clients derive all other UI colors (card, muted, border, etc.) from these 3 values.

Font tag

Format: ["f", "<family>", "<url>"]

Optional. At most one per event. The font applies globally to all text. Variable font files covering multiple weights are preferred.

Background tag

Uses an imeta-style variadic format: ["bg", "url <url>", "mode <mode>", "m <mime-type>", ...]

KeyRequiredDescription
urlYesURL to an image or video file
modeYesDisplay mode: "cover" or "tile"
mYesMIME type (e.g. "image/jpeg", "video/mp4")
dimNoDimensions: "<width>x<height>"
blurhashNoBlurhash placeholder for progressive loading

Multiple themes per user

Since kind 36767 is addressable, a user can publish multiple themes by using different d tag values. Publishing a new event with the same d tag replaces the previous version.


⚙️

Ditto Settings

Ditto stores encrypted per-user settings in a NIP-78 application-specific data event. The d tag is always ditto-metadata and the content is NIP-44 encrypted JSON.

Event structure

json
{
  "kind": 30078,
  "content": "<NIP-44 encrypted JSON>",
  "tags": [
    ["d", "ditto-metadata"],
    ["title", "Ditto Metadata"],
    ["client", "ditto.pub"]
  ]
}

Decrypted content schema

After NIP-44 decryption with the user’s own pubkey, the content is a JSON object with these fields:

FieldTypeDescription
theme"light" | "dark" | "system" | "custom"Active theme mode
customThemeThemeConfigCustom theme configuration with 3 core colors, optional font and background (see Theming)
useAppRelaysbooleanWhether to use Ditto’s default relays alongside the user’s relay list
feedSettingsFeedSettingsToggles controlling which content types appear in the sidebar and feed
contentFiltersContentFilter[]User-defined content filter rules
contentWarningPolicy"blur" | "show" | "hide"How to handle NIP-36 content-warning events
notificationsCursornumberUnix timestamp (seconds) of the last viewed notification
lastSyncnumberTimestamp of the last settings sync (milliseconds)

Example (decrypted)

json
{
  "theme": "dark",
  "customTheme": {
    "colors": {
      "background": "228 20% 10%",
      "text": "210 40% 98%",
      "primary": "258 70% 60%"
    }
  },
  "useAppRelays": true,
  "feedSettings": {
    "feedIncludePosts": true,
    "feedIncludeReposts": true,
    "feedIncludeArticles": true,
    "feedIncludeVines": true,
    "showVines": true,
    "showStreams": true,
    "showPolls": false
  },
  "contentWarningPolicy": "blur",
  "notificationsCursor": 1700000000,
  "lastSync": 1700000000000
}

🔍

Ditto’s relay supports full-text search through NIP-50 with search extensions. The public relay is available at wss://relay.ditto.pub.

Extensions can be combined with each other and with free-text search terms. For example, "search": "bitcoin sort:hot language:en" returns trending English-language posts matching “bitcoin”.

json
{
  "kinds": [1],
  "search": "bitcoin sort:hot language:en",
  "limit": 20
}

Search extensions

Ditto-introduced extension
ExtensionDescription
language:<en/zh/ja/...>Filter events by detected language (NIP-50)
sentiment:<positive/negative/neutral>Filter events by detected sentiment (NIP-50)
protocol:<activitypub/atproto/nostr>Filter by originating protocol (NIP-48). protocol:nostr returns native Nostr events only.
media:<true/false>Filter by presence of media attachments
video:<true/false>Filter by presence of video content
sort:topSort by total engagement (unique engagers). Default when search text is present.
sort:hotSort by engagement weighted with time decay, surfacing what's trending now
sort:controversialSort by controversy score, favoring events with balanced comments and reactions
sort:risingSort by engagement velocity relative to age
sort:zapsSort by total zap amount
sort:newSort chronologically (prevents the default sort:top behavior)
distinct:authorDeduplicate results to one event per author
-<term>Exclude events matching the given term

📊

Stats

Ditto’s relay publishes engagement stats for events using NIP-85 (kind 30383). These are addressable events authored by the relay’s stats pubkey, with the d tag set to the target event’s ID.

The stats pubkey for wss://relay.ditto.pub is:

5f68e85ee174102ca8978eef302129f081f03456c884185d5ec1c1224ab633ea

Event structure

json
{
  "kind": 30383,
  "pubkey": "5f68e85ee174102ca8978eef302129f081f03456c884185d5ec1c1224ab633ea",
  "content": "",
  "tags": [
    ["d", "<target-event-id>"],
    ["k", "1"],
    ["p", "<target-event-pubkey>"],
    ["comment_cnt", "42"],
    ["repost_cnt", "7"],
    ["reaction_cnt", "128"],
    ["zap_cnt", "15"]
  ]
}

Tags

TagDescription
dID of the event being described
kKind of the referenced event
pPubkey of the referenced event’s author
comment_cntNumber of replies/comments
repost_cntNumber of reposts
reaction_cntNumber of reactions
zap_cntNumber of zaps

Filter example

json
{
  "kinds": [30383],
  "authors": ["5f68e85ee174102ca8978eef302129f081f03456c884185d5ec1c1224ab633ea"],
  "#d": ["<target-event-id>"],
  "limit": 1
}

Clients can batch multiple event IDs into a single request by passing an array of IDs in #d.


🔥

Ditto publishes trending data as NIP-32 label events under the pub.ditto.trends namespace. A trusted relay pubkey publishes these periodically.

A label event with l: #t contains the current trending hashtags. Each t tag carries the hashtag name along with engagement counts.

json
{
  "kind": 1985,
  "pubkey": "15b68d319a088a9b0c6853d2232aff0d69c8c58f0dccceabfb9a82bd4fd19c58",
  "content": "",
  "tags": [
    ["L", "pub.ditto.trends"],
    ["l", "#t", "pub.ditto.trends"],
    ["t", "bitcoin", "", "142", "580"],
    ["t", "nostr", "", "98", "312"],
    ["t", "art", "", "67", "201"]
  ]
}

t tag format: ["t", <hashtag>, "", <accounts>, <uses>]

IndexValueDescription
0"t"Tag name
1hashtagThe trending hashtag (lowercased)
2""Reserved (empty)
3accountsNumber of distinct accounts using this hashtag
4usesTotal number of uses

Filter structure

json
{
  "kinds": [1985],
  "authors": ["15b68d319a088a9b0c6853d2232aff0d69c8c58f0dccceabfb9a82bd4fd19c58"],
  "#L": ["pub.ditto.trends"],
  "#l": ["#t"],
  "limit": 1
}