Skip to content
Dashboard

Articles

Create, list, and manage AI-generated SEO articles.

The Articles API lets you programmatically generate long-form SEO content, retrieve existing articles, and monitor generation progress. All endpoints require a valid API key. Article generation is asynchronous. Start a job with the generate endpoint, then poll the status endpoint until it reports is_complete.

There is no published status. A finished, published article has status cms. There is also no generating and no scheduled status. Filtering on any of those returns an empty list. This is the single most common mistake when integrating.

MethodEndpointDescription
GET/api/v1/articlesList articles (paginated, filterable)
GET/api/v1/articles/:idGet a single article with full content
POST/api/v1/articles/generateGenerate an article (1.5 credits, write permission)
GET/api/v1/articles/:id/statusCheck article generation status
GET/api/v1/articles

Returns a paginated list of your articles. Supports filtering by status, project, and search query. Results are sorted by creation date descending by default.

Query Parameters

NameTypeRequiredDescription
pageintegerOptionalPage number (1-indexed)(default: 1)
limitintegerOptionalResults per page (1-100)(default: 20)
statusstringOptionalFilter by status: draft, queued, cms, needs_editing, failed, archived. Note there is no "published" value, use cms.
project_iduuidOptionalFilter by project ID
searchstringOptionalSearch articles by title (case-insensitive partial match)
sortstringOptionalSort field: created_at, updated_at, title(default: created_at)
orderstringOptionalSort order: asc, desc(default: desc)
Request
curl "https://www.brainpercent.app/api/v1/articles?page=1&limit=10&status=cms" \
  -H "Authorization: Bearer bp_your_key"
200Response
{
  "success": true,
  "data": [
    {
      "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
      "title": "The Complete Guide to SEO in 2026",
      "slug": "complete-guide-seo-2026",
      "status": "cms",
      "meta_description": "Learn the latest SEO strategies and techniques for 2026...",
      "created_at": "2026-01-15T10:00:00Z",
      "updated_at": "2026-01-20T14:30:00Z",
      "project_id": "d290f1ee-6c54-4b01-90e6-d701748f0851"
    }
  ],
  "pagination": {
    "total": 42,
    "page": 1,
    "limit": 10,
    "total_pages": 5,
    "has_more": true
  }
}
GET/api/v1/articles/:id

Returns the full article row for a single article, including the rendered content. Returns 404 if the article does not exist or is not owned by your account.

Request
curl https://www.brainpercent.app/api/v1/articles/a1b2c3d4-e5f6-7890-abcd-ef1234567890 \
  -H "Authorization: Bearer bp_your_key"
200Response
{
  "success": true,
  "data": {
    "id": "a1b2c3d4-e5f6-7890-abcd-ef1234567890",
    "title": "The Complete Guide to SEO in 2026",
    "slug": "complete-guide-seo-2026",
    "status": "cms",
    "content": "<h2>Introduction</h2><p>Search engine optimization continues to evolve...</p>",
    "meta_description": "Learn the latest SEO strategies and techniques for 2026...",
    "project_id": "d290f1ee-6c54-4b01-90e6-d701748f0851",
    "created_at": "2026-01-15T10:00:00Z",
    "updated_at": "2026-01-20T14:30:00Z"
  }
}
POST/api/v1/articles/generate

Start asynchronous article generation. Returns the new article ID with an initial status of 'queued'. Poll /api/v1/articles/:id/status for progress. Requires write permission and costs 1.5 credits from your single account balance. project_id is required: the project supplies the brand, business context, and output language. In the 202 body, credits_deducted is the number of articles billed and credits_remaining is how many more articles your balance covers, so check GET /api/v1/user/credits for the balance itself.

Request Body

NameTypeRequiredDescription
topicstringRequiredThe article topic or title (3-500 characters)
project_iduuidRequiredThe project this article belongs to. Supplies the brand, business context, and output language.
keywordsstring[]OptionalTarget SEO keywords (max 20 items)
tonestringOptionalWriting tone: professional, casual, academic, conversational
word_countintegerOptionalTarget word count (300-5000)(default: 800)
Request
curl -X POST https://www.brainpercent.app/api/v1/articles/generate \
  -H "Authorization: Bearer bp_your_key" \
  -H "Content-Type: application/json" \
  -d '{
    "topic": "Content Marketing Strategies That Actually Convert",
    "project_id": "d290f1ee-6c54-4b01-90e6-d701748f0851",
    "keywords": ["content marketing", "conversion", "automation"],
    "tone": "professional",
    "word_count": 1200
  }'
