Nostrautica docs

Nostrautica — Event Organizer Guide

Nostrautica is an event app built around one idea: the point of your event is who meets whom. Attendees record short intro videos; an optional AI coordinator analyzes them and tells every attendee who they should talk to and why. This guide takes you from nothing to a running event.

What you'll do

  1. Create your identity (once).
  2. Create the event — optionally attaching an AI coordinator right there, or later.
  3. Share the event — open link, invite codes, or both.
  4. Approve attendees (or let invite codes auto-approve them).
  5. Post updates, customize your event page, and run the event.

Everything runs in your browser. There is no server to set up — the app stores event data, encrypted, on the open Nostr network. Your browser holds the event's keys, so use one browser you'll keep (and back up your identity when prompted).

A note on how the app is laid out. Once you're inside an event, the bottom bar is event-scopedOverview, People, Matches, Updates, and More all act on the event you're in, with a compact header showing the event's name and your status. Two further tabs, Talks and Chat, appear only when you've turned those features on (§6.5), for you and for attendees. Your global stuff (all your events, messages, settings, your identity) lives under More. As the organizer you also get Manage event in that menu, which opens the admin console described in §3.

1. Create your identity

Open the app. On the welcome screen, type your name and tap Create my identity (you can add a photo too). No email, no password — the account is created instantly. If you already use Nostr, tap Already on Nostr? Sign in and use your key, browser extension, or remote signer instead.

Tip: you don't have to do this as a separate step — if you go straight to creating an event while logged out, the app makes your organizer identity as part of the same submit.

When your identity is created you'll be shown a backup card. Do it now: tap Copy my secret key and paste it somewhere safe (a password manager). Anyone with that key is you; without it, a lost browser profile means a lost event. "More ways to back up" offers an emailed recovery link or a password-protected file.

Key backup cardKey backup card

2. Create the event

Choose Create an event and fill in the form:

Event creation formEvent creation form

Event language

Pick the language your event runs in. Start typing to search — by language name in your own language or by its two-letter code (type "slov" or "sk" to find Slovak). Your own language, the ones your browser prefers, and English/Slovak/ Czech are pinned to the top; everything else follows alphabetically.

Choosing the event languageChoosing the event language

The language does three things. It sets the default interface language for attendees who open your event (they can still switch it in Settings). It sets the language the AI writes in: match reasoning and profile summaries are always in your event language, no matter what language each attendee actually speaks or records in — someone can record their intro in English at a Slovak event and everyone still reads why-you-should-meet-them in Slovak. And when an attendee writes their bio in a different language, the coordinator publishes a translation into your event language so the rest of the room can read it — the person's original text is always kept and shown too. English is the default; leave it as-is for an English event.

(You never have to re-run anything for this: when an attendee updates their intro, the system automatically recomputes only the matches that person is part of.)

Note the copy under the form: key rotation is forward-only — revoking someone (§4) protects future content, not what they've already seen. Configure a retention window in Admin → Settings → Delete member data after the event (a number of days, or blank to keep it indefinitely) — attendees see the declared period at join, and once it passes the coordinator cleans up its own copies too, not just the published records. It's a real cleanup, not an absolute guarantee that every last copy is gone everywhere (relay deletion is best-effort, and backups are a separate matter) — see Encryption & Privacy for the exact limits.

After creating, you get a shareable link, a next-steps checklist, and a receipt — each publishing step reported independently, so a partial failure is obvious and retryable instead of silently missing:

Event created — share link and checklistEvent created — share link and checklist

The event itself always succeeds if you got this far. Two secondary steps can fail independently on a bad connection — enrolling you as a participant, and sending the coordinator its install grant if you picked one on the form — and each gets its own Retry button right in the receipt rather than forcing you to redo the whole form. A third line, backup pending, just means you haven't saved your key yet (see step 1) — it isn't an error.

Running this event again next month? Once it exists, open it and use Duplicate event from the event menu: a fresh Create form pre-filled from this one's title, description, images, language, and settings (title becomes "Copy of …") — you still review and submit it, and it becomes a brand-new event with its own keys and an empty roster, not a copy of the data.

