Documentation: AI Tinkerers Agent API
AI Tinkerers Agent API
Use the Agent API to help an AI Tinkerers member or organizer with events, chapters, community operations, documents, and other capabilities available to their account.
The API is permissioned. An Agent key acts as the member who created it, and every response is limited to what that member and key may use.
Start here
- Developer page:
https://aitinkerers.org/developers/api-keys - Base URL:
https://aitinkerers.org/api/agents/v1 - API discovery:
https://aitinkerers.org/api - OpenAPI:
https://aitinkerers.org/api/agents/v1/openapi.yaml - MCP:
https://aitinkerers.org/api/agents/mcp/v1
The OpenAPI document is capability-filtered. Without authentication it describes the shared public surface. With a valid Agent key it privately includes only the additional operations that key is authorized to use. Agents should use the authenticated OpenAPI response as the source of truth for available operations and request schemas.
Authentication
Create a personal Agent key on the developer page. Agent keys begin with sk_.
Send the key in a header:
Authorization: Bearer sk_...
X-API-Key is also supported. Never put a key in a URL or request body.
Validate a key before starting a workflow:
curl https://aitinkerers.org/api/agents/v1/auth/validate \
-H "Authorization: Bearer sk_..."
The validation response describes the key’s effective roles, scopes, and available API groups. Do not infer capabilities that are absent from that response or from the authenticated OpenAPI document.
Scopes
Keys can have narrow scopes such as:
-
read: retrieve permitted records -
write: create or update permitted records -
generate: request supported generated content -
export: create supported exports
Use the narrowest scopes needed. A scope permits a type of action, but it does not grant access to every chapter, event, person, or document.
Request and response shape
Client photo fields
Serialized client records, including client detail, client search, and RSVP client objects, include scraped_li_image_url, uploaded_image_url, picture_url, scraped_twitter_profile_image_url, and scraped_gu_avatar_url. Missing stored values are returned as null.
profile_image_url is the computed display candidate using cached image checks only. It respects suppress_auto_profile_image and suppress_public_profile_enrichment, which are also returned. It can be null or a Gravatar fallback; a non-null value does not prove a usable headshot exists. These reads do not download images or verify their current availability, so a later synchronous UI check can reject a candidate.
scraped_li_image_url is the stored LinkedIn image field, normally containing the rehosted delivery URL. Imported images preserve the source URL separately in ImportedImage.original_url; do not assume this client field is the original LinkedIn CDN URL.
Read-shaped endpoints generally support GET. Existing clients may also use POST with JSON. Mutations use POST.
Successful responses use this envelope:
{
"ok": true,
"data": {}
}
Errors use this envelope:
{
"ok": false,
"error": {
"code": "invalid_request",
"message": "Check the request and try again."
}
}
Treat returned tokens as stable API identifiers. Pass them to later get or update calls instead of guessing database IDs.
Common organizer workflows
Find a chapter or event
Use the authenticated OpenAPI document to locate chapter lookup, event search, and upcoming event operations. Search first, retain the returned token, and then use the matching detail operation.
Public worldwide event syndication is also available without a key:
GET https://aitinkerers.org/api/public/v1/events
It returns only live, indexed, public AI Tinkerers events. It does not expose attendees, private venues, RSVP details, drafts, or organizer contact data.
Work with an organizer’s events
An organizer can read or modify only the chapters, series, and events included in their management access. Finding an event in a public catalog does not imply write access to it.
Before a mutation:
- Confirm the authenticated OpenAPI document includes the operation.
- Retrieve the target record through an authorized detail operation.
- Confirm the user asked for the exact state-changing action.
- Send only fields defined by the operation schema.
- Read the result back when practical.
Invite one person to a private VIP dinner
The Agent API supports an authorized owner or organizer inviting one named person to an inventory-managed, invitation-only VIP dinner. This includes Mixture of Experts owners acting on Mixture dinners they may manage. The production capability is feature-gated and is available to a caller only when its operations appear in the authenticated OpenAPI document or MCP tool list. Agents must not guess or probe absent routes.
The workflow lists eligible dinners, previews and records one invitation, reads it back, and can record a decline in either communications mode, or a confirmation in organizer-managed communications mode. It uses a personal Agent key and the authenticated member is always the recorded actor and sender. Event ownership, an explicit event organizer tag, or an invitation-manager dinner-team role is required. A public event listing, an unrelated organizer role, administrator status by itself, or possession of a private event token is not sufficient.
The approved operation names and routes are:
-
dinner_invitations_events_list:GET|POST /api/agents/v1/dinner_invitations/events/list -
dinner_invitations_list:GET|POST /api/agents/v1/dinner_invitations/list -
dinner_invitations_preview:POST /api/agents/v1/dinner_invitations/preview -
dinner_invitations_send:POST /api/agents/v1/dinner_invitations/send -
dinner_invitations_get:GET|POST /api/agents/v1/dinner_invitations/get -
dinner_invitations_response_preview:POST /api/agents/v1/dinner_invitations/response/preview -
dinner_invitations_response_update:POST /api/agents/v1/dinner_invitations/response/update
The recipient may be selected by an existing Client token, by an authorized Prospecting person with an exact email, or simply by entering an email address and optional name. Existing email addresses are matched case-insensitively and reuse the existing Client. A new email creates only a minimal email identity for this invitation. It does not create an RSVP or grant attendee access at send time.
VIP invitation links do not expire. There is no structured response deadline, deadline-setting control, countdown, or automatic deadline transition. Organizers may write urgency into an invitation, for example, “Respond by Friday at 7pm or we will invite someone else.” That is message copy only. The platform does not interpret or enforce it, reject a late response, or release a seat when that time passes. Organizers can inspect invitation, communication, and response timestamps and explicitly accept, reject, or release a person through the normal audited controls. Passage of time alone never changes invitation or seat state.
dinner_invitations_list is the event’s seat-filling ledger. It returns named invitations across pending, accepted, declined, canceled, and released states, plus per-status counts and current event capacity. Pending invitations are separate EventInvitation records, not pending RSVPs. Each pending named invitation holds one seat while awaiting a response.
Preview shows the exact recipient, message, and resulting capacity overage. It holds no seat, sends nothing, and returns a signed proposal valid for 15 minutes. The short lifetime prevents an agent from sending old reviewed copy or relying on stale settings. If it expires, preview again. It has no effect on an invitation that was already sent.
When platform guest communications are off, invitation issuance records the guest and seat hold but suppresses platform email and calendar delivery. Response preview writes nothing; response update requires the exact returned confirmation and an idempotency key. Confirmations remain restricted to organizer-managed mode, with SMS controlled independently by the event setting.
To record a guest saying they cannot attend, use decision: "declined" in either communications mode. Pending and released named invitations become declined without creating an RSVP or restoring a hold. Previously accepted guests become not_attending and their RSVP is canceled. Pass suppress_notifications: true (the default for declines) to suppress notifications for this action, including SMS and calendar notification emails, while retaining calendar cleanup when enabled. No decline confirmation email is generated. false permits the existing event calendar/SMS workflows; it does not force email delivery or override disabled event channels. This option is supported only for declines and must match between preview and update. It is included in confirmation and idempotency checks. Event communication settings remain unchanged.
Send uses an idempotency key and rechecks authorization, recipient suppression, duplicates, configured capacity, and organizer invite limits. A successful send adds exactly one held seat immediately. When the recipient verifies the invited email and accepts, that same seat moves from Held to Occupied and the RSVP is created. Acceptance never consumes a second seat. Decline or explicit organizer release frees the hold once.
Configured table capacity stays fixed unless an organizer deliberately changes that setting. Named invitations may create an overage, which the API reports as over_capacity_by and over_capacity_by_after_send; invitation preview and send never change capacity. Mixture of Experts collaborators still require explicit fixed invite limits. An ordinary private VIP dinner uses the shared pool if no limits exist; after any collaborator limit is configured, other inviters need their own limit.
409 organizer_allocation_exhausted includes the caller’s invite limit, used count, and remaining count. The error makes no changes and directs the caller to the website Invitations workspace. It never directs an agent to expand table capacity to make an invitation fit. Version 1 does not expose allocation transfer through the API. 409 event_capacity_exhausted remains available for actions that immediately confirm attendance or create multi-use seat commitments.
If invitation creation succeeds but delivery fails, the API returns 502 delivery_failed with the invitation token and explicit invitation_created and seat_held flags. The agent must not say the email was sent. Retrying the same idempotency key does not create another seat; use the website Invitations workspace to review the failed delivery.
Creating the email identity, sending the invitation, and accepting it do not subscribe the person to a newsletter, chapter list, Mixture list, or general AI Tinkerers mailing list. Existing preferences are preserved. Event invitation, confirmation, reminder, venue-update, and cancellation messages are transactional messages tied only to that dinner. A new person is prompted to complete their profile after acceptance.
Record an invitation already made off-platform
Use this workflow when an organizer says, “I already invited them; track it,” including an invitation made in Gmail, SMS, instant message, by phone, or in person. The action creates a normal pending invitation and its audit history together. It sends no guest email, SMS, or calendar notification, whether platform guest communications are enabled or disabled. It does not change the event’s communications setting or subscribe the guest to a mailing list.
Discover the operations in the caller’s authenticated OpenAPI or MCP tool list before using them:
-
dinner_invitations_off_platform_preview:POST /api/agents/v1/dinner_invitations/off_platform/preview -
dinner_invitations_off_platform_record:POST /api/agents/v1/dinner_invitations/off_platform/record
These operations require a write-scoped personal key and current invitation-management authority for the dinner, consistent with the other invitation mutation previews. Preview performs no writes and reserves no seat. Record requires the exact returned required_confirmation and an idempotency_key. A user’s explicit request to record an already-made invitation authorizes that recording; protocol confirmation does not require asking the user for the same permission again.
| Action | Guest communications enabled | Guest communications disabled |
|---|---|---|
| Platform invitation issuance | Creates invitation and sends platform email | Existing silent issuance behavior |
| Record off-platform invitation | Creates invitation and audit history with zero guest notifications | Same behavior |
For a new invitation, supply meetup_token and exactly one recipient selector: client_token, email (with optional name), or radar_person_token. Use an unambiguous identity. Existing clients can be recorded without email-delivery eligibility. Email suppression remains in force for any future send.
Example SMS preview, using illustrative tokens:
{
"meetup_token": "mu_example",
"client_token": "cl_example",
"communication": {
"channel": "sms",
"provider": "imessage",
"occurred_at": "2026-09-04T10:30:00-07:00",
"note": "Invited personally by text. They are checking their calendar."
}
}
For Gmail, communication may instead contain:
{
"channel": "email",
"provider": "gmail",
"source_ref": "gmail-message-example",
"subject": "Dinner invitation",
"body_text": "The actual message sent, when available.",
"note": "Invitation sent from my personal Gmail."
}
For a verbal invitation, no email copy or exact time is required:
{
"channel": "in_person",
"reported_inviter": "Event organizer",
"note": "Invited during our conversation after the meetup."
}
Repeat the reviewed request at /record, adding its exact confirmation and a fresh idempotency key. communication is optional. Supported channels are email, sms, instant_message, phone, in_person, other, and unspecified. Omitted channel means unspecified. Omitted occurred_at remains unknown; the server separately records when and by whom the entry was made. Never invent a timestamp, message copy, provider reference, inviter, or recipient acceptance.
Optional communication fields include provider (50 characters), note (2,000), reported_inviter (200), source_ref (500), subject (200), body_text (12,000), and body_html (30,000). Notes preserve supplied paragraph boundaries and are internal to authorized organizers. reported_inviter is reported attribution, separate from the authenticated recorder; it does not change permissions or seat-allocation ownership. Unsupported communication fields are rejected so context is not silently discarded.
To append history to an existing invitation, provide invitation_token and communication, omitting the new-invitation fields. This works for accepted and released invitations as well as pending invitations. It adds no seat, does not change RSVP status or a known original invitation source. For a pending hold with no previous sent invitation or known source, the first recorded communication establishes its off-platform origin. A duplicate creation returns duplicate_invitation and the existing token. Inspect and explicitly target that invitation instead of creating another one. Do not use attachment to reactivate released seats.
The response includes invitation_created, guest_notifications: {email: false, sms: false, calendar: false}, the invitation, the communication, the note, and current capacity. A new invitation has status: pending, seat_state: held, and delivery_state: external_recorded. One pending invitation holds one seat under the normal allocation and overage rules; record never changes configured capacity. An invitation is not an RSVP.
invitation.origin preserves the original source, channel, provider, occurrence time when known, recording time, recorder, and reported inviter when supplied. Later platform communications do not replace that original source. dinner_invitations/get returns sourced notes and chronological communications; delivery continues to summarize recent communication. recorded_by_client_token and recorded_at identify the audit recorder. The legacy message field sent_by_client_token remains available for compatibility; for external records use the explicit recorder and reported-inviter fields to interpret attribution.
The same idempotency key and payload replay the original receipt without adding a seat, message, or note, regardless of how much time has passed. Reusing a key with changed data returns idempotency_conflict. Re-recording the same provider/message reference for the same invitation returns duplicate_external_message. Creation and audit writes commit together or roll back together. Authorization and allocation failures must not be treated as successful recording.
Later legitimate event communications follow the event settings and the action taken. The recording creates no deliverable mail log, so switching communications on later does not replay the external invitation. A reported external communication is not proof of provider delivery or recipient read status.
The website offers Record off-platform invitation from Invitations in both communications modes and from individual invitation details. Communication history distinguishes recorded conversations from platform emails. The Guest list’s person details expose invitation history and internal notes, including accepted or released records, to invitation managers.
Existing operations remain supported:
-
dinner_invitations_external_delivery_previewanddinner_invitations_external_delivery_record, at/dinner_invitations/external_delivery/previewand/record, record an email against an existing invitation. They requireinvitation_token,sent_at,provider,subject, andbody_text; record also requires exact confirmation and idempotency. They send nothing and work with event communications enabled or disabled. Use the new off-platform workflow to create a missing invitation or record other channels. -
dinner_invitations_note_create, at/dinner_invitations/notes/create, adds an internal sourced note usinginvitation_token,body, optionalsource_type,source_ref,occurred_at, andmetadata, plus an idempotency key. Read it back withdinner_invitations/get.
Manual acceptance and decline recording remain separate response operations with their existing communications-mode requirement. Off-platform invitation recording always begins in pending state. Do not infer that an invitation was accepted.
Create and configure owner-managed private events
Workspace Owners can create private meal events and update dinner settings through the Personal Agent API. Authors, removed owners, unrelated workspace owners, and platform administrators without a local Owner membership do not receive this capability. The operations appear only in the caller’s authenticated OpenAPI document or MCP tool list.
-
private_events_workspaces_list:GET|POST /api/agents/v1/private_events/workspaces/list -
private_events_create_preview:POST /api/agents/v1/private_events/events/create/preview -
private_events_create:POST /api/agents/v1/private_events/events/create -
private_event_settings_preview:POST /api/agents/v1/private_events/events/settings/preview -
private_event_settings_update:POST /api/agents/v1/private_events/events/settings/update -
private_events_team_get:POST /api/agents/v1/private_events/events/team/get -
private_events_invitation_allowance_update:POST /api/agents/v1/private_events/events/team/invitation_allowance/update -
private_events_team_assign:POST /api/agents/v1/private_events/events/team/assign -
private_events_team_lead_assign:POST /api/agents/v1/private_events/events/team/lead/assign -
private_events_team_remove:POST /api/agents/v1/private_events/events/team/remove
Team assignment keeps guest-facing co-organizer credit (show_as_co_organizer) separate from event management access (grant_event_management). Lead assignment accepts weblog_token, meetup_token, email, confirmation: "ASSIGN EVENT LEAD ORGANIZER", and an idempotency_key. It uses the same service as the UI to designate the single event lead and retain the previous lead as a visible co-organizer with management access. Lead organizers always have event management access. Team role mutations require a write-scoped key and workspace Owner membership; they do not grant workspace membership, RSVP anyone, reserve a seat, change invite allocations, or send email. Use team/get to read back current roles after a mutation. An idempotent replay returns the original result without reapplying the role change.
Invitation allowances can be changed separately through private_events_invitation_allowance_update. Supply an existing event team member’s email, the workspace and event tokens, unlimited: true (omit seat_limit) or unlimited: false with a nonnegative whole-number seat_limit, the exact confirmation UPDATE EVENT INVITATION ALLOWANCE, and a fresh idempotency_key. Numeric allowances may exceed table capacity. Zero prevents new invitations only when no committed invitations remain; existing event-management access is preserved. A finite allowance cannot be reduced below committed invitations. The lead always has unlimited invitations, so a finite lead allowance is rejected. This operation uses the same people-settings service as the UI, enables invitation access for a positive or Unlimited allowance, preserves other permissions and attendance, and sends no email. It requires local workspace Owner membership and a write-enabled personal key.
Example request to POST /api/agents/v1/private_events/events/team/invitation_allowance/update:
{
"weblog_token": "blog_example",
"meetup_token": "mu_example",
"email": "[email protected]",
"unlimited": true,
"confirmation": "UPDATE EVENT INVITATION ALLOWANCE",
"idempotency_key": "event-organizer-unlimited-v1"
}
Both the mutation response’s member and private_events_team_get rows include invitation_allowance, with unlimited, seat_limit, seats_used, and seats_available. Unlimited limits and remaining counts are null. A replay returns the original response without reapplying the change, even if a newer allowance was subsequently saved; use team/get for current state. Reusing the key with a different payload returns a conflict.
Creation and settings changes use preview, exact confirmation, and idempotent execution. A write-scoped key is required for execution. Read-only keys may list workspaces and request no-write previews. Event creation accepts independent platform_guest_communications_enabled and sms_updates_enabled values, so organizers can control guest email and SMS separately. Settings updates also accept calendar_automation_enabled independently. Set confirm_calendar_location: true to validate the supplied or existing venue using Google Maps before confirming calendar readiness. The preview performs provider validation but does not change the event or send messages. Ambiguous matches and provider failures reject confirmation; there is no address regex or token-matching fallback. Venue edits invalidate prior validation and enqueue a background check. Virtual events retain their meeting-URL readiness check.
The settings preview includes calendar eligibility, attendee count, and whether synchronization will be scheduled. The update response includes automation and location-confirmation state. Confirmation is bound to the venue text, and updates use normal asynchronous calendar delivery. A scheduled sync is not proof that Google delivered an invitation. Existing events require provider validation before their next calendar delivery; run calendar:validate_upcoming_venues when rolling out this change.
Work with community records
Person, RSVP, subscriber, sponsor, and related records are privacy-scoped. Responses omit protected fields the key cannot access. An omitted field should be treated as unavailable, not as evidence that the field exists with an empty value.
Do not use this API to assemble lead lists, scrape contact data, or infer hidden fields.
Read AI Tinkerers documents
Use the document search and get operations exposed by the authenticated OpenAPI document. Search results and retrieval are filtered to documents the member may access.
Research a company independently
Use companies_get (GET or read-only POST /api/agents/v1/companies/get) to retrieve the latest saved public company research by company token, domain, or unambiguous exact name. It returns source-backed data, collection/expiry dates, freshness and the latest attempt without launching research.
Use companies_enrichment_request (POST /api/agents/v1/companies/enrichment/request) with a company token or name/domain plus an idempotency key to request research. Fresh results and equivalent active work are reused across people. refresh: true requests newer research but still joins active work. These tools are available to index owners, admins and authorized Talent Scouts; requesting research requires write scope.
Person and company enrichment are independent. A person may have no company assigned. For a person-plus-company task, call the existing person tool and company tool separately and combine their results; neither call assigns an employer. See Company enrichment for contracts, identity rules and examples.
Use MCP
OAuth-capable MCP clients can connect to:
https://aitinkerers.org/api/agents/mcp/v1
The server supports interactive OAuth and Agent bearer keys. Its tool list is capability-filtered for the authenticated member. Refresh the tool list after permissions or scopes change.
Agent safety rules
- Never probe undocumented paths to discover unavailable products or operations.
- Never claim a write succeeded until the API returns success and, when possible, a readback confirms the new state.
- Do not turn an invitation request into an RSVP, registration, send, or other different action without explicit confirmation.
- Do not reveal private API responses outside the user’s requested workflow.
- Preserve idempotency keys and concurrency values when an operation requires them.
- If an error is safe but nonspecific, explain the user action that is blocked without speculating about hidden permissions or product features.
Errors and troubleshooting
-
401: the key is missing, invalid, expired, or revoked. Validate it and create a new key if needed. -
403: the requested action is not available to this member, key, or resource. Check the authenticated OpenAPI document, key scopes, and ownership of the target resource. -
404: the resource is unavailable or not visible to this caller. Do not use the response to infer that a hidden record exists. -
409: the request conflicts with current state. Refresh the record and follow any returned concurrency or idempotency guidance. -
422: the request shape or values are invalid. Compare the request with the authenticated OpenAPI schema. -
429: wait for the requested retry interval before trying again.
For persistent access problems, use the developer page to inspect or replace the key. Report the operation, HTTP status, safe error code, and request identifier. Never include the full key.
Silent check-in backfills
Use POST /api/agents/v1/rsvps/mark_attended to check in an existing RSVP after its event starts. Pass send_email: false when reconciling attendance without notifying the attendee:
{"rsvp_ref":"rsvp_example","send_email":false}
The option suppresses both the checked-in follow-up email and the resolved-attendance email for this operation. It defaults to true for compatibility. The endpoint preserves the registration state, records the email choice in the audit entry, and returns send_email alongside already_attended. Repeated calls preserve the original check-in timestamp and do not create another check-in audit entry or notification. This option does not cancel previously queued mail or change unrelated event communications.
Explicit private dinner attendance
Use POST /api/agents/v1/rsvps/attendance/update to record a guest as attended, absent (an explicit no-show), or unknown (clear the record):
{"rsvp_ref":"rsvp_example","status":"absent"}
This uses Dinner HQ’s attendance operation, requires event facilitator access, and allows absence only after the event ends. It preserves registration state, including an existing cancellation, records before/after values in the RSVP status history, and sends no email or badge print. It replaces prior attendance evidence when correcting a record. RSVP get/search responses expose attendance_status and attendance_recorded_at. An unknown status is not an explicit no-show. The existing status=no_show search filter is heuristic (accepted but not checked in), so inspect attendance_status to distinguish recorded absence from missing check-in data, including cancelled guests.
Media folder reference files
Organizers can upload ordinary UTF-8 .txt and .md files alongside raw videos at /media/upload. Completed text files directly in a video’s folder provide speaker, project, talk-title, and spelling hints for transcription, video identification, editing, and short titles. They are reference material, not instructions or replacement transcript text. No filename convention or structured template is required.
For example, speaker-notes.md can contain:
# Final presentations
- Cornelius Hagmeister: Patchwork, federated code inspection using contributors' existing coding agents.
- Nameer Khan: SIE Sentinel, a repository scanner, proof-of-concept generator, and live agent monitor.
For authorized agents, discover the media operations in authenticated OpenAPI/MCP, then:
- Use
media_folder_searchormedia_folder_listto find the raw-video folder. - Call
media_folder_infowith itsfolder_token. Theai_contextresponse lists reference files, read limits, and an upload recipe when the caller can upload. - Call
media_file_upload(POST /api/agents/v1/media/files/upload) withfolder_token, a.txtor.mdfilename, andbody_base64containing the UTF-8 file bytes encoded as base64.content_typeis optional and inferred from the extension. This existing endpoint also accepts videos up to 50 MB; larger videos use the multipart web uploader. - Verify the returned file has
ai_context_file: true, then readmedia_folder_infoagain to confirm the file is in the intended folder.
References apply only to files in the same folder, not parents, siblings, or child folders. Reads use at most the first 32 KB per file, 32 files ordered by upload ID, and 96,000 text characters in total. Prompt entries identify source files and mark truncated excerpts. Upload reference files before editing begins. Adding notes does not automatically replace completed videos; those need an explicit correction/reprocess run. References help attribution but do not grant speaker approval or bypass existing publication checks.