nessie

API

L-API tal-HTTP li hemm wara kull klijent ta’ Nessie, u kif tawtentika ruħek magħha.

X’inhu l-API

Nessie għandu API HTTP wieħed. L-applikazzjoni web tal-amministrazzjoni, il-klijenti għal macOS u iOS, u d-daemon tal-executor remot huma kollha klijenti normali tiegħu, u ebda ħaġa li jistgħu jagħmlu ma tintlaħaq b’mod ieħor. Hija API JSON fuq server Fastify, mhijiex GraphQL, u m’għandhiex sett “pubbliku” separat: l-interfaċċa li jsejħu is-skripts tiegħek hija l-istess li jsejħu l-prodott.

M’hemm l-ebda segment ta’ verżjoni fil-mogħdija. Kull rotta tinsab taħt /api, ħlief l-endpoint MCP tad-dħul f’POST /mcp u ftit dokumenti ta’ skoperta /.well-known/. Il-kompatibbiltà tinżamm billi jiżdiedu dejjem biss oqsma, għalhekk klijent li jinjora dak li ma jagħrafx ikompli jaħdem.

L-URL bażi

Nessie huwa self-hosted, għalhekk l-URL bażi hija l-oriġini li fuqha d-deployment tiegħek iservi l-API — l-operatur jistabbilixxiha bħala NESSIE_API_PUBLIC_URL, u l-istess valur huwa dak li l-API tuża meta jkollha bżonn toħloq URL assolut tagħha stess. Fuq l-istanza li nħaddmu aħna, dan huwa https://api.nessie.works; istanza ta’ żvilupp imnedija b’pnpm dev twieġeb fuq http://localhost:5454.

L-applikazzjoni web tal-amministrazzjoni hija oriġini differenti mill-API, għalhekk il-klijenti tal-browser huma soġġetti għal lista ta’ permessi CORS (NESSIE_CORS_ORIGINS). It-talbiet minn script jew minn server ma għandhom l-ebda oriġini biex jiġu ċċekkjati, u ma jiġux affettwati minn dan.

L-awtentikazzjoni

Kull talba barra minn sett żgħir ta’ rotti pubbliċi maħsuba apposta tgħaddi token tal-aċċess fl-intestatura standard:

Authorization: Bearer <token>

It-token huwa JWT iffirmat, maħruġ mill-API. Huwa ta’ żmien qasir — tletin minuta b’mod awtomatiku (NESSIE_AUTH_TOKEN_TTL) — u huwa l-unika kredenzjali li kwalunkwe klijent ordinarju jippreżenta. Nessie m’għandux ċavetti API personali ta’ żmien twil. Jekk trid li script isejjaħ l-API, dan jidħol bl-istess mod li jidħol il-browser ta’ persuna, u jiġġedded it-token hekk kif jaħdem.

Kif tikseb token

POST /api/auth/session joħloq sessjoni. Iwieġeb bit-token tal-aċċess u bl-identità ta’ min qed isejjaħ, u jpoġġi t-token tat-tiġdid bħala cookie separata HTTP-only.

Kif turi min int jiddependi minn kif tkun installata l-istanza. Istanza li taħdem fil-modalità local taċċetta email u password. Fuq istanza hosted jew selfHosted, id-dħul b’password jiġi rrifjutat direttament b’403 PASSWORD_AUTH_DISABLED, u l-unika triq biex tidħol hija l-fornitur tal-identità kkonfigurat — b’hekk il-kont qatt ma jkun jista’ jikber triq ta’ identità t-tieni, aktar dgħajfa, miegħu.

Idħol permezz ta’ fornitur tal-identità

Single sign-on (SSO) huwa skambju tal-kodiċi ta’ awtorizzazzjoni OAuth b’PKCE, f’tliet passi. Il-fornitur tal-identità ta’ Nessie stess huwa UnlikeOtherAI, li jmexxi wkoll l-istruttura tal-organizzazzjoni u tat-timijiet li istanza tirrifletti; l-iskambju hawn taħt huwa l-istess forma għal kwalunkwe fornitur ikkonfigurat.

  1. GET /api/auth/providers jelenka dak li din l-istanza taċċetta, b’providerId, tikketta u indikazzjoni dwar jekk il-paġna tad-dħul għandhiex tirridireġi lejh awtomatikament.
  2. GET /api/auth/providers/:providerId/authorize, b’codeChallenge, redirectUri u state bħala parametri tal-query, iwieġeb b’{ data: { authorizeUrl } }. Ibgħat lill-persuna hemm.
  3. Il-fornitur iġib lura lill-persuna għal redirectUri tiegħek b’kodiċi. Ibgħat dan lura bħala POST /api/auth/session b’{ providerId, code, codeVerifier, redirectUri } — l-erbgħa kollha huma meħtieġa flimkien, u sett mhux sħiħ huwa 400 EXTERNAL_AUTH_INCOMPLETE.