3. Open the admin screen and share

Tap Open organizer admin (also reachable any time from More → Manage event). Your control panel is split into two tabs, so running the event day to day never means scrolling past one-time setup:

Fresh event, no requests yet:

Admin overview, Administration tabAdmin overview, Administration tab

The overview strip

At the top of Administration, before any per-person detail, a compact overview puts the state of the whole event in one glance: pending / approved / no-intro counts, whether matching, the coordinator, and billing are healthy, and anything that actually needs your attention (failed jobs, talks awaiting review) surfaced above the routine detail rather than buried in it. Below it, a search box and filter narrow both the join-request queue and the approved list at once — by name, or by status (pending, approved, no intro, processing failed, talk submitted) — so a 200-person event doesn't mean scrolling to find the one person who emailed you:

Organizer admin overviewOrganizer admin overview

Tap anyone's row to open a detail drawer — their submitted profile, media, and operational history (coordinator status, submitted talks) — without leaving the list.

You have three kinds of links to share:

Generated invite codes with QRGenerated invite codes with QR

More than a handful of codes gets tedious to hand out one link at a time — Copy all / Download grab every generated link as plain text for a mail-merge, and Print invite sheet lays out one QR per code, several to a page, ready to cut up and hand out at the door.

Shared entry code — one QR for the roomShared entry code — one QR for the room

4. Approve attendees

Join requests appear in the Join requests section — each shows the person's name, a short id, their skills, an invite badge if they used a code, and a 🎥 badge if they've recorded an intro. The "N pending requests ↓" button at the top jumps you there.

Pending join requestsPending join requests

Tap Approve on the people you want in one at a time, or Approve all (N) to work through everyone waiting. Bulk approval reports each person's outcome individually — queued → publishing → confirmed, or failed — so one person's flaky connection never hides whether the other nine went through; a summary line ("N approved, M need retry") wraps it up, and any failure gets its own Retry rather than making you redo the batch.

Not everyone waiting needs a yes-or-no right now: Reject hides a request locally (the attendee isn't notified, and it's undoable from a small "N rejected" strip), and Leave pending just marks it reviewed without committing either way — both are local bookkeeping for you, not protocol actions, so they're free to change your mind about later.

Approved people move to the Approved section. Each approved card has Re-process (re-publishes their directory entry / recomputes their matches) and Revoke.

Approved attendeesApproved attendees

Approved attendees get access to the encrypted roster, other people's intro videos, and (with a coordinator) their matches. Approving someone works the same whether or not a coordinator is attached; attaching one (§5) is still worthwhile for auto-approval and matches, just no longer required to make manual approval work.

Removing someone

Tap Revoke on an approved card. You'll get a confirmation explaining the consequence:

"Revoke {name}? They lose access to everything new. What they already saw can't be taken back."

Confirming rotates the event key for everyone else automatically, so the revoked person can't decrypt anything published from that point on. What they already saw can't be unseen — revoke early if in doubt.

Approved card with the Revoke actionApproved card with the Revoke action

5. Attach the AI coordinator (matchmaking)

The coordinator is a small service that transcribes intro videos, builds a profile of each attendee, and computes who should meet whom. Without it, the event still fully works — roster, videos, follows — there are just no automatic matches, and invite links need your manual approval.

You can pick one right on the create form (§2) so it's live from the start, or attach one later — same discovery list either way, just relocated: on an existing event it's under Admin → Settings → AI coordinator, not Administration (that tab is for things you do repeatedly; attaching a coordinator is one-time setup). Either way you pick a coordinator from the list — each announces itself on Nostr with its name, features, a privacy disclosure (which AI steps leave the secure enclave), and its pricing (the reference one is Free). Tap Use this coordinator:

Choosing a coordinator from the discovery listChoosing a coordinator from the discovery list

Prefer to run your own, or were given a specific one? Expand Or paste a coordinator npub (advanced) and paste its public key instead. Either way you'll see it confirmed:

