Logga in Starta kostnadsfri provperiod

Hämta Era artiklar.
Publicera dem på Ert sätt.

Varje artikel vi skriver åt Er kan läsas över HTTP: titeln, metadata, Markdown, HTML, huvudbilden och FAQ:n. Ta in dem i Er Next.js-, Astro- eller anpassade webbplats när Er build körs, publicera dem och tala om för oss vilken adress var och en hamnade på.

En bearer-token. JSON in, JSON ut. Ingen SDK att installera och inget att konfigurera utöver en nyckel.

Webhooken pushar. API:et låter er hämta.

De bär samma artikel i samma form, så en parser som skrivits för den ena läser den andra utan ändringar. Skillnaden är vem som startar kommunikationen.

Webhooken, när er webbplats kan ta emot ett inlägg när som helst

Vi anropar er endpoint i samma stund som en artikel är klar, och igen när den ändras. Inget att polla, inget att schemalägga. WordPress, Shopify, Ghost, en Zapier-utlösare eller en route som ni själva har skrivit.

API:et, när er webbplats byggs och driftsätts som en enhet

En statisk webbplats kan inte ta emot ett inlägg halv sju på morgonen, något måste byggas om först. Så Er build frågar vad som väntar, hämtar det och talar sedan om adressen för oss efteråt. Ni väljer när.

Båda, om Ni vill ha dem

De är separata anslutningar och ingen av dem utesluter den andra. En webhook som matar ett nyhetsbrev och ett API som matar webbplatsen är en normal lösning.

En nyckel, skickad som en bearer-token.

Skapa en nyckel i instrumentpanelen under Settings, sedan Connections. Den visas en gång, när den skapas, eftersom bara dess hash lagras: om Ni tappar bort den, återkalla den och skapa en ny. En nyckel läser varje webbplats på kontot och återkallas från samma skärm.

Varje förfrågan

Authorization: Bearer sns_live_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
Accept: application/json

Kontrollera att det fungerar

curl https://seonis.ai/api/v1/me \
  -H "Authorization: Bearer $SEONIS_API_KEY"
{
  "organisation": { "id": 12, "name": "Peppervale", "country": "GB" },
  "key": {
    "name": "Production build",
    "prefix": "sns_live_ab",
    "created_at": "2026-09-06T09:12:44+00:00",
    "last_used_at": "2026-09-06T09:31:02+00:00"
  },
  "sites": 2
}

Hastighetsgräns

120 förfrågningar per minut, räknat mot nyckeln i stället för adressen den kommer från, eftersom build-runners delar adresser. Över det får Ni 429 med standardhuvudena Retry-After och X-RateLimit. Att hämta artiklar för en build är en handfull förfrågningar, så detta är inte en gräns Ni bör nå av misstag.

Håll nyckeln borta från Ert repository

Den läser allt vi har skrivit för Ert konto, inklusive artiklar som ännu inte är publicerade. Lägg den i Er build-miljö, inte i Er källkod. Återkalla den här så fort den finns någonstans där den inte ska vara, så får allt som använder den omedelbart 401.

Fem stycken, och fyra läser bara.

Allt ligger under /api/v1/. Versionen finns i sökvägen från första dagen, så en v2 kan finnas en dag utan att bryta det Ni skriver i dag.

GET /api/v1/me

Kontot som nyckeln tillhör, och nyckelns eget namn och prefix. Framför allt användbart för en sak: att tala om för er att nyckeln i denna miljö är den nyckel ni tror att det är.

Exempel

curl https://seonis.ai/api/v1/me \
  -H "Authorization: Bearer $SEONIS_API_KEY"
GET /api/v1/sites

Varje webbplats på kontot. id är det som artikellistan filtrerar på, och domänen finns där så att ett build-skript kan matcha mot något det redan känner till i stället för att bära med sig ett id.

Exempel

curl https://seonis.ai/api/v1/sites \
  -H "Authorization: Bearer $SEONIS_API_KEY"
{
  "sites": [
    {
      "id": 5,
      "name": "Peppervale",
      "domain": "peppervale.co.uk",
      "url": "https://peppervale.co.uk",
      "language": "en",
      "country": "GB",
      "market": "en-GB",
      "status": "active",
      "articles_published": 34,
      "created_at": "2026-06-02T11:04:19+00:00"
    }
  ]
}
GET /api/v1/articles