Tiġdid tas-sessjoni

It-token tat-tiġdid qatt ma jidher fil-kontenut tar-risposta. Jiġi mpoġġi bħala cookie HTTP-only msemmija nessie_refresh, limitata għall-mogħdija /api/auth, b’żmien ta’ tletin jum b’mod awtomatiku (NESSIE_AUTH_REFRESH_TOKEN_TTL). Is-sejħa ta’ POST /api/auth/refresh bil-cookie dik tikkonsma t-token, toħroġ token tal-aċċess ġdid u tpoġġi cookie ġdid minflok dak il-qadim — it-tokens jiddawru, u b’hekk token misruq ikun validu biss sakemm il-klijent reali jiġġedded it-token li jmiss.

Browser imdaħħal f’diversi kontijiet iżomm cookie waħda għal kull idħol, imsemmija nessie_refresh_<slot>, u jsemmi liema minnhom tikkonċerna t-talba, permezz tal-intestatura x-nessie-account-slot. Klijent li ma jibgħatx dik l-intestatura jitlob dwar nessie_refresh, u dik hija kollox li jeħtieġ klijent tal-linja tal-kmand.

Klijent tal-linja tal-kmand għalhekk jeħtieġ kontenitur tal-cookies. B’curl dan huwa --cookie-jar fuq is-sejħa tal-idħol u --cookie fuq it-tiġdid, kif fl-eżempju ta’ hawn taħt.

Dak li jiġi ċċekkjat f’kull talba

L-awtentikazzjoni mhix biss kontroll tal-firma. Qabel ma jaħdem kwalunkwe handler, l-API tivverifika l-firma u l-iskadenza tat-token, tikkonferma li s-sessjoni ma ġietx irrevokata (kemm bil-verżjoni tat-token għall-utenti kollha, kemm bl-ID tas-sessjoni individwali), u tgħabbi l-membership tal-persuna fl-organizzazzjoni li t-token isemmi. Membership diżattivata tfisser 403. Meta l-organizzazzjoni tkun marbuta ma’ fornitur tal-identità estern, l-istatus attwali tal-persuna jiġi rivalutat ma’ dak il-fornitur fuq it-talba stess, minflok ma jinqara mit-token; b’hekk aċċess li jitneħħa hemmhekk jieqaf immedjatament, mhux fl-iskadenza li jmiss.

Kredenzjali oħra li mhumiex token tas-sessjoni

Jeżistu żewġ kredenzjali oħra tal-bearer, u ebda waħda minnhom m’hi ċavetta ta’ użu ġenerali. Kredenzjali ta’ apparat tal-vuċi tiġi aċċettata biss fuq ir-rotti tas-sejħiet vokali, u kredenzjali ta’ aġent għall-aċċess tiġi aċċettata biss fuq l-endpoint MCP. Meta jiġi ppreżentat wieħed minnhom fi kwalunkwe post ieħor jiġi rrifjutat b’403 li jsemmi l-kredenzjali, mhux ippruvat mill-ġdid bħala sessjoni aktar dgħajfa — ara MCP u għodod konnessi biex tara kif tinħareġ il-kredenzjali tal-aġent.

Il-kontenitur tar-risposta

Kull risposta ta’ suċċess hija oġġett b’ċavetta data. M’hemm l-ebda array mingħajr kontenitur, u l-ebda payload fil-għeruq, għalhekk klijent qatt m’għandu bżonn jiddistingwi skont il-forma:

{
  "data": { "id": "3f1c…", "label": "engineering" }
}

Endpoints tal-listi jiżdiedu oġġett meta flimkien miegħu. Ebda ħaġa oħra ma tiżdied qatt fil-livell ta’ fuq.

Il-falliment juża wkoll forma waħda, xi kawża jkun:

{
  "error": {
    "code": "VALIDATION_ERROR",
    "message": "A message needs content or at least one attachment",
    "field": "body",
    "details": { "formErrors": [], "fieldErrors": {} }
  }
}

code huwa l-parti li tinqara mill-magni, li għandek tibbaża fuqha; message huwa għal persuna. field u details jidhru meta l-falliment ikun speċifiku biżżejjed biex jiġi lokalizzat. Errur mhux ittrattat tas-server huwa dejjem 500 INTERNAL_ERROR b’messaġġ fiss — it-test tal-errur sottostanti jiġi llogat, qatt ma jintbagħat lura, għax seta’ jkun ħa dejta tat-talba miegħu.