Coordinator attachedCoordinator attached

Paid coordinators. A coordinator may charge (AI matchmaking costs scale with attendee count), so a listing can show a price or a free tier (e.g. "up to 20 attendees free"). If payment is ever needed, the Settings screen shows a Payment required banner with a checkout link — the current reference coordinator is free.

The coordinator can read submissions and publish on the event's behalf — directory entries, rosters, matches, talks — but it can never impersonate you or change your event's settings. Choose an operator you trust with that authority. An ↻ Recompute all matches button appears on the Administration tab (it's a recurring action, not setup); use it after a burst of new attendees.

Replacing or detaching a coordinator

Not happy with the one you picked, or need to stop paying for one? Back on Settings → AI coordinator, Replace opens the same discovery list (or the npub field) to switch to a different coordinator — this rotates the event's keys and re-grants the new coordinator, and the old one loses access from that point on. Detach removes it entirely, with no replacement.

Both are one-way for the coordinator you're leaving — once replaced or detached, it can't regain authority over the event later. Detaching specifically means:

Attaching or detaching mid-event

Both operations are safe to do while an event is running, but a coordinator restart drops whatever it was mid-processing at that instant — the job retry logic resumes it, but if you're actively running an event, it's kinder to your attendees to do this kind of change between processing bursts (right after a wave of arrivals settles) rather than the moment someone's intro is uploading.

Running the coordinator is a separate, technical step (a small daemon that needs ffmpeg and an LLM/STT provider key). See packages/coordinator/coordinator.example.toml, the operator guide, and the repo README. Point its relays at the same relay your event uses.

6. Post to your attendees

The Event posts card (under Communicate in admin) is your announcement channel — "schedule is live", "venue change", "tonight's dinner is at…". Give it a title and an optional summary/header image, write the body (Markdown works — headings, lists, links, bold), and pick who can read it:

Tap Publish post. The visibility is fixed once published (you can edit the text later, but a public post can't be quietly turned members-only or vice versa). You can also drop a link to an existing post straight from the composer's picker, and pin a post to the top of the event page.

Event posts composer — members-only selectedEvent posts composer — members-only selected

Public posts render on the event page for everyone; members-only posts show up for approved attendees in Updates and in the event's Overview "Latest" strip, marked with a lock badge. Here's the members-only lock as an attendee who hasn't joined yet sees it:

Members-only post, locked to a non-memberMembers-only post, locked to a non-member

Customize the event page and its look

Two more controls live in Admin → Settings:

Appearance — per-event theme CSS with live previewAppearance — per-event theme CSS with live preview

Not sure what your changes look like to someone who isn't in yet? The event menu has a View as visitor toggle — it hides everything members-only (locked posts, members-only menu items and sections) so you see exactly what a stranger with the link sees, with an exit bar to jump back to your normal organizer view any time. There's deliberately no equivalent "view as a member" mode — your own organizer view already is the member view for everything that isn't visitor-specific.

6.5 Talks and group chat (both new, both optional)

Prerecorded talks. In Admin → Settings → Prerecorded talks, switch it On (or Prerecord-first, which puts Talks ahead of People in attendees' nav — good for a "watch ahead, meet at the venue" format) and Save. Approved attendees can then submit short talks — recorded in the browser, uploaded as a file, or given as an unlisted YouTube / .mp4 URL (useful for talks too large to upload; the coordinator never fetches these, so URL talks are watch-only).

Submitting a talk — pick a video source and, optionally, opt in to matchingSubmitting a talk — pick a video source and, optionally, opt in to matching

Note that talks no longer feed matching by default: a speaker chooses, per talk, whether to tick "Process this talk for matching?". Leave that in mind if a submitted talk doesn't appear in anyone's match reasoning — that's expected unless the speaker opted in (and it never happens for URL talks). This keeps transcription costs off talks nobody asked to match.

The video-URL field, with "Detected: YouTube video"The video-URL field, with "Detected: YouTube video"

Submitted talks don't go live by themselves. A Talks moderation card further down Administration lists everything waiting for review — Preview each one, then Publish it so attendees can watch, or Reject it. Nothing an attendee submits is visible to anyone else until you act on it here (and publishing needs a coordinator attached, same as the rest of admin). The People search/filter (§3) has a Talk submitted filter, so on a busy event you can jump straight to who's waiting on you without scrolling the whole roster.

Group chat (Marmot, experimental). In Admin → Settings, toggle Group chat and save — it needs a coordinator attached (the coordinator operates the encrypted group: adding people as they're approved, removing them on revoke). Once on, approved attendees get a Chat tab: a single end-to-end-encrypted room for the whole event, separate from 1:1 messages — a normal running conversation, nothing for them to configure, and every device they open it on joins automatically (see the participant guide's "Group chat" section for the per-device details attendees see).

Group chat toggle in adminGroup chat toggle in admin

The group chat, with a message sentThe group chat, with a message sent

This is early: joining the group can take a little while server-side even once toggled on, and it's marked Experimental in the UI on purpose — don't lean on it as the only way to reach attendees during an event yet. Posts (§6) remain the reliable channel.

A quiet safety net. The coordinator administers the group day to day, but every device an approved organizer attests to the chat is automatically promoted to co-administrator too — no enrollment step, it just happens. If your coordinator's database is ever lost with no backup (see the operator guide), your own devices can still add or remove members and keep the room running while you sort out a replacement coordinator. Keeping the coordinator's backups current is still the real recovery plan; this is the backstop for when that plan fails.

7. During the event

Troubleshooting & FAQ

Appendix: tracking invite codes when you sell tickets elsewhere (optional)

Everything above is the whole story for most organizers. This section is only for the specific case of selling tickets somewhere other than Nostrautica — Eventbrite, your own webshop, cash at the door — where the only thing you have on a buyer is their email address. You send each of them one invite link; some join right away, some never get around to it, and a few days before the event you want to nudge exactly the people who haven't shown up yet.

Set this expectation early: the app never learns anyone's email address, and it never sends anyone an email. Mailing codes out, and matching a code back to the person you sent it to, is entirely your own job, done in your own tools — a mail-merge, a spreadsheet, whatever ticketing system you already use. All the app can ever tell you is which code numbers have been used.

Every code carries a number

Each invite code you generate is labelled — invite-1, invite-2, and so on — right next to it wherever it appears. That number is the only thing linking a code back to a person, and only you know who: write it in a column next to their email address the moment you send the code out, in a file of your own.

Numbers keep counting up. Generate 20 codes today and 10 more next week, and the new ones start at invite-21 — nothing already handed out changes its number, and none get reused.

Two exports for two different moments

Open Exports, under invite codes in Admin (§3). There are two downloads here, on purpose, because they answer different questions at different times:

The workflow

  1. Create your codes, then immediately export Codes for mailing in the spreadsheet format (CSV).
  2. Mail-merge it against your ticket list, keeping each code's number in a column next to the matching email address, in a file of your own.
  3. Closer to the event — or any time after — open Exports again and download Who has joined, with Unused codes only selected.
  4. Match those numbers back to email addresses in your file.
  5. Re-send to just that shorter list, instead of mailing everyone again.

Which format to pick

The spreadsheet file is the default, and it's the one to use for a mail-merge — open it straight in Excel, Google Sheets, or whatever you already use. The plain list of links is there mainly for people who script their own mailing instead.

One honest caveat

"Used" only ever counts up: once the app has seen a code used, it stays marked used, permanently. But "unused" is a softer signal than it looks — for an event that finished a while back, or if you simply haven't opened the organizer view since some people joined, a handful of codes can still show as unused even though those people genuinely did join. Treat used as certain, and unused as "probably not yet — worth a quick check before you re-mail someone." A little annoyance for someone who already joined beats no reminder at all for someone who didn't, but it's worth knowing this can happen rather than being caught off guard by it.

At the door

The invite sheet (§3) already leaves out any code that's been used, so if you print it again close to the event, everyone who joined online in the meantime simply won't be on the page anymore.