202Response
{
  "success": true,
  "data": {
    "article_id": "f8c9d0e1-2345-6789-abcd-ef0123456789",
    "status": "queued",
    "job_id": "01JQ8Z3M4N5P6Q7R8S9T0U1V2W",
    "slug": "content-marketing-strategies-that-actually-convert",
    "language": "en",
    "credits_deducted": 1,
    "credits_remaining": 32,
    "estimated_time": "10-15 minutes",
    "poll_url": "/api/v1/articles/f8c9d0e1-2345-6789-abcd-ef0123456789/status"
  }
}
GET/api/v1/articles/:id/status

Check the generation progress of an article. Poll this endpoint after calling the generate endpoint until is_complete is true, or until the status is 'failed'. is_complete is true when the status is cms or needs_editing.

Request
curl https://www.brainpercent.app/api/v1/articles/f8c9d0e1-2345-6789-abcd-ef0123456789/status \
  -H "Authorization: Bearer bp_your_key"
200Response
{
  "success": true,
  "data": {
    "article_id": "f8c9d0e1-2345-6789-abcd-ef0123456789",
    "status": "queued",
    "title": "Content Marketing Strategies That Actually Convert",
    "slug": "content-marketing-strategies-that-actually-convert",
    "progress": 65,
    "is_complete": false,
    "created_at": "2026-02-01T12:00:00Z",
    "updated_at": "2026-02-01T12:04:32Z"
  }
}

Article Statuses

The status field is one of exactly six values:

StatusDescription
draftArticle exists but has not been published.
queuedGeneration job has been accepted and is running. Poll the status endpoint.
cmsFinished and published. This is the terminal success state, there is no "published" status.
needs_editingGeneration finished but the article is flagged for review before it goes live. Counts as complete.
failedGeneration failed.
archivedArticle has been archived and is no longer part of the active set.

published, generating, and scheduled are not article statuses. Use cms for published articles and queued for in-flight generations.

Permissions & Scopes

Each endpoint requires specific API key permissions and the articles scope.

EndpointPermissionScope
GET /api/v1/articlesreadarticles
GET /api/v1/articles/:idreadarticles
POST /api/v1/articles/generatewritearticles
GET /api/v1/articles/:id/statusreadarticles

New keys are created with ["read"] by default. A key without the write permission receives a 403 from the generate endpoint.

Error Responses

Common error responses for article endpoints:

StatusCodeWhen
400VALIDATION_ERRORMissing topic or project_id, invalid tone, word_count outside 300-5000, more than 20 keywords
402INSUFFICIENT_CREDITSNot enough credits to cover the generation
403FORBIDDENAPI key lacks write permission or the articles scope
404NOT_FOUNDArticle or project does not exist, or is not owned by your account

Generation Flow

Article generation is asynchronous and typically takes 10 to 15 minutes. The flow is:

1. POST /articles/generate → returns 202 with article_id, status queued, and a poll_url
2. GET /articles/:id/status → poll until is_complete is true (30-second intervals are plenty)
3. Terminal states: cms or needs_editing (success), or failed
4. GET /articles/:id → retrieve the complete article with content

Response Field Reference

Fields returned in article responses:

FieldTypeDescription
iduuidUnique article identifier
titlestringGenerated article title
slugstringURL-friendly version of the title
statusstringOne of draft, queued, cms, needs_editing, failed, archived
contentstringArticle body (only in single-article responses)
meta_descriptionstringSEO meta description
project_iduuidProject the article belongs to
created_atdatetimeISO 8601 creation timestamp
updated_atdatetimeISO 8601 last update timestamp
progressintegerGeneration progress percentage (status endpoint only)
is_completebooleanTrue when status is cms or needs_editing (status endpoint only)