Il-kodiċijiet tal-errur li tiltaqa’ magħhom l-ewwel

StatKodiċiTifsira
400VALIDATION_ERRORIl-kontenut jew il-kwerya ma kkorrispondewx mal-iskema.
401AUTH_REQUIREDMa hemm ebda bearer token, jew l-intestatura kienet ħażina.
401TOKEN_EXPIREDIt-token tal-aċċess għadda l-iskadenza tiegħu. Ġedded u erġa’ pprova.
401TOKEN_REVOKEDIs-sessjoni ġiet magħluqa, jew kull sessjoni ġiet imneħħija b’mod sfurzat.
403ACCOUNT_DEACTIVATEDIl-membership ta’ din l-organizzazzjoni ġiet diżattivata.
404NOT_FOUNDEbda rotta bħal din, jew ebda rekord bħal dan li dan il-klijent jista’ jara.
429RATE_LIMITEDIl-limitu huwa mimli. Aqra Retry-After.
500INTERNAL_ERRORErrur mhux ittrattat tas-server, intenzjonalment mhux spjegat.

Paġinazzjoni

L-endpoints tal-listi jinqsmu f’paġni b’cursor keyset opaku, mhux b’offset — ir-rekords jiżdiedu waqt li xi ħadd jaqra, u b’offset it-tieni paġna terġa’ turi, mingħajr ma jinduna ħadd, rekord li l-ewwel paġna diġà wriet.

Hemm tliet parametri tal-kwerya aċċettati: cursor, limit u direction (forward jew backward). Il-paġna standard hija ta’ 25 u l-limitu massimu 100; valur akbar jiġi limitat għal dak il-massimu minflok ma jiġix miċħud. Endpoints li jordnaw jew jiffiltraw iżidu wkoll sort, order u q għat-tfittxija b’test liberu.

Il-meta tal-paġna tgħidlek fejn tinsab:

{
  "data": [ … ],
  "meta": {
    "hasMore": true,
    "nextCursor": "2026-09-12T08:31:44.005Z|8b2f…",
    "prevCursor": null,
    "total": 134
  }
}

nextCursor u prevCursor huma t-tnejn reali: Previous u Next huma t-tnejn kontrolli li persuna tistenna. Huma opaki — is-server jikodifika fihom iċ-ċavetta tal-ordni tiegħu stess, u klijent li janalizza jew jibni wieħed minnhom jinkiser malajr kif lista tibdel l-ordni tagħha. total jidher fuq ħafna mil-listi u jitħalla barra fejn l-għadd ma jkunx ta’ tifsira, bħal f’riżultati ta’ tfittxija ordnati skont ir-rilevanza.

Limiti tar-rata

Il-limiti huma għal finestri fissi u jiġu infurzati qabel ma jinqara anke l-kontenut tat-talba. Talba miċħuda hija 429 bil-kodiċi RATE_LIMITED u b’intestatura Retry-After f’sekondi.

Ħafna mill-bucket jinżammu skont l-indirizz IP tal-klijent; dawk sensittivi għall-kredenzjali — dħul, tiġdid, kontroll mill-ġdid tal-password u kitba ta’ kredenzjali MCP — iżommu wkoll kontatur għal kull kont, u jirrifjutaw meta jew wieħed minnhom jaqbeż il-limitu. B’hekk indirizz wieħed li jibgħat talbiet lil ħafna kontijiet, kif ukoll kont wieħed attakkat minn ħafna indirizzi, jiltaqgħu mal-istess ħajt. Id-dħul b’default ikun 10 tentattivi għal kull IP u 5 għal kull indirizz tal-email f’għaxar minuti; l-għoti ta’ messaġġ b’default huwa 60 fil-minuta; kitbiet taħt /api/agents 60 fil-minuta. Kull limitu jista’ jiġi kkonfigurat għal kull deployment, għalhekk ħu dawn bħala d-default li jintbagħtu, mhux bħala kuntratt. Il-kontrolli tas-saħħa u l-istrimijiet realtime huma eżenti.

F’ħin reali

Li tistaqsi lista f’intervalli regolari hija l-mod ħażin biex issegwi konverżazzjoni. Minflok hemm tliet endpoints tal-istrim:

  • GET /api/events/stream — server-sent events għal kull ħaġa li l-persuna mdaħħla tista’ tara.
  • GET /api/threads/:threadId/stream — server-sent events għal thread wieħed. Jirrispetta Last-Event-ID, għalhekk ir-rikonnessjoni tkompli minn fejn kienet, minflok tibda mill-ġdid.
  • GET /api/activity — WebSocket li jġib il-feed tal-attività.

Il-browsers ma jistgħux isettjaw intestaturi fil-handshake tal-WebSocket, għalhekk ir-rotta tal-WebSocket taċċetta wkoll it-token tal-aċċess bħala parametru ?token= fil-query. Dan huwa l-unika post fejn token jista’ jidher f’URL; kull rotta oħra tieħu l-intestatura.

Il-familji tar-riżorsi

Hemm ferm aktar minn elf endpoint, wisq biex jitniżżlu kollha hawn. Jinqasmu f’familji, u ladarba tkun taf il-prefiss ta’ familja, ir-rotti individwali jkunu prevedibbli — kollezzjoni fil-prefiss, rekord taħtha, u azzjonijiet bl-isem bħala sub-paths POST.

FamiljaPrefissDak li jkopri
Awtentikazzjoni/api/authDħul, tiġdid, ħruġ, l-identità attwali, u s-sessjonijiet ta’ persuna stess.
Kanali u threads/api/channels, /api/threadsIl-mudell tal-konverżazzjoni: kanali jżommu threads, threads iżommu messaġġi, u t-tweġibiet jitqiegħdu taħt messaġġ ewlieni.
Aġenti/api/agentsDefinizzjonijiet tal-aġenti, il-konnessjonijiet tal-kanali tagħhom, il-konverżazzjonijiet, il-kompiti tagħhom u l-istatus.
Proġetti u bords/api/projects, /api/tasks, /api/iterationsTraċċar tax-xogħol: bords u kolonni taħt proġett, tiketti fuqhom, u iterazzjonijiet fuq dawn.
Għarfien/api/knowledge-baseSpazji ta’ paġni u fajls bil-verżjonijiet, bil-kummenti, bil-backlinks u bit-tfittxija.
Posta/api/mail, /api/mailbox-connectionsKaxxi tal-posta konnessi, kaxxi tal-posta tal-aġenti, u abbozzi li aġent ikteb għal persuna biex tapprovahom.
Approvazzjonijiet/api/approvalsIl-kju ta’ azzjonijiet li aġent ma jistax jieħu waħdu, u s-sejħa waħda li tirrisolvi dawn.
Awditu/api/audit-logIt-traċċa tal-awditu tal-organizzazzjoni, b’katina ta’ hash, b’endpoint tal-verifika. Għall-proprjetarji u l-admins.
Spejjeż u użu/api/ledger, /api/billingKontabilità tat-token u tal-ispejjeż, il-baġits u l-ħinijiet tat-tħaddim; separatament, il-krediti u t-top-ups. Għall-proprjetarji u l-admins.
Organizzazzjoni u timijiet/api/organizations, /api/teams, /api/usersAmministrazzjoni tat-tenant, tat-timijiet u tal-membership, inklużi l-inviti.
Triggers/api/triggersSkedi u webhooks li jibdew xogħol ta’ aġenti, bl-istorja tal-attivazzjonijiet tagħhom.
Sejħiet u vuċi/api/calls, /api/voiceSejħiet fil-kanal, u s-sessjoni tal-assistent vokali, it-trankrizzjoni tagħha u t-tokens tal-apparat.
Executors/api/executors, /api/execution-environment-templatesIl-magni fejn jaħdmu l-aġenti, l-ambjenti tagħhom, u l-kanal tal-ipparjar tad-daemon.
Runs/api/runsRuns ta’ aġenti li għaddejjin: ikkanċellar, tkomplija, erġa’ tibda, u rbit ma’ executor.
Tgħabbija/api/uploads, /api/attachmentsTgħabbi l-fajl l-ewwel, imbagħad għaqqad l-ID li jintbagħat lura ma’ messaġġ.
Tfittxija/api/messages/searchTfittxija fil-messaġġi, fuq l-organizzazzjoni kollha jew limitata għal kanal wieħed.
Sigrieti u impostazzjonijiet/api/secrets, /api/settings/scopedĦażna tal-kredenzjali li tinkiteb biss, b’drittijiet espliċiti, u valuri tal-konfigurazzjoni f’saffi.
Għodod konnessi/api/mcpIs-servers MCP li din l-istanza tisejjaħ. Ara MCP u għodod konnessi.
Saħħa/api/healthIl-ħajja u l-prontezza, it-tnejn pubbliċi. /api/health/ready jiċċekkja wkoll id-database.

Id-drittijiet jiġu infurzati għal kull rotta, mhux għal kull familja. B’mod wiesa’: il-log tal-awditu, il-ledger tal-ispejjeż, ir-regoli tal-politika u l-control plane tal-inferenza huma superfiċji għall-proprjetarji u l-admins tal-organizzazzjoni, filwaqt li l-konverżazzjonijiet, il-proġetti, l-għarfien u l-approvazzjonijiet huma miftuħa għal kull membru u limitati skont dak li dan il-membru verament jista’ jara.

Eżempji pprattikati

Idħol u żomm il-cookie tat-tiġdid

Fuq istanza fil-modalità local, b’password. It-token tal-aċċess jiġi lura fil-kontenut; it-token tat-tiġdid jidħol fil-kontenitur tal-cookies.

curl -sS https://api.example.com/api/auth/session \
  --cookie-jar nessie.cookies \
  -H 'Content-Type: application/json' \
  -d '{"email":"ada@example.com","password":"…"}'
{
  "data": {
    "token": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9…",
    "me": {
      "user": {
        "id": "1d4e…",
        "email": "ada@example.com",
        "displayName": "Ada Lovelace",
        "roleIds": ["owner"],
        "superAdmin": false
      },
      "session": {
        "sessionId": "9c07…",
        "issuedAt": "2026-09-16T09:00:00.000Z",
        "expiresAt": "2026-09-16T09:30:00.000Z"
      },
      "context": {
        "organizationId": "5a81…",
        "projectId": "7b12…",
        "teamId": "2e60…",
        "channelId": null,
        "bootstrapMode": false
      },
      "auth": {
        "providerId": "local",
        "providerType": "local-bootstrap",
        "autoRedirectToSso": false
      }
    }
  }
}

Meta t-token jiskadi, ibdel l-cookie b’waħda ġdida:

curl -sS -X POST https://api.example.com/api/auth/refresh \
  --cookie nessie.cookies --cookie-jar nessie.cookies

Ir-risposta hija l-istess forma { token, me }, u l-kontenitur tal-cookies issa fih it-token tat-tiġdid irrotat.

Elenka il-kanali li tista’ tara

curl -sS https://api.example.com/api/channels \
  -H "Authorization: Bearer $TOKEN"
{
  "data": [
    {
      "id": "8b2f…",
      "label": "engineering",
      "type": "standard",
      "visibility": "public",
      "projectId": "…",
      "projectName": "Platform",
      "teamId": "…",
      "defaultThreadId": "c41a…",
      "unreadCount": 3,
      "lastMessageAt": "2026-09-15T18:22:07.441Z",
      "viewerCanManage": true
    }
  ]
}

Żid ?teamId=… biex tillimita għal tim wieħed, jew ?includeArchived=true biex tinkludi kanali arkivjati. Il-defaultThreadId huwa t-thread li fih tibgħat li jmiss.

Ibgħat messaġġ

Messaġġ irid ikollu xi content jew mill-anqas attachment imgħobbi wieħed. Ibgħatu Idempotency-Key, u talba mtennija tirriżolvi għall-messaġġ li l-ewwel tentattiv ħoloq, minflok ma tibgħat kopja t-tieni.

curl -sS https://api.example.com/api/threads/c41a…/messages \
  -H "Authorization: Bearer $TOKEN" \
  -H 'Content-Type: application/json' \
  -H 'Idempotency-Key: 0f9c2d16-8f4a-4c1e-9a77-6b0d4f2e1a53' \
  -d '{"content":"Deploying the migration now."}'

Messaġġ ġdid huwa 201:

{
  "data": {
    "message": {
      "id": "d70e…",
      "threadId": "c41a…",
      "role": "user",
      "content": "Deploying the migration now.",
      "createdAt": "2026-09-16T09:04:11.882Z"
    },
    "pendingAgentInvites": []
  }
}

Talba mtennija bl-istess idempotency key twieġeb b’200 bil-messaġġ oriġinali u b’array pendingAgentInvites vojta, għax l-ewwel tentattiv diġà għamel l-avviżi u d-dispatch li dik l-array tiddeskrivi.

Żewġ rifjuti f’din ir-rotta jistħoqqilhom attenzjoni espliċita. Kontenut li jaqbeż il-limitu tat-tul tal-chat jiġi 413 MESSAGE_TOO_LARGE, u r-risposta t-tajba hija li tgħabbi t-test bħala fajl minflok. Kontenut li strutturalment jidher bħal kredenzjali jiġi 422 SECRET_INTERCEPTED — is-server jirrifjuta qabel ma l-messaġġ jinħażen, jiġi mgħoddi lill-aġenti jew jiġi rreġistrat, u l-kredenzjali għandhom jinħażnu f’/api/secrets.