En sida med artiklar, senaste ändring först, utan själva texten. Sorterad efter när varje artikel senast ändrades snarare än när den skrevs, vilket är det som gör updated_since användbar: en artikel som redan är live kan redigeras senare, när en länk läggs in i den eller tas bort igen.

Frågeparametrar

Namn Vad det gör
site_id En webbplats, från /sites. Ett id som inte finns på Ert konto svarar 404.
status En av draft, qa, needs_repair, review, ready, published, failed. Allt annat är 422 i stället för en tom sida. "ready" är vad en build vill ha: skriven, kontrollerad och ännu inte någonstans.
updated_since ISO 8601, till exempel 2026-09-06T00:00:00Z. Kom ihåg tidsstämpeln för Er senaste körning och skicka tillbaka den vid nästa.
per_page Upp till 100. Standardvärdet är 25.
page Från 1. meta.has_more anger om Ni ska begära en till.

Exempel

curl -G https://seonis.ai/api/v1/articles \
  -H "Authorization: Bearer $SEONIS_API_KEY" \
  -d site_id=5 \
  -d status=ready \
  -d updated_since=2026-09-01T00:00:00Z \
  -d per_page=50
{
  "articles": [
    {
      "id": 918,
      "site_id": 5,
      "language": "en",
      "status": "ready",
      "title": "How to choose a pepper grinder",
      "slug": "how-to-choose-a-pepper-grinder",
      "meta_title": "How to choose a pepper grinder | Peppervale",
      "meta_description": "Burr or blade, ceramic or steel: what matters in a grinder.",
      "meta_keywords": ["pepper grinder", "burr grinder"],
      "tags": ["Kitchen"],
      "excerpt": "A burr grinder gives an even grind; a blade one does not.",
      "key_takeaways": ["A burr grinder gives an even grind; a blade one does not."],
      "faq": [{ "question": "Ceramic or steel?", "answer": "Steel for pepper, ceramic for salt." }],
      "hero_image": { "url": "https://seonis.ai/storage/images/5/918.jpg", "alt": "A pepper grinder" },
      "infographic_url": null,
      "word_count": 1812,
      "published_url": null,
      "published_at": null,
      "updated_at": "2026-09-06T06:31:12+00:00",
      "created_at": "2026-09-05T02:14:55+00:00",
      "quality": { "seo_score": 88, "language_score": 96, "language_findings": [] }
    }
  ],
  "meta": { "page": 1, "per_page": 50, "total": 1, "last_page": 1, "has_more": false }
}
GET /api/v1/articles/{id}

En artikel, med allt som listan utelämnar: content_markdown, content_html, FAQ:n som schema.org JSON-LD redo att lägga in på sidan, och alla utbyteslänkar som artikeln innehåller.

Fältnamnen är med avsikt de som vår webhook skickar. Om ni redan har en webhook-mottagare läser samma parser detta.

Exempel

curl https://seonis.ai/api/v1/articles/918 \
  -H "Authorization: Bearer $SEONIS_API_KEY"
{
  "article": {
    "id": 918,
    "site_id": 5,
    "language": "en",
    "status": "ready",
    "title": "How to choose a pepper grinder",
    "slug": "how-to-choose-a-pepper-grinder",
    "meta_description": "Burr or blade, ceramic or steel: what matters in a grinder.",
    "content_markdown": "Grinders differ.\n\n## Burr or blade\n\nA **burr** grinder ...",
    "content_html": "<p>Grinders differ.</p>\n<h2>Burr or blade</h2> ...",
    "faq_schema": { "@context": "https://schema.org", "@type": "FAQPage", "mainEntity": [] },
    "hero_image": { "url": "https://seonis.ai/storage/images/5/918.jpg", "alt": "A pepper grinder" },
    "word_count": 1812,
    "published_url": null,
    "updated_at": "2026-09-06T06:31:12+00:00",
    "quality": { "seo_score": 88, "language_score": 96, "language_findings": [] },
    "exchange_links": []
  }
}
POST /api/v1/articles/{id}/published

Ni publicerar artikeln; här talar ni om adressen för oss. Det är den enda endpoint som ändrar något.

Det gör exakt det som en leverans vi själva gjorde gör: artikeln markeras som publicerad, Er månadsgräns räknar den, planposten stängs, alla utbyteslänkar i den får adressen som verifieraren har väntat på, och Er Facebook-sida meddelas om Ni har anslutit en. Utan detta anrop förblir artikeln redo för alltid och inget av det händer.

Exempel

curl -X POST https://seonis.ai/api/v1/articles/918/published \
  -H "Authorization: Bearer $SEONIS_API_KEY" \
  -H "Content-Type: application/json" \
  -d '{"url": "https://peppervale.co.uk/blog/how-to-choose-a-pepper-grinder"}'

Svar

200 Registrerat. Artikeln kommer tillbaka med sin nya status, published_at och published_url.
422 Url:en saknas eller är inte en fullständig http://- eller https://-adress.
409 Artikeln är inte redo att publiceras, eller är redan registrerad som publicerad. Artikeln kommer tillbaka med avslaget, så att ni kan se vilket som gäller.

Anslut "REST API" som Er publiceringsmotor.

Under Settings, sedan Publishing, finns en motor som heter "REST API: ni hämtar och publicerar". Den ber inte om något, eftersom det inte finns något för oss att skicka. Det den ändrar är vad som händer varje morgon: en färdig artikel förblir redo utan adress, och publiceringsskärmen säger att den väntar på att ni ska hämta den i stället för att visa en leverans som misslyckades.

Ni kan använda API:et utan att ansluta det: endpoints fungerar för alla konton med en nyckel. Att ansluta det är hur resten av produkten vet att den ska sluta förvänta sig en egen adress, och det är det som gör att en artikel som ni själva publicerar inte räknas som ett misslyckande.

Varje fel är JSON med ett meddelande.

Samma form hela vägen, oavsett om avslaget kom från nyckelkontrollen eller från valideraren, så att inget behöver tolka två.

{ "message": "That API key is not valid, or it has been revoked." }
Status Vad det betyder
401 Ingen nyckel, en nyckel som inte är vår eller en nyckel som har återkallats.
404 Ingen sådan artikel eller webbplats på detta konto. En annan kontos artikel svarar 404 i stället för 403: ett API som säger "det där är inte Ert" har bekräftat att saken finns.
409 Begäran var korrekt men artikeln är inte i ett tillstånd för det.
422 En parameter saknas eller är fel. Svaret innehåller ett errors-objekt som anger fältet, samt meddelandet.
429 Över hastighetsgränsen. Retry-After anger hur länge Ni ska vänta.

Vad ett byggsteg faktiskt gör.

#!/usr/bin/env bash
set -euo pipefail

# 1. What is finished and not yet on the site?
ready=$(curl -sG https://seonis.ai/api/v1/articles \
  -H "Authorization: Bearer $SEONIS_API_KEY" \
  -d site_id=5 -d status=ready -d per_page=100)

for id in $(echo "$ready" | jq -r '.articles[].id'); do
  # 2. Take the article, body and all.
  curl -s https://seonis.ai/api/v1/articles/$id \
    -H "Authorization: Bearer $SEONIS_API_KEY" \
    | jq -r '.article.content_markdown' > "content/posts/$id.md"

  # 3. Your build puts it live, and you know where it landed.
  slug=$(echo "$ready" | jq -r ".articles[] | select(.id==$id) | .slug")

  curl -s -X POST https://seonis.ai/api/v1/articles/$id/published \
    -H "Authorization: Bearer $SEONIS_API_KEY" \
    -H "Content-Type: application/json" \
    -d "{\"url\": \"https://peppervale.co.uk/blog/$slug\"}"
done

Skapa en nyckel och prova den.

Testperioden räcker för att läsa API:et: artiklarna som skrivs under den är riktiga artiklar, och de kommer tillbaka via dessa endpoints som alla andra.

Starta kostnadsfri provperiod