NAV
curl C# Dart Go Java JavaScript PHP Python Ruby Swift

curl C# Dart Go Java JavaScript PHP Python Ruby Swift API Docs

Introduction

This document is a detailed reference for our REST API. See our full documentation for tutorials on using Butter with your framework.

The ButterCMS API is organized around REST. Our API has predictable, resource-oriented URLs, and uses HTTP response codes to indicate API errors. JSON is returned by all API responses, including errors, although our API libraries convert responses to appropriate language-specific objects.

As you read these docs, a sample API Key will be used in the sample code, which you should replace with your own butter API key. If you don't yet have an account, create one free.

Run in Postman

Postman is a great tool for experiementing with our API. We wrote a post about it here. Once you've installed Postman, click this button to quickly add our end point Collection to your Postman.

Run in Postman

Authentication

curl -X GET 'https://api.buttercms.com/v2/posts/?auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"
var butter = require('buttercms')("your_api_token");
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
<?
use ButterCMS\ButterCMS;
$butter = new ButterCMS('your_api_token');
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
using ButterCMS;
var butterClient = new ButterCMSClient("your_api_token");
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

OR

var butter = Butter('your_api_token');
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

// In Swift, you can also override the default false setting
// for preview mode at the client level. 
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY", previewMode: true)

// For custom sessions:
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY", urlSession: yourURLSession)

Read API Authentication

Authentication to the API is performed by passing your api token via the auth_token parameter on every request: ?auth_token=your_api_token. You can access your API token from your settings page.

Requests made with a missing or invalid token will get a 401 Unauthorized response. All requests must be made over HTTPS.

Write API Authentication

The API token you use for reading from the ButterCMS API will not allow you to create content in the API. For this you will need to use a different write-enabled token. Chat or email support@buttercms.com to get yours.

Set the Authorization header to Token your_write_api_token_here rather than using a query string parameter.

Your write-enabled token should never be used anywhere it would be exposed, e.g. in client-side JavaScript.

Errors

Butter CMS uses conventional HTTP response codes. Codes in the 2xx range indicate success, codes in the 4xx range indicate an error that failed given the information provided and codes in the 5xx range indicate an error with Butter's servers (these are rare).

Code Description
200 Success.
400 Bad request, often due to missing a required parameter.
401 No valid API key provided.
404 The requested resource doesn't exist.

Write API

We have a Write / POST API that allows you to programmatically create content. This can enable many powerful use cases and allow you to scale your content faster than ever.

Refer to these sections to see how to format your API requests when creating content:

Write Authentication

The API token you use for reading from the ButterCMS API will not allow you to create content in the API. For this you will need to use a different write-enabled token. Chat or email support@buttercms.com to get yours.

Set the Authorization header to Token your_write_api_token rather than using a query string parameter.

Your write-enabled token should never be used anywhere it would be exposed, e.g. in client-side JavaScript.

Pages

Quickly launch a new marketing site or add pages to your existing one using our Pages end points.

The Page Object

Attribute Description
slug string Unique identifier
name string Name of the Page
published timestamp Timestamp of when the page was first published
updated timestamp Timestamp of when the page was most recently published
scheduled timestamp Timestamp of when the page is scheduled to be published. If not scheduled, this field will be null. Scheduled timestamps do not use fractional seconds.
status status Status of the current version of the page. Possible values are published, draft, scheduled.
page_type string API slug identifier of the page_type for the Page
fields string fields contains all of the actual content for the Page

Create Page via Write API

Create Page WITHOUT Locales or with a Single Locale

(Add locale to query params if single locale, or use multi-locale format)

curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "headline": "Frequently Asked Questions",
    "hero_image": "",
    "body": "<p class=\"content\">We love questions</p>",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
    }]
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "headline": "Frequently Asked Questions",
    "hero_image": "",
    "body": "<p class=\"content\">We love questions</p>",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
    }]
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "headline": "Frequently Asked Questions",
    "hero_image": "",
    "body": "<p class=\"content\">We love questions</p>",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
    }]
  }
}'
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "headline": "Frequently Asked Questions",
      "hero_image": "",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
      }]
   }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

let payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "headline": "Frequently Asked Questions",
      "hero_image": "",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
      }]
   }
}

fetch('https://api.buttercms.com/v2/pages/', {
  method: 'POST',
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
    {
        "title": "Frequently Asked Questions",
        "slug": "faq",
        "page-type": "questions",
        "fields": {
          "headline": "Frequently Asked Questions",
          "hero_image": "",
          "body": "<p class=\"content\">We love questions</p>",
          "questions": [{
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }, {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }]
      }
    }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/pages/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
<?php
$url = "http://api.buttercms.com/v2/pages/";

$payload = array(
    "title" => "Frequently Asked Questions",
    "slug" => "faq34",
    "page-type" => "questions",
    "fields" => array(
      "headline" => "Frequently Asked Questions",
      "hero_image" => "",
      "body" => "<p class=\"content\">We love questions</p>",
      "questions" => [array(
        "question" => "Are dogs allowed?",
        "answer" => "Leashed dogs are allowed.",
        "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      ), array(
        "question" => "Are wallabies allowed?",
        "answer" => "Yes, leashed wallabies are allowed",
        "picture" => "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
      )]
    )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>
import requests

payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "headline": "Frequently Asked Questions",
      "hero_image": "",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }, {
        "question": "Are wallabies allowed?",
        "answer": "Yes, leashed wallabies are allowed",
        "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
      }]
   }
}

response = requests.post("https://api.buttercms.com/v2/pages/", json=payload, headers={"Authorization": "Token your_write_api_token" })

import 'dart:convert' as convert;
import 'package:http/http.dart' as http;


void main() async{
    Map payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "headline": "Frequently Asked Questions",
        "hero_image": "",
        "body": "<p class=\"content\">We love questions</p>",
        "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }, {
          "question": "Are wallabies allowed?",
          "answer": "Yes, leashed wallabies are allowed",
          "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
        }]
    }
  };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/pages/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
var payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "headline": "Frequently Asked Questions",
    "hero_image": "",
    "body": "<p class=\"content\">We love questions</p>",
    "questions": [{
      "question": "Are dogs allowed?",
      "answer": "Leashed dogs are allowed.",
      "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }, {
      "question": "Are wallabies allowed?",
      "answer": "Yes, leashed wallabies are allowed",
      "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
    }]
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Create Page WITH Locales

(Can use this format for one or more locales at the same time)

curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "en": {
        "headline": "Frequently Asked Questions",
        "body": "<p class=\"content\">We love questions</p>",
        "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }],
      },
      "es": {
        "headline": "Preguntas frecuentes",
        "body": "<p class=\"content\">Nos encantan las preguntas</p>",
        "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      }
   }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

let payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "en": {
        "headline": "Frequently Asked Questions",
        "body": "<p class=\"content\">We love questions</p>",
        "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }],
      },
      "es": {
        "headline": "Preguntas frecuentes",
        "body": "<p class=\"content\">Nos encantan las preguntas</p>",
        "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      }
   }
}

fetch('https://api.buttercms.com/v2/pages/', {
  method: 'POST',
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));

import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "title": "Frequently Asked Questions",
        "slug": "faq",
        "page-type": "questions",
        "fields": {
          "en": {
            "headline": "Frequently Asked Questions",
            "body": "<p class=\"content\">We love questions</p>",
            "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
            }],
          },
          "es": {
            "headline": "Preguntas frecuentes",
            "body": "<p class=\"content\">Nos encantan las preguntas</p>",
            "questions": [{
              "question": "Se admiten perros?",
              "answer": "Se permiten perros con correa.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
            }]
          }
        }
      }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/pages/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

<?php
$url = "http://api.buttercms.com/v2/pages/";

$payload = array(
    "title" => "Frequently Asked Questions",
    "slug" => "faq34",
    "page-type" => "questions",
    "fields" => array(
      "en" => array(
        "headline" => "Frequently Asked Questions",
        "body" => "<p class=\"content\">We love questions</p>",
        "questions" => [array(
          "question" => "Are dogs allowed?",
          "answer" => "Leashed dogs are allowed.",
          "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        )],
       ),
      "es" => array(
        "headline" => "Preguntas frecuentes",
        "body" => "<p class=\"content\">Nos encantan las preguntas</p>",
        "questions" => [array(
          "question" => "Se admiten perros?",
          "answer" => "Se permiten perros con correa.",
          "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        )]
      )
   )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
>

import requests

payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "en": {
        "headline": "Frequently Asked Questions",
        "body": "<p class=\"content\">We love questions</p>",
        "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      },
      "es": {
        "headline": "Preguntas frecuentes",
        "body": "<p class=\"content\">Nos encantan las preguntas</p>",
        "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      }
   }
}

response = requests.post("https://api.buttercms.com/v2/pages/", json=payload, headers={"Authorization": "Token your_write_api_token" })

import 'dart:convert' as convert;
import 'package:http/http.dart' as http;


void main() async{
    Map payload = {
        "title": "Frequently Asked Questions",
        "slug": "faq",
        "page-type": "questions",
        "fields": {
          "en": {
            "headline": "Frequently Asked Questions",
            "body": "<p class=\"content\">We love questions</p>",
            "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
            }]
          },
          "es": {
            "headline": "Preguntas frecuentes",
            "body": "<p class=\"content\">Nos encantan las preguntas</p>",
            "questions": [{
              "question": "Se admiten perros?",
              "answer": "Se permiten perros con correa.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
            }]
          }
      }
    };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/pages/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
var payload = payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "questions": [{
        "question": "Se admiten perros?",
        "answer": "Se permiten perros con correa.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Authentication

See the authentication section for details on how to authenticate your requests.

Making requests

Requests should be HTTP POST requests made to https://api.buttercms.com/v2/pages/, with the Content-Type header set to application/json.

The ButterCMS Write API allows you to send your request body in one of two formats when updating or creating Pages.

WITHOUT Locales or with a Single Locale

If you don't have locales, or if you are only updating a single locale's version of a page, you can format your request body into a JSON object like the example to the right, where fields is an array of objects in which each object represents a content list object with each of its fields created by key and value.

Note that if you are using this format to update only a single locale's version of a page, you must specify the locale via query param, e.g., ?locale=en.

WITH Locales

The second format is our multi-locale format, which can be used to update one or more locales of a page at the same time. In this format, the objects in each array have an extra level and must be first mapped to the locale code to use, as in the example to the right. The locale codes must already be configured in your account; however, you can pick and choose which locales to update.

Body Fields
Attribute Description
title Required. The title of the page.
slug Required. The slug of the page.
status Optional. Status of the update. Can be draft or published. Defaults to draft. Note that you cannot create a page with a status of scheduled via the write API.
page-type Required. The key of the page type.
locale Not applicable to accounts without locales. Set to the api slug of a pre-configured locale (e.g. en or fr).
fields Required. A dictionary object of your page fields and their values.

The fields attribute describes the page content itself.

Responses

A validated POST request will return a response with HTTP status code 202. Full page creation occurs asynchronously, meaning a successfully created page may not show immediately. Pages are validated prior to returning the API response but it is also possible that page creation may fail after returning a 202 response. If this happens please contact support.

The API will return HTTP status code 400 if your data does not pass the initial validation stage. This may happen if you are missing a field, missing a required field, or the remote URL for a media field returns a 404. Error explanations will be returned in a single JSON array.

Update Page via Write API

Update Page WITHOUT Locales

(Add locale to endpoint or payload if single locale)

curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}'
import requests


payload = {
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}

response = requests.patch("https://api.buttercms.com/v2/pages/*/faq/", json=payload, headers={"Authorization": "Token your_write_api_token" })

print(response.content)
require 'net/http'
require 'uri'
require 'json'


uri = URI.parse('https://api.buttercms.com/v2/pages/*/faq/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)


let payload = {
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}

fetch('https://api.buttercms.com/v2/pages/*/faq/', {
  method: 'PATCH',
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));


import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
      "status": "draft",
      "fields": {
        "headline": "Frequently Asked Questions Updated",
        "questions": [{
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        },
        {
            "question": "Another dog question",
            "answer": "Another dog answer",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      }
    }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/pages/*/faq/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}


import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "status": "draft",
      "fields": {
        "headline": "Frequently Asked Questions Updated",
        "questions": [{
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        },
        {
            "question": "Another dog question",
            "answer": "Another dog answer",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        }]
      };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.patch(
    url: 'https://api.buttercms.com/v2/pages/*/faq/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}


<?php
$url = "https://api.buttercms.com/v2/pages/*/faq/";
$payload = array(
      "status" => "draft",
      "fields" => array(
        "headline" => "Frequently Asked Questions Updated",
        "questions" => [array(
            "question" => "Are dogs allowed?",
            "answer" => "Leashed dogs are allowed.",
            "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        ),
        array(
            "question" => "Another dog question",
            "answer" => "Another dog answer",
            "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
        )]
      );

  $content = json_encode($payload);

  $curl = curl_init($url);
  curl_setopt($curl, CURLOPT_HEADER, false);
  curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
  curl_setopt($curl, CURLOPT_CUSTOMREQUEST, 'PATCH');
  curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

  $json_response = curl_exec($curl);

  curl_close($curl);
  $response = json_decode($json_response, true);

  print_r($response);
?>

var payload = {
  "status": "draft",
  "fields": {
    "headline": "Frequently Asked Questions Updated",
    "questions": [{
        "question": "Are dogs allowed?",
        "answer": "Leashed dogs are allowed.",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    },
    {
        "question": "Another dog question",
        "answer": "Another dog answer",
        "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
    }]
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/*/faq/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Update Page WITH Locales

(Can use this format for one or more locales at the same time)

curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions Updated",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      },
      {
          "question": "Another dog question",
          "answer": "Another dog answer",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;


void main() async {
  Map payload = {
      "status": "draft",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions Updated",
          "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          },
          {
              "question": "Another dog question",
              "answer": "Another dog answer",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }]
        }
      }
    };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.patch(
    url: 'https://api.buttercms.com/v2/pages/*/faq/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}

 import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)


func main() {
  payload := strings.NewReader(`
      {
      "status": "draft",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions Updated",
          "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          },
          {
              "question": "Another dog question",
              "answer": "Another dog answer",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }]
        }
      }
    }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/pages/*/faq/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
curl -X PATCH \
  'https://api.buttercms.com/v2/pages/*/faq/' \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions Updated",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      },
      {
          "question": "Another dog question",
          "answer": "Another dog answer",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'

let payload = {
      "status": "draft",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions Updated",
          "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          },
          {
              "question": "Another dog question",
              "answer": "Another dog answer",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }]
        }
      }
    }

  fetch('https://api.buttercms.com/v2/pages/*/faq/', {
    method: 'PATCH',
    headers: {
      "Authorization": "Token your_write_api_token",
      "Content-Type": "application/json",
    },
    body: JSON.stringify(payload),
  })
  .then(json => console.log(json))
  .catch(err => console.log("Request Failed", err));

<?php
$url = "https://api.buttercms.com/v2/pages/*/faq/";
$payload = array(
      "status" => "draft",
      "fields" => array(
        "en" => array(
          "headline" => "Frequently Asked Questions Updated",
          "questions" => [array(
              "question" => "Are dogs allowed?",
              "answer" => "Leashed dogs are allowed.",
              "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          ),
          array(
              "question" => "Another dog question",
              "answer" => "Another dog answer",
              "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
         )]
      )
    )
);

  $content = json_encode($payload);

  $curl = curl_init($url);
  curl_setopt($curl, CURLOPT_HEADER, false);
  curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
  curl_setopt($curl, CURLOPT_CUSTOMREQUEST, 'PATCH');
  curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

  $json_response = curl_exec($curl);

  curl_close($curl);
  $response = json_decode($json_response, true);

  print_r($response);
?>

import requests

payload =  {
      "status": "draft",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions Updated",
          "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          },
          {
              "question": "Another dog question",
              "answer": "Another dog answer",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }]
        }
      }
    }

response = requests.patch("https://api.buttercms.com/v2/pages/*/faq/", json=payload, headers={"Authorization": "Token your_write_api_token" })

print(response.content)

require 'net/http'
require 'uri'
require 'json'


uri = URI.parse('https://api.buttercms.com/v2/pages/*/faq/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload =  {
      "status": "draft",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions Updated",
          "questions": [{
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          },
          {
              "question": "Another dog question",
              "answer": "Another dog answer",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }]
        }
      }
    }

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

var payload = {
  "status": "draft",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions Updated",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      },
      {
          "question": "Another dog question",
          "answer": "Another dog answer",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/*/faq/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can update existing Pages by using a PATCH request to /v2/pages/*/your-page-slug/ endpoint. In the body of the request you can specify one or more fields you'd like to update.

As in with creating pages, there are two data formats: one that mirrors the read API response, and can be used for either pages without locales or updating a single, specified locale for a page, and one that can be used for updating multiple locales at once.

You can also specify status of the update, which is by default "draft", to be "published" which will cause your update to go live immediately.

It's not currently possible to update the page title or slug via PATCH.

Writing Components via Write API

Adding Components via Write API

curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Frequently asked questions"
      },
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Preguntas frecuentes"
      },
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Frequently asked questions"
      },
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Preguntas frecuentes"
      },
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Frequently asked questions"
      },
      "body": "<p class=\"content\">We love questions</p>",
      "questions": [{
          "question": "Are dogs allowed?",
          "answer": "Leashed dogs are allowed.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "body": "<p class=\"content\">Nos encantan las preguntas</p>",
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg",
        "alt_text": "Preguntas frecuentes"
      },
      "questions": [{
          "question": "Se admiten perros?",
          "answer": "Se permiten perros con correa.",
          "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
      }]
    }
  }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }

  String body = convert.jsonEncode(payload);

  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/pages/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
    {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/pages/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }

  fetch('https://api.buttercms.com/v2/pages/', {
    method: 'POST',
    headers: {
      "Authorization": "Token your_write_api_token",
      "Content-Type": "application/json",
    },
    body: JSON.stringify(payload),
  })
  .then(json => console.log(json))
  .catch(err => console.log("Request Failed", err));

<?php

$url = "https://api.buttercms.com/v2/pages/";

$payload = array(
      "title" => "Frequently Asked Questions",
      "slug" => "faq",
      "page-type" => "questions",
      "fields" => array(
        "en" => array(
          "headline" => "Frequently Asked Questions",
          "body" => "<p class=\"content\">We love questions</p>",
          "sections" => [
            array(
              "question" => array(
                "question" => "Are dogs allowed?",
                "answer" => "Leashed dogs are allowed.",
                "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              )
            ),
            array(
              "question" => array(
                "question" => "Are wallabies allowed?",
                "answer" => "Yes, leashed wallabies are allowed",
                "picture" => "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              )
            ),
            array(
              "trivia" => array(
                "title" => "Pocket creatures",
                "body" => "Wallabies are marsupials. The keep their babies in their pouches"
              )
            )
          ]
       )
   )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
import requests

payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}

response = requests.post("https://api.buttercms.com/v2/pages/", json=payload, headers={"Authorization": "Token your_write_api_token" })


require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/')
header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Updating Components via Write API

curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "en": {
      "hero": { 
        "alt_text": "Questions and answers"
       }
    },
    "es": {
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
      }
    }
  }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "en": {
      "hero": { 
        "alt_text": "Questions and answers"
       }
    },
    "es": {
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
      }
    }
  }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/pages/*/faq/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "status": "draft",
  "fields": {
    "en": {
      "hero": { 
        "alt_text": "Questions and answers"
       }
    },
    "es": {
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
      }
    }
  }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "status": "draft",
      "fields": {
        "en": {
          "hero": { 
            "alt_text": "Questions and answers"
          }
        },
        "es": {
          "hero": {
            "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
          }
        }
      }
    }

  String body = convert.jsonEncode(payload);

  http.Response response = await http.patch(
    url: 'https://api.buttercms.com/v2/pages/*/faq/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
    payload := strings.NewReader(`
        {
        "status": "draft",
        "fields": {
          "en": {
            "hero": { 
              "alt_text": "Questions and answers"
            }
          },
          "es": {
            "hero": {
              "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
            }
          }
        }
      }
    `)

    req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/pages/*/faq/", payload)

    req.Header.Add("Authorization", "Token your_write_api_token")

    req.Header.Add("Content-type", "application/json")

    client := &http.Client{}

    resp, err := client.Do(req)

    if err != nil {
      log.Fatalln(err)
    }

    body, _ := ioutil.ReadAll(resp.Body)
    log.Println(string([]byte(body)))
}

let payload = {
    "status": "draft",
    "fields": {
      "en": {
        "hero": { 
          "alt_text": "Questions and answers"
        }
      },
      "es": {
        "hero": {
          "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
        }
      }
    }
  }

fetch('https://api.buttercms.com/v2/pages/', {
    method: 'PATCH',
    headers: {
      "Authorization": "Token your_write_api_token",
      "Content-Type": "application/json",
    },
    body: JSON.stringify(payload),
  })
  .then(json => console.log(json))
  .catch(err => console.log("Request Failed", err));
<?php
$url =  "https://api.buttercms.com/v2/pages/*/faq/";

$payload = array(
    "status" => "draft",
    "fields" => array(
      "en" => array(
        "hero" => array( 
          "alt_text" => "Questions and answers"
        )
      ),
      "es" => array(
        "hero" => array(
          "image" => "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
        )
      )
    )
  );

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_CUSTOMREQUEST, 'PATCH');
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
import requests

payload = {
    "status": "draft",
    "fields": {
      "en": {
        "hero": { 
          "alt_text": "Questions and answers"
        }
      },
      "es": {
        "hero": {
          "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
        }
      }
    }
  }

response = requests.patch("https://api.buttercms.com/v2/pages/*/faq/", json=payload, headers={"Authorization": "Token your_write_api_token" })


require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/*/faq/')
header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
    "status": "draft",
    "fields": {
      "en": {
        "hero": { 
          "alt_text": "Questions and answers"
        }
      },
      "es": {
        "hero": {
          "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
        }
      }
    }
  }

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

var payload = {
  "status": "draft",
  "fields": {
    "en": {
      "hero": { 
        "alt_text": "Questions and answers"
      }
    },
    "es": {
      "hero": {
        "image": "https://live.staticflickr.com/6005/5908020758_bcd2bdcec9_c_d.jpg"
      }
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/*/faq/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Component picker fields combine one or more pre-defined components in an ordered field. These can be added by including an array of component objects. In this example the questions repeater has been replaced with a component picker field with key of sections.

{ "type": "component_key", "fields": { "field_one": "field value", ... } }

{ "type": question", "fields": { "question": "Are dogs allowed?", "answer": "Leashed dogs are allowed.", "picture": "dog.jpg" } }

{ "question": { "question": "Are dogs allowed?", "answer": "Leashed dogs are allowed.", "picture": "dog.jpg" } }

Combining one or more predefined components

curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}
'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}
'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}
'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "title": "Frequently Asked Questions",
    "slug": "faq",
    "page-type": "questions",
    "fields": {
      "en": {
        "headline": "Frequently Asked Questions",
        "body": "<p class=\"content\">We love questions</p>",
        "sections": [
          {
            "question": {
              "question": "Are dogs allowed?",
              "answer": "Leashed dogs are allowed.",
              "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
            }
          },
          {
            "question": {
              "question": "Are wallabies allowed?",
              "answer": "Yes, leashed wallabies are allowed",
              "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
            }
          },
          {
            "trivia": {
              "title": "Pocket creatures",
              "body": "Wallabies are marsupials. The keep their babies in their pouches"
            }
          }
        ]
      }
    }
  }

  String body = convert.jsonEncode(payload);
  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/pages/',
    headers: {
      "Content-Type":"application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
    {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/pages/",, payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}
  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
let payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "body": "<p class=\"content\">We love questions</p>",
          "sections": [
            {
              "question": {
                "question": "Are dogs allowed?",
                "answer": "Leashed dogs are allowed.",
                "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
              }
            },
            {
              "question": {
                "question": "Are wallabies allowed?",
                "answer": "Yes, leashed wallabies are allowed",
                "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
              }
            },
            {
              "trivia": {
                "title": "Pocket creatures",
                "body": "Wallabies are marsupials. The keep their babies in their pouches"
              }
            }
          ]
        }
      }
    }

fetch("https://api.buttercms.com/v2/pages/", {
  method: 'POST',
  header: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?
$url = "https://api.buttercms.com/v2/pages/"
$payload = array(
  "title" => "Frequently Asked Questions",
  "slug" => "faq",
  "page-type" => "questions",
  "fields" => array(
    "en" => array(
      "headline" => "Frequently Asked Questions",
      "body" => "<p class=\"content\">We love questions</p>",
      "sections" => [
        array(
          "question" => array(
            "question" => "Are dogs allowed?",
            "answer" => "Leashed dogs are allowed.",
            "picture" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          )
        ),
        array(
          "question" => array(
            "question" => "Are wallabies allowed?",
            "answer" => "Yes, leashed wallabies are allowed",
            "picture" => "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          )
        ),
        array(
          "trivia" => array(
            "title" => "Pocket creatures",
            "body" => "Wallabies are marsupials. The keep their babies in their pouches"
          )
        )
      ]
    )
  )
)

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>
import requests

payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}

response = requests.post('https://api.buttercms.com/v2/pages/', json=payload, headers={"Authorization": "Token your_write_api_token" })
require 'net/http'
require 'uri'
require  'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/')
header = {
  "Content-Type": "application/json",
  "Authorization": "Token your_write_api_token"
}

payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

var payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "body": "<p class=\"content\">We love questions</p>",
      "sections": [
        {
          "question": {
            "question": "Are dogs allowed?",
            "answer": "Leashed dogs are allowed.",
            "picture": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg"
          }
        },
        {
          "question": {
            "question": "Are wallabies allowed?",
            "answer": "Yes, leashed wallabies are allowed",
            "picture": "https://farm2.staticflickr.com/1840/29120307158_a9586a58b1_m_d.jpg"
          }
        },
        {
          "trivia": {
            "title": "Pocket creatures",
            "body": "Wallabies are marsupials. The keep their babies in their pouches"
          }
        }
      ]
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

The pages write API supports adding components as well. Components, like the hero component in this example, map component field value to their respective field keys within a JSON object which is mapped to the component key in the field list.

The update API supports both creating and updating components, and updating individual component fields works the same way as updating individual page fields.

Component picker fields can be updated as well however, as with repeaters, they cannot be partially updated. If a component picker field is included in an update request the included contents will be used to overwrite the previous contents.

Updating Reference Fields via Write API

Updating References via Write API

curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  }
}'
curl -X POST \
  https://api.buttercms.com/v2/pages/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    },
    "es": {
      "headline": "Preguntas frecuentes",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "related_page": "example-page-slug",
          "tags": [1, 2, 3]
        }
      }
    }

  String body = convert.jsonEncode(payload);

  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/pages/',
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
    {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "related_page": "example-page-slug",
          "tags": [1, 2, 3]
        }
      }
    }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/pages/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "related_page": "example-page-slug",
          "tags": [1, 2, 3]
        }
      }
    }

  fetch('https://api.buttercms.com/v2/pages/', {
    method: 'POST',
    headers: {
      "Authorization": "Token your_write_api_token",
      "Content-Type": "application/json",
    },
    body: JSON.stringify(payload),
  })
  .then(json => console.log(json))
  .catch(err => console.log("Request Failed", err));

<?php

$url = "https://api.buttercms.com/v2/pages/";

$payload = array(
      "title" => "Frequently Asked Questions",
      "slug" => "faq",
      "page-type" => "questions",
      "fields" => array(
        "en" => array(
          "headline" => "Frequently Asked Questions",
          "related_page" => "example-page-slug",
          "tags" => [1, 2, 3]
       )
   )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
import requests

payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  }
}

response = requests.post("https://api.buttercms.com/v2/pages/", json=payload, headers={"Authorization": "Token your_write_api_token" })


require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/pages/')
header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
      "title": "Frequently Asked Questions",
      "slug": "faq",
      "page-type": "questions",
      "fields": {
        "en": {
          "headline": "Frequently Asked Questions",
          "related_page": "example-page-slug",
          "tags": [1, 2, 3]
        }
      }
    }

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "title": "Frequently Asked Questions",
  "slug": "faq",
  "page-type": "questions",
  "fields": {
    "en": {
      "headline": "Frequently Asked Questions",
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/pages/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Reference fields for Page Types and Collections can both be edited via the Pages Write API.

To edit a reference field pointing to a specific Page Type, provide a Page slug for a one-to-one relationship, e.g., "related_page": "example-page-slug", or a list of slugs for a one-to-many relationship, e.g., "related_pages: ["example-page-1-slug", "example-page-2-slug"].

To edit a reference field pointing to a Collection, provide the Collection Item ID for a one-to-one relationship, e.g., "tag": 123, and a list of Collection Item IDs for a one-to-many relationship, e.g., "tags: [1, 2].

For both Page Type and Collection reference fields, it is possible to remove the references by setting the field to "" (for one-to-one relationships), [] (for one-to-many relationships), or null (for either relationship type). However, if the field key is omitted in the request, which is only possible when updating a Page, the references will not change from their current values.

Previewing Pages

To give your marketers the ability to preview pages you will want to first configure the preview URL of your Page Type.

When your marketer clicks "Preview", they will get taken to that preview URL such as https://yoursite.com/the-page/?preview=1 with a preview=1 parameter appended.

Your application will then look for that preview=1 parameter and when detected, call the ButterCMS API with the same preview parameter. You can see this defined in our API docs when querying Pages.

Passing preview=1 to ButterCMS will cause the draft version of the Page content to be returned and thus displayed within your application, allowing your marketing team to see a full in-context preview of their draft changes.

Get a single Page

Example request

curl -X GET 'https://api.buttercms.com/v2/pages/<page_type_slug>/<page_slug>/?locale=en&preview=1&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"
params = {"locale": 'en', "preview": 1}
ButterCMS::Page.get('*', 'example-news-page', params)
var butter = require('buttercms')("your_api_token");

butter.page.retrieve('*', 
    'example-news-page', 
    {
        "locale": "en",
        "preview": 1
    }
).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
                            "locale": "en",
                            "preview":"1"
                            }
ButterCMS.GetPage("*", "example-news-page", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchPage('*', 'example-news-page', [
    'locale' => 'en',
    'preview' => 1
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.pages.get('*', 'example-news-page', {
    'locale': 'en',
    'preview': 1
})
using ButterCMS;
// Takes a generic PageType which is a class you define
// to match your ButterCMS config
var paramterDict = new Dictionary<string, string>() 
{
    {"preview", "1"},
    {"locale", "en"},
};

public class NewsPage
{
    public string seo_title { get; set; }
    public string seo_description { get; set; }
    public string seo_keywords { get; set; }
    public string title { get; set; }
    public string body { get; set; }
}

PageReponse<NewsPage> newsPage = butterClient.RetrievePage<NewsPage>("*", "example-news-page", paramterDict);
// Async
PageReponse<NewsPage> newsPage = await butterClient.RetrievePageAsync<NewsPage>("*",
                                                                                "example-news-page",
                                                                                paramterDict);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.page.retrieve('news', 'example-news-page', {
    'locale': 'en',
    'preview': 1
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#retrieve-a-single-page
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String, String> queryParams = new HashMap<String, String>() {{
  put("preview", "1")
}}
PageResponse<NewsPage> response = butterClient.getPage(
  "*", 
  "example-news-page",
  queryParams,
  NewsPage.class
  )
// Note: The swift SDK requires you to model the Page 
// schema as a Codable Struct and pass it to getPages API. 
// This allows the SDK to deserialize the page data for you.

private struct PageFields: Codable {
  var name: String
  var slug: String
  // ... continue building struct based on expected datatypes.
  // To see the expected data as a json, you can make a query using
  // the API endpoint to the left. 
  // See https://developer.apple.com/documentation/foundation/archives_and_serialization/encoding_and_decoding_custom_types for more details
}
import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getPage(
  slug:"example-news-page", 
  parameters: [
    .preview(value: 1),
    .locale(value: "en"),
    .levels(value: 2),
  ], 
  pageTypeSlug:"*",
  type: PageFields.self
) // {Do something with result}

Example response

{
  "data": {
    "slug": "example-news-page",
    "name": "Example News Page",
    "page_type": "news",
    "published": "2019-11-12T17:23:53.109696Z",
    "updated": "2020-10-22T20:07:52.965850Z",
    "fields": {
      "seo": {
        "title": "Example News Page",
        "description": "SEO Description",
        "keywords": "SEO, Keywords"
      },      
      "headline": "This is an example news page",
      "sections": [
        {
          "fields": {
            "headline": "...",
            "subheadline": "...",
            "call_to_action": "..."
          },
          "type": "hero"
        },
        {
          "fields": {
            "video_headline": "...",
            "video_link": "..."
          },
          "type": "product_video"
        }
      ]
    }
  }
}

Get a single Page using its slug.

API Endpoint

https://api.buttercms.com/v2/pages/<page_type>/?auth_token=your_api_token

Arguments
Argument Description
page_type Required. Use '*'. If limiting to a Page Type, use the Page Type slug (see below).
page_slug Required. The slug of the page.
preview Optional. Set to 1 to return the latest draft version of a page. Useful for previewing changes before publishing live. i.e. &preview=1. If you are trying to view a scheduled page for which the most recent page version is published, you must pass the preview parameter to see the scheduled changes.
locale Optional. Set to the api slug of your configured locale (e.g. en or fr). When omitted, this query parameter will default to your organization's default locale.
levels Optional. Defaults to 2. Defines the levels of relationships to serialize. See below.
Returns

A hash with a data property that contains the page matching the page slug.

Get multiple Pages (Single Pages)

Example request

curl -X GET 'https://api.buttercms.com/v2/pages/*/?preview=1&page=1&page_size=10&locale=en&levels=2&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"
params = { 
     "preview": 1,
     "page": 1,
     "page_size": 10,
     "locale": 'en',
     "levels": 2
} # optional
ButterCMS::Page.list('*', params)
var butter = require('buttercms')("your_api_token");
var params = {
    "preview": 1,
    "page": 1,
    "page_size": 10,
    "locale": 'en',
    "levels": 2
};

butter.page.list('*', params)
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
     "preview":"1",
     "page": "1",
     "page_size": "10",
     locale": "en",
     "levels": "2"
}
ButterCMS.GetPages("*", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchPages('*', [
     'preview' => '1',
     'page' => '1',
     'page_size' => '10',
     'locale' => 'en',
     'levels' => '2'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
params = {
     'preview': '1',
     'page': '1',
     'page_size': '10',
     'locale': 'en',
     'levels': '2'
}

client.pages.all('*', params)
// Takes a generic PageType which is a class you define
// to match your ButterCMS config
using ButterCMS;

public class BasePage
{
  ...
}

var paramterDict = new Dictionary<string, string>() 
{
    {"preview", "1"},
    {"page", "1"},
    {"page_size", "10"}
    {"locale", "en"},
    {"levels", "2"},
};

PagesResponse<BasePage> newsPages = butterClient.ListPages<BasePage>("*", 
    paramterDict
);

// Async
PagesResponse<BasePage> newsPages = await butterClient.ListPagesAsync<BasePage>("*",
    paramterDict
);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.page.list('*', {
     'preview': '1',
     'page': '1',
     'page_size': '10',
     'locale': 'en',
     'levels': '2'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#list-pages
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String, String> queryParams = new HashMap<String, String>() {{
    put("preview", "1");
    put("page", "1");
    put("page_size", "10");
    put("locale", "en");
    put("levels", "2");  
}};
PagesResponse<BasePage> response = butterClient.getPages(
  "*",
  queryParams,
  BasePage.class
)

// Note: The swift SDK requires you to model the Page Type 
// schema as a Codable Struct and pass it to getPages 
// API. This allows the SDK to deserialize the page data 
// for you.

// As such, although you can fetch all single pages from
// the API via a getPages call, the data returned would
// likely not match any codable struct configuration.

// There is no similar limitation for multiple pages of 
// a defined page type (see the entry, "Get multiple Pages
// (Page Type) below" or blog posts, which have a defined
// schema.)

Example response

{
  "meta": {
    "previous_page": null,
    "next_page": null,
    "count": 2
  },
  "data": [
    {
      "slug": "single-page-1",
      "page_type": null,
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "title": "This is a single page",
        "body": "<p>Single PAGE!</p>"
      }
    },
    {
      "slug": "single-page-2",
      "page_type": null,
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "title": "Amazing Single Page",
        "body": "<p>Another single page!</p>",
        "tag": "example",
        "genre": "api"
      }
    }
  ]
}

Single Pages (those without a Page Type) are used to represent unique pages on your site. For example your Homepage. To get a list of all of your Single Pages, for instance when creating your sitemap.xml, simply use '*' as the PageType slug.

API Endpoint

https://api.buttercms.com/v2/pages/*/?auth_token=your_api_token

Arguments
Argument Description
page_type Required. '*'.
preview Optional. Set to 1 to return the latest draft version of a page. Useful for previewing changes before publishing live. i.e. &preview=1. If you are trying to view a scheduled page for which the most recent page version is published, you must pass the preview parameter to see the scheduled changes.
page¹ Optional. Used for Paginating through result set.
page_size¹ Optional. Used for Paginating. Defines the number of results returned.
locale Optional. Set to the api slug of your configured locale (e.g. en or fr). When omitted, this query parameter will default to your organization's default locale.
levels Optional. Defaults to 2. Defines the levels of relationships to serialize. See below.
limit¹ Optional. Used for Paginating. Defines the number of results returned.
offset¹ Optional. Used for Paginating through result set.

¹ We support two types of pagination. You have to choose if you want to use page + page_size or limit + offset for getting entries. If you provide limit or offset we will ignore page and page_size.

Returns

A hash with a data property that contains an array with all single pages, and a meta property that contains pagination information.

Get multiple Pages (Page Type)

Example request

curl -X GET 'https://api.buttercms.com/v2/pages/<page_type>/?preview=1&fields.tag=example&fields.genre=api&order=title&page=1&page_size=10&locale=en&levels=2&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"
params = { 
     "preview": 1,
     "fields.tag": 'example',
     "fields.genre": 'api',
     "order": 'title',
     "page": 1,
     "page_size": 10,
     "locale": 'en',
     "levels": 2
} # optional
ButterCMS::Page.list('news', params)
var butter = require('buttercms')("your_api_token");
var params = {
    "preview": 1,
    "fields.tag": "example",
    "fields.genre": "api",
    "order": 'title',
    "page": 1,
    "page_size": 10,
    "locale": 'en',
    "levels": 2
};

butter.page.list('news', params)
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
     "preview":"1",
     "fields.tag": "example",
     "fields.genre": "api",
     "order": "title",
     "page": "1",
     "page_size": "10",
     locale": "en",
     "levels": "2"
}
ButterCMS.GetPages("news", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchPages('news', [
     'preview' => '1',
     'fields.tag' => 'example',
     'fields.genre' => 'api',
     'order' => 'title',
     'page' => '1',
     'page_size' => '10',
     'locale' => 'en',
     'levels' => '2'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
params = {
     'preview': '1',
     'fields.tag': 'example',
     'fields.genre': 'api',
     'order': 'title',
     'page': '1',
     'page_size': '10',
     'locale': 'en',
     'levels': '2'
}

client.pages.all('news', params)
// Takes a generic PageType which is a class you define
// to match your ButterCMS config
using ButterCMS;

public class NewsPage
{
    public string seo_title { get; set; }
    public string title { get; set; }
    public string body { get; set; }
    public string tag { get; set; }
    public string genre { get; set; }
}

var paramterDict = new Dictionary<string, string>() 
{
    {"preview", "1"},
    {"fields.tag", "example"},
    {"fields.genre", "api"},
    {"order", "title"},
    {"page", "1"},
    {"page_size", "10"}
    {"locale", "en"},
    {"levels", "2"}
};

PagesResponse<NewsPage> newsPages = butterClient.ListPages<NewsPage>("news", 
    paramterDict
);

// Async
PagesResponse<NewsPage> newsPages = await butterClient.ListPagesAsync<NewsPage>("news",
    paramterDict
);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.page.list('news', {
     'preview': '1',
     'fields.tag': 'example',
     'fields.genre': 'api',
     'order': 'title',
     'page': '1',
     'page_size': '10',
     'locale': 'en',
     'levels': '2'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#list-pages
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String, String> queryParams = new HashMap<String, String>(){{
  put("preview", "1");
  put("page", "1");
  put("page_size", "10");
  put("locale", "en");
  put("levels", "2");
}}
PagesResponse<NewsPage> response = butterClient.getPages(
  "news",
  queryParams,  
  NewsPage.class
)

import ButterCMSSDK

// Note: The swift SDK requires you to model the Page 
// schema as a Codable Struct and pass it to getPages API. 
// This allows the SDK to deserialize the page data for you.

private struct NewsPageFields: Codable {
  var name: String
  var slug: String
  // ... continue building struct based on expected datatypes.
  // To see the expected data as a json, you can make a query using
  // the API endpoint to the left. 
  // See https://developer.apple.com/documentation/foundation/archives_and_serialization/encoding_and_decoding_custom_types for more details
}

var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")
butter.getPages(
  parameters: [
    .preview(value: 1),
    .page(value: 1)
    .fields(key: "tag", value: "example")
    .fields(value: "genre", value: "api")
    .order(value: "title")
    .locale(value: "en"),
    .pageSize(value: 10),
    .levels(value: 2)
  ],
  pageTypeSlug:"news",
  type: NewsPageFields.self,
) // {do something with result ....}

Example response

{
  "meta": {
    "previous_page": null,
    "next_page": null,
    "count": 2
  },
  "data": [
    {
      "slug": "example-news-page",
      "name": "Example News Page",
      "page_type": "news",
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "seo": {
          "title": "Example News Page",
          "description": "SEO Description",
          "keywords": "SEO, Keywords"
        },      
        "headline": "This is an example news page",
        "tag": "example",
        "genre": "api",
        "sections": [
          {
            "fields": {
              "headline": "...",
              "subheadline": "...",
              "call_to_action": "..."
            },
            "type": "hero"
          }
        ]
      }
    },
    {
      "slug": "example-news-page-2",
      "name": "Example News Page 2",
      "page_type": "news",
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "seo": {
          "title": "Example News Page",
          "description": "SEO Description",
          "keywords": "SEO, Keywords"
        },      
        "headline": "This is another news page",
        "tag": "example",
        "genre": "api",
        "sections": [
          {
            "fields": {
              "video_headline": "...",
              "video_link": "..."
            },
            "type": "product_video"
          }
        ]
      }
    }
  ]
}

Page Types allow you to create many pages with the same structure. Get a list of all pages for a given Page Type using its slug.

API Endpoint

https://api.buttercms.com/v2/pages/<page_type>/?auth_token=your_api_token

Arguments
Argument Description
page_type Required. The slug of the type of pages you want to retrieve.
preview Optional. Set to 1 to return the latest draft version of a page. Useful for previewing changes before publishing live. i.e. &preview=1. If you are trying to view a scheduled page for which the most recent page version is published, you must pass the preview parameter to see the scheduled changes.
fields.key Optional. Filter the result set by the field and value. You can pass in multiple filters at once. i.e. &fields.category=news&fields.genre=finance . To filter on Reference or Component fields use dot notation. i.e. fields.hero.title= or fields.hero.reference.title=
order Optional. Can order by page level published, updated, or a content field of the Page Type. Defaults to ascending, preprend '-' to sort descending.
page¹ Optional. Used for Paginating through result set.
page_size¹ Optional. Used for Paginating. Defines the number of results returned.
locale Optional. Set to the api slug of your configured locale (e.g. en or fr). When omitted, this query parameter will default to your organization's default locale.
levels Optional. Defaults to 2. Defines the levels of relationships to serialize. See below.
limit¹ Optional. Used for Paginating. Defines the number of results returned.
offset¹ Optional. Used for Paginating through result set.

¹ We support two types of pagination. You have to choose if you want to use page + page_size or limit + offset for getting entries. If you provide limit or offset we will ignore page and page_size.

Returns

A hash with a data property that contains an array of pages matching the query, and a meta property that contains pagination information.

Search Pages

Example Request

curl -X GET 'https://api.buttercms.com/v2/pages/search/?query=buttercmsapi&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

pages = ButterCMS::Page.search("buttercmsapi", {
 "page_type": "news",
 "page": 1,
 "page_size": 10
})
var butter = require('buttercms')("your_api_token");

butter.page.search("buttercmsapi", {
    "page_type": "news",
    "page": 1,
    "page_size": 10
}).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
    "page_type": "news",
    "page": "1",
    "page_size": "10"
}
ButterCMS.SearchPages("buttercmsapi", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->searchPages('buttercmsapi', [
 'page_type' => 'news',
 'page' => 1,
 'page_size' => 10
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.pages.search('buttercmsapi', {
 'page_type': 'news',
 'page': 1,
 'page_size': 10
})
using ButterCMS;
PagesResponse pages =
  butterClient.SearchPages("buttercmsapi",
    page_type: "news",
    page: 1,
    pageSize: 10
  );
// We also support Async requests for all C# calls
PagesResponse caffeinePages =
  await butterClient.SearchPagesAsync(query: "buttercmsapi",
    page_type: "news",
    page: 3,
    pageSize: 5
  );
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.page.search("buttercmsapi", {
    'page_type'; 'news',
    'page': '1',
    'page_size': '10'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#pages
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("query","search term");
}}
PagesResponse pages = butterClient.getPageSearch(queryParams);
import ButterCMSSDK

// Note: The swift SDK requires you to model the Page 
// schema as a Codable Struct and pass it to searchPages API. 
// This allows the SDK to deserialize the page data for you. As such,
// the swift SDK pageSearch function is likely most useful when
// narrowing your search by Page Type, so that the data returned
// has a consistent structure.

// Note that for Swift, you'll want to pass page_type and 
// query inside of your parameters dictionary.

private struct SearchPageFields: Codable {
  var name: String
  var slug: String
  // ... continue building struct based on expected datatypes.
  // To see the expected data as a json, you can make a query using
  // the API endpoint to the left. 
  // See https://developer.apple.com/documentation/foundation/archives_and_serialization/encoding_and_decoding_custom_types for more details
}

var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")
butter.searchPages(
  parameters: [
    .preview(value: 1),
    .page(value: 1),
    .pageSize(value: 10),
    .pageType(value: "news"),
    .query(value: "buttercmsapi")
  ],
  type: SearchPageFields.self,
) // {do something with result ....}

Example response

{
  "meta": {
    "previous_page": null,
    "next_page": null,
    "count": 2
  },
  "data": [
    {
      "slug": "example-news-page",
      "name": "Example News Page",
      "page_type": "news",
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "seo": {
          "title": "Example News Page",
          "description": "SEO Description",
          "keywords": "SEO, Keywords"
        },
        "headline": "This is an example news page",
        "sections": [
          {
            "fields": {
              "headline": "...",
              "subheadline": "...",
              "call_to_action": "..."
            },
            "type": "hero"
          }
        ]
      }
    },
    {
      "slug": "example-news-page-2",
      "name": "Example News Page 2",
      "page_type": "news",
      "published": "2019-11-12T17:23:53.109696Z",
      "updated": "2020-10-22T20:07:52.965850Z",
      "fields": {
        "seo": {
          "title": "Example News Page",
          "description": "SEO Description",
          "keywords": "SEO, Keywords"
        },
        "headline": "This is another news page",
        "sections": [
          {
            "fields": {
              "video_headline": "...",
              "video_link": "..."
            },
            "type": "product_video"
          }
        ]
      }
    }
  ]
}

Returns a list of pages that match the search query. The pages are returned sorted by relevancy.

API Endpoint

https://api.buttercms.com/v2/pages/search/?query=&auth_token=your_api_token

Arguments
Argument Description
query Required. Search query
page_type Optional. The slug of the type of pages you want to limit your search to. Use * if you want to search only Single Pages (without a Page Type). If left empty, searching will not be limited to a specific Page Type.
locale Optional. Set to the api slug of your configured locale (e.g. en or fr). When omitted, this query parameter will default to your organization's default locale.
levels Optional. Defaults to 2. Defines the levels of relationships to serialize. See below.
page¹ Optional. Used for Paginating through result set.
page_size¹ Optional. Used for Paginating. Defines the number of results returned.
limit¹ Optional. Used for Paginating. Defines the number of results returned.
offset¹ Optional. Used for Paginating through result set.

¹ We support two types of pagination. You have to choose if you want to use page + page_size or limit + offset for getting entries. If you provide limit or offset we will ignore page and page_size.

Returns

A hash with a data property that contains an array of pages matching the query, and a meta property that contains pagination information.

If no results are found, the API returns an empty array: "data": []

Pages Reference Levels

Example Reference Response

// related_pages and tags are Reference fields
"fields": {
  "title": "...",
  "body": "...",
  "related_pages": [
    "/v2/pages/example-page-type/example-page-slug"
  ],
  "tags": [
    "/v2/content/?keys=artists[_id=1234]"
  ]

Using Reference fields, you can create relationships between a Page Type and another type of content (Page Type or Collection). These relationships can create heirarchies of content many levels deep and sometimes circular in nature (A references B which references A).

The most common case is for one Reference to exist (A references B) which means two levels of content, which is what we serialize by default. If you need more levels, specify that parameter. If you only need one level, you can specify levels=1 which also makes the response payload smaller.

When the level limit is reached, we return unique URIs for any unserialized objects.

Localization

Example Request

curl -X GET 'https://api.buttercms.com/v2/pages/news/locale=en&auth_token=your_api_token'

When Localization is enabled in your account, your Pages have a version for each locale specified. To query Pages based on locale, simply add locale= as a parameter. For example:

v2/pages/news/locale=en

The API slugs values for each locale are configured by you in your account.

Collections

Collections are tables of data to be referenced by Pages, extending the use cases that you can achieve with ButterCMS. Collections can also be queried from the API directly using its API key. You can also query multiple Collections at once.

Write API: Create Collection Item

Create Item WITHOUT Locales

curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
        ...
    ]
}'
curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
        ...
    ]
}'
curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
        ...
    ]
}'

import requests

payload = {
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
    ]
}

response = requests.post("https://api.buttercms.com/v2/content/", json=payload, headers={"Authorization": "Token your_write_api_token"})
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
    ]
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.post(
    url: "https://api.buttercms.com/v2/content/",
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
    },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "key": "collection_api_slug",
        "status": "published",
        "fields": [
            {
              "field1_key": "Field value",
              "field2_key": "Field value"
            },
        ]
      }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/content/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
    ]
}

fetch("https://api.buttercms.com/v2/content/", {
  method: "POST",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/";

$payload = array(
    "key" => "collection_api_slug",
    "status" => "published",
    "fields" => [
        array(
          "field1_key" => "Field value",
          "field2_key" => "Field value"
        ),
    ]
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/")
payload = {
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
        {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
    ]
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "key": "collection_api_slug",
  "status": "published",
  "fields": [
    {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  ]
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Create Item WITH Locales

curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
      {
      "en": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
      "es": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        }
      },
      ...
    ]
}'
curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
      {
      "en": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
      "es": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        }
      },
      ...
    ]
}'
curl -X POST \
  https://api.buttercms.com/v2/content/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "key": "collection_api_slug",
    "status": "published",
    "fields": [
      {
      "en": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        },
      "es": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        }
      },
      ...
    ]
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "key": "collection_api_slug",
      "status": "published",
      "fields": [
        {
        "en": {
            "field1_key": "Field value",
            "field2_key": "Field value"
          },
        "es": {
            "field1_key": "Field value",
            "field2_key": "Field value"
          }
        },
      ]
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.post(
    url: "https://api.buttercms.com/v2/content/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body
  );

  print(convert.jsonDecode(response.body));
}

import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "key": "collection_api_slug",
        "status": "published",
        "fields": [
          {
          "en": {
              "field1_key": "Field value",
              "field2_key": "Field value"
            },
          "es": {
              "field1_key": "Field value",
              "field2_key": "Field value"
            }
          },
        ]
      }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/content/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
  "key": "collection_api_slug",
  "status": "published",
  "fields": [
    {
    "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
    "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    },
  ]
}

fetch("https://api.buttercms.com/v2/content/", {
  method: "POST",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php 
$url = "https://api.buttercms.com/v2/content/";
$payload = array(
  "key" => "collection_api_slug",
  "status" => "published",
  "fields" => [
    array(
    "en" => array(
        "field1_key" => "Field value",
        "field2_key" => "Field value"
      ),
    "es" => array(
        "field1_key" => "Field value",
        "field2_key" => "Field value"
      )
    ),
  ]
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>
import requests

payload = {
  "key": "collection_api_slug",
  "status": "published",
  "fields": [
    {
    "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
    "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    },
  ]
}

response = requests.post("https://api.buttercms.com/v2/content/", json=payload, headers={"Authorization": "Token your_write_api_token"})

require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/")
payload =  {
  "key": "collection_api_slug",
  "status": "published",
  "fields": [
    {
    "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
    "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    },
  ]
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "key": "collection_api_slug",
  "status": "published",
  "fields": [
    {
    "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
    "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    }
  ]
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can create Collection items by using POST requests to the Butter /v2/content/ API endpoint.

Authentication

See the authentication section for details on how to authenticate your requests.

Making requests

Requests should be HTTP POST requests made to https://api.buttercms.com/v2/content/, with the Content-Type header set to application/json.

The structure of your request body is conditional on whether you have any configured locales (English, Spanish, etc).

WITHOUT Locales

If you don't have locales, your request body should be a JSON object like the example to the right. fields is an array of objects, where each object represents a content list object with each of its fields created by key and value.

WITH Locales

If you do have locales configured, the objects in each array have an extra level and must be first mapped to the locale code to use. See the example to the right. Locale codes must already be configured in your account, however it is not necessary that they are all used.

Body Fields
Attribute Description
key Required. The unique name for the Collection.
status Optional. Should be published or draft. Defaults to draft.
fields Required. An array of objects, where each object represents a collection item with each of its fields created by key and value.

Responses

A validated POST request will return a response with HTTP status code 202. Full Collection item creation occurs asynchronously, meaning a successfully created Collection item may not show immediately. Items are validated prior to returning the API response, but it is also possible that item creation may fail after returning a 202 response. If this happens please contact support.

The API will return HTTP status code 400 if your data does not pass the initial validation stage. This may happen if you are missing a field, missing a required field, or the remote URL for a media field is not a valid URL. Error explanations will be returned in a single JSON array.

Write API: Update Collection Item

Update the whole Item WITHOUT Locales

curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}'
curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}'
curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}'

import requests

payload = {
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}

response = requests.put("https://api.buttercms.com/v2/content/collection_api_slug/123/", json=payload, headers={"Authorization": "Token your_write_api_token"})
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.put(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "status": "published",
        "fields": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        }
      }
  `)

  req, err := http.NewRequest("PUT", "https://api.buttercms.com/v2/content/collection_api_slug/123/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "PUT",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";

$payload = array(
    "status" => "published",
    "fields" => array(
      "field1_key" => "Field value",
      "field2_key" => "Field value"
    )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_PUT, true);
curl_setopt($curl, CURLOPT_PUTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")
payload = {
    "status": "published",
    "fields": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Put.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "status": "published",
  "fields": {
    "field1_key": "Field value",
    "field2_key": "Field value"
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PUT"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Partial update WITHOUT Locales

curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}'

import requests

payload = {
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}

response = requests.patch("https://api.buttercms.com/v2/content/collection_api_slug/123/", json=payload, headers={"Authorization": "Token your_write_api_token"})
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.patch(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "status": "published",
        "fields": {
          "field2_key": "Field value"
        }
      }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/content/collection_api_slug/123/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "PATCH",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";

$payload = array(
    "status" => "published",
    "fields" => array(
      "field2_key" => "Field value"
    )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_PATCH, true);
curl_setopt($curl, CURLOPT_PATCHFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")
payload = {
    "status": "published",
    "fields": {
      "field2_key": "Field value"
    }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "status": "published",
  "fields": {
    "field2_key": "Field value"
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Update the whole Item WITH Locales

curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    }
}'
curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    }
}'
curl -X PUT \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value",
        "field2_key": "Field value"
      }
    }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "status": "published",
      "fields": {
        "en": {
            "field1_key": "Field value",
            "field2_key": "Field value"
        },
        "es": {
          "field1_key": "Field value",
          "field2_key": "Field value"
        }
      }
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.put(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body
  );

  print(convert.jsonDecode(response.body));
}

import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "status": "published",
        "fields": {
          "en": {
            "field1_key": "Field value",
            "field2_key": "Field value"
          },
          "es": {
            "field1_key": "Field value",
            "field2_key": "Field value"
          }
        }
      }
  `)

  req, err := http.NewRequest("PUT", "https://api.buttercms.com/v2/content/collection_api_slug/123/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
  "status": "published",
  "fields": {
    "en": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "PUT",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";
$payload = array(
  "status" => "published",
  "fields" => array(
    "en" => array(
      "field1_key" => "Field value",
      "field2_key" => "Field value"
    ),
    "es" => array(
      "field1_key" => "Field value",
      "field2_key" => "Field value"
    )
  )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_PUT, true);
curl_setopt($curl, CURLOPT_PUTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>
import requests

payload = {
  "status": "published",
  "fields": {
    "en": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  }
}

response = requests.put("https://api.buttercms.com/v2/content/collection_api_slug/123/", json=payload, headers={"Authorization": "Token your_write_api_token"})

require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")
payload =  {
  "status": "published",
  "fields": {
    "en": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Put.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "status": "published",
  "fields": {
    "en": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value",
      "field2_key": "Field value"
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PUT"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Partial update WITH Locales

curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value"
      }
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value"
      }
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "en": {
        "field2_key": "Field value"
      },
      "es": {
        "field1_key": "Field value"
      }
    }
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
      "status": "published",
      "fields": {
        "en": {
          "field2_key": "Field value"
        },
        "es": {
          "field1_key": "Field value"
        }
      }
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.patch(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body
  );

  print(convert.jsonDecode(response.body));
}

import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "status": "published",
        "fields": {
          "en": {
            "field2_key": "Field value"
          },
          "es": {
            "field1_key": "Field value"
          }
        }
      }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/content/collection_api_slug/123/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
  "status": "published",
  "fields": {
    "en": {
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value"
    }
  }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "PATCH",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";
$payload = array(
  "status" => "published",
  "fields" => array(
    "en" => array(
      "field2_key" => "Field value"
    ),
    "es" => array(
      "field1_key" => "Field value"
    )
  )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_PATCH, true);
curl_setopt($curl, CURLOPT_PATCHFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>
import requests

payload = {
  "status": "published",
  "fields": {
    "en": {
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value"
    }
  }
}

response = requests.patch("https://api.buttercms.com/v2/content/collection_api_slug/123/", json=payload, headers={"Authorization": "Token your_write_api_token"})

require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")
payload =  {
  "status": "published",
  "fields": {
    "en": {
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value"
    }
  }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "status": "published",
  "fields": {
    "en": {
      "field2_key": "Field value"
    },
    "es": {
      "field1_key": "Field value"
    }
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can update Collection items by using PUT and PATCH requests to the Butter /v2/content/<collection_key>/<item_id>/ API endpoint.

How to get <item_id>?

The ID used to compose the Item's URL can be found in the meta field on each individual item returned by /v2/content/ and /v2/content/<collection_key>/ API endpoints.

Making requests

Requests should be HTTP PUT (to update all fields) or PATCH (to update only a subset of fields) requests made to https://api.buttercms.com/v2/content/<collection_key>/<item_id>/, with the Content-Type header set to application/json.

The structure of your request body is conditional on whether you have any configured locales (English, Spanish, etc).

WITHOUT Locales

If you don't have locales, your request body should be a JSON object like the example to the right. fields is an object representing a content list object with each of its fields updated by key and value.

WITH Locales

If you do have locales configured, the object has an extra level and must be first mapped to the locale code to use. See the example to the right. Locale codes must already be configured in your account, however it is not necessary that they are all used.

Body Fields
Attribute Description
status Optional. Should be published or draft.
fields Required. An object representing a collection item with each of its fields created by key and value.

Responses

A validated PUT or PATCH request will return a response with HTTP status code 202. Full collection item update occurs asynchronously, meaning a successfully updated content may not show immediately. Content item fields are validated prior to returning the API response, but it is also possible that the update may fail after returning a 202 response. If this happens please contact support.

The API will return HTTP status code 400 if your data does not pass the initial validation stage. This may happen if you are missing a field, missing a required field, or if the remote URL for a media field is not a valid URL. Error explanations will be returned in a single JSON array.

Updating Collection Reference Fields via Write API

Updating References via Write API

curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}'
curl -X PATCH \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}'

import requests

payload = {
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}

response = requests.patch("https://api.buttercms.com/v2/content/collection_api_slug/123/", json=payload, headers={"Authorization": "Token your_write_api_token"})
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
  };

  String body = convert.jsonEncode(payload);
  http.Response response = await http.patch(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "status": "published",
        "fields": {
          "related_page": "example-page-slug",
          "tags": [1, 2, 3]
        }
      }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/content/collection_api_slug/123/", payload)

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}

let payload = {
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "PATCH",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  },
  body: JSON.stringify(payload)
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";

$payload = array(
    "status" => "published",
    "fields" => array(
      "related_page" => "example-page-slug",
      "tags" => [1, 2, 3]
    )
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_PATCH, true);
curl_setopt($curl, CURLOPT_PATCHFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")
payload = {
    "status": "published",
    "fields": {
      "related_page": "example-page-slug",
      "tags": [1, 2, 3]
    }
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)
var payload = {
  "status": "published",
  "fields": {
    "related_page": "example-page-slug",
    "tags": [1, 2, 3]
  }
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

Reference fields for Collections items that point to Page Types or Collections can be edited via the Collection item Write API.

To edit a reference field pointing to a specific Page Type, provide a Page slug for a one-to-one relationship, e.g., "related_page": "example-page-slug", or a list of slugs for a one-to-many relationship, e.g., "related_pages: ["example-page-1-slug", "example-page-2-slug"].

To edit a reference field pointing to a Collection, provide the Collection Item ID for a one-to-one relationship, e.g., "tag": 123, and a list of Collection Item IDs for a one-to-many relationship, e.g., "tags: [1, 2].

For both Page Type and Collection reference fields, it is possible to remove the references by setting the field to "" (for one-to-one relationships), [] (for one-to-many relationships), or null (for either relationship type). However, if the field key is omitted in the request, which is only possible when updating a Collection Item using PATCH, the references will not change from their current values.

Write API: Delete Collection Item

Delete a Collection Item

curl -X DELETE \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json'
curl -X DELETE \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json'
curl -X DELETE \
  https://api.buttercms.com/v2/content/collection_api_slug/123/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json'

import requests

response = requests.delete("https://api.buttercms.com/v2/content/collection_api_slug/123/", headers={"Authorization": "Token your_write_api_token"})
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  http.Response response = await http.delete(
    url: "https://api.buttercms.com/v2/content/collection_api_slug/123/",
    headers: {
      "Content-Type": "application/json",
      "Authorization": "Token your_write_api_token"
    }
  );
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  req, err := http.NewRequest("DELETE", "https://api.buttercms.com/v2/content/collection_api_slug/123/")

  req.Header.Add("Content-Type", "application/json")
  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }
}

fetch("https://api.buttercms.com/v2/content/collection_api_slug/123/", {
  method: "DELETE",
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json"
  }
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err))
<?php
$url = "https://api.buttercms.com/v2/content/collection_api_slug/123/";

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_DELETE, true);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);

?>
require 'net/http'
require 'uri'
require 'json'

uri = URI.parse("https://api.buttercms.com/v2/content/collection_api_slug/123/")

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Delete.new(uri.request_uri, header)

response = http.request(request)
// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/content/collection_api_slug/123/")
var request = URLRequest(url: requestUrl)
request.httpMethod = "DELETE"
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can delete a single Collection item by using DELETE request to the Butter /v2/content/<collection_key>/<item_id>/ API endpoint.

How to get <item_id>?

The ID used to compose the Item's URL can be found in the meta field on each individual item returned by /v2/content/ and /v2/content/<collection_key>/ API endpoints.

Making requests

Requests should be HTTP DELETE made to https://api.buttercms.com/v2/content/<collection_key>/<item_id>/, with the Content-Type header set to application/json and Authorization header set to Token your_write_api_token.

The request should have no body data.

Responses

A successful DELETE request will return a response with HTTP status code 204 (No content).

Full collection update occurs asynchronously, meaning a successfully deleted content may still show up for a short time.

The API will return HTTP status code 404 if the Collection item doesn't exist.

Retrieve a Collection

Example request

curl -X GET 'https://api.buttercms.com/v2/content/artists/?preview=1&fields.genre=Rock&order=name&page=1&page_size=10&locale=en&levels=2&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

params = { 
     "preview": 1, 
     "fields.genre": "Rock",
     "order": "name",
     "page": 1,
     "page_size": 10,
     "locale": "en",
     "levels": 2
} # optional

content = ButterCMS::Content.list('artists', params)
var butter = require('buttercms')("your_api_token");
var params = {
     "preview": 1,
     "fields.genre": "Rock",
     "page": 1, 
     "page_size": 10,
     "locale": "en",
     "levels": 2
};

butter.content.retrieve(['artists'], params)
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
     "preview":"1",
     "fields.genre": "Rock",
     "order": "name",
     "page": "1",
     "page_size": "10",
     "locale": "en",
     "levels": "2"
}

ButterCMS.GetContentFields([]string{"artists"},)
<?
use ButterCMS\ButterCMS;
$butter = new ButterCMS('your_api_token');
$butter->fetchContentFields(['artists'], [
 'preview' => '1',
 'fields.genre' => 'Rock',
 'order' => 'name',
 'page' => '1',
 'page_size' => '10',
 'locale' => 'en',
 'levels' => '2'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
params = {
 'preview': '1',
 'fields.genre': 'Rock',
 'order': 'name',
 'page': '1',
 'page_size': '10',
 'locale': 'en',
 'levels': '2'
}

client.content_fields.get(['artists'], params)
using ButterCMS;
// You can pass one or more keys at a time
var keys = new string[2] { "artists" };
var paramterDict = new Dictionary<string, string>() 
{
    {"preview", "1"},
    {"fields.genre", "Rock"},
    {"order", "name"},
    {"page", "1"},
    {"page_size", "10"}
    {"locale", "en"},
    {"levels", "2"},
};
var contentFields = await butterClient.RetrieveContentFieldsJSONAsync(keys, 
    parameterDict
);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.content.retrieve(['artists'], {
     'preview': '1',
     'fields.genre': 'Rock',
     'order': 'name',
     'page': '1',
     'page_size': '10',
     'locale': 'en',
     'levels': '2'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#list-collection-items
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String, String> queryParams = new HashMap<String, String>(){{
  put("preview", "1");
  put("page", "1");
  put("page_size", "10");
  put("locale", "en");
  put("levels", "2");
  put("fields.genre", "Rock");
  put("order", "name");
}}

CollectionResponse response = butterClient.getCollection(
  "artists", 
  queryParams,
  ArtistCollection.class
  );
// Note: The swift SDK requires you to model the Collection 
// schema as a Codable Struct and pass it to getPages API. 
// This allows the SDK to deserialize the page data for you.

private struct CollectionFields: Codable {
  var name: String
  var description: String
  // ... continue building struct based on expected datatypes.
  // To see the expected data as a json, you can make a query using
  // the API endpoint to the left. 
  // See https://developer.apple.com/documentation/foundation/archives_and_serialization/encoding_and_decoding_custom_types for more details
}
import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")
butter.getCollection(
  slug:"artists", 
  parameters: [
    // Collections API for Swift does not have preview at this time
    .page(value: 1)
    .fields(value: "genre", value: "Rock")
    // Note - currently takes two keys, "by", and "direction"
    .order(by: "name", direction:"")
    .locale(value: "en"),
    .pageSize(value: 10),
    .levels(value: 2),
  ], 
  type: CollectionFields.self
) // {Do something with result}

Example response

{
  "data": {
    "artists": [
      {
        "meta": {
          "id": 123
        },
        "name": "The Beatles",
        "genre": "Rock"
      },
      {
        "meta": {
          "id": 123
        },
        "name": "The Rolling Stones",
        "genre": "Rock"
      }
    ]
  }
}

Returns values for the supplied Collection keys.

API Endpoint

https://api.buttercms.com/v2/content/<collection_slug>/?auth_token=your_api_token

Arguments

Argument Description
keys Comma delimited list of Collection keys.
preview Optional. Set to 1 to enable Preview mode for viewing draft content.
fields.key Optional. Filter the result set by the field and value.
order Optional. Order the result set by this field. Defaults to Ascending. Preprend '-' to sort Descending. i.e. &order=-your_field
page Optional. Used for Paginating through result set.
page_size Optional. Used for Paginating. Defines the number of results returned.
locale Optional. Set to the api slug of your configured locale (e.g. en or fr). When omitted, this query parameter will default to your organization's default locale.
levels Optional. Defaults to 2. Defines the levels of relationships to serialize. See below.

Returns

An object with a data property that contains a list of objects with Collection item keys and values.

Meta data

Each returned Collection item object contains a special meta key. This key contains an object with data about the Collection item. Currently, it only contains the item's ID, which can be used to update or delete the item. In the future this object could contain other information.

Meta property Description
id An identifier for the Collection item.

Filtering a Collection

Sometimes you want to filter a Collection to return only a subset of items. Use fields.key to do this. i.e. ?fields.field_name=value

For example, if you have a Collection of musical artists:

/v2/content/artists/

You can filter on any Collection property:

/v2/content/artists?fields.name=The Beatles

Previewing Collections

Example Request

curl -X GET 'https://api.buttercms.com/v2/content/artists/?&preview=1&auth_token=your_api_token'

To setup a staging website for previewing content you'll need to fetch the draft version of a Collection item. To do this, simply add ?preview=1 as a parameter to the normal API call.

You'll often want to set this ?preview=1 flag in your local, development, and staging environments to enable previewing of content.

Collections Reference Levels

Example Reference Response

// related_pages and tags are Reference fields
"title": "...",
"body": "...",
"related_pages": [
  "/v2/pages/example-page-type/example-page-slug"
],
"tags": [
  "/v2/content/?keys=artists[_id=1234]"
]

Using Reference fields, you can create relationships between a Page Type and another type of content (Page Type or Collection). These relationships can create heirarchies of content many levels deep and sometimes circular in nature (A references B which references A).

The most common case is for one Reference to exist (A references B) which means two levels of content, which is what we serialize by default. If you need more levels, specify that parameter. If you only need one level, you can specify levels=1 which also makes the response payload smaller.

When the level limit is reached, we return unique URIs for any unserialized objects.

Localization

Example Request

curl -X GET 'https://api.buttercms.com/v2/content/artists/?locale=en&auth_token=your_api_token'

When Localization is enabled in your account, your content has a version for each locale specified. To query content based on locale, simply add locale= as a parameter. For example:

/v2/content/artists/?locale=en

The API slugs values for each locale are configured by you in your account.

Blog Engine

The ButterCMS Blog Engine provides you with a set of pre-built API's to quickly add a fully customized blog to your website.

The Blog Post Object

Attribute Description
slug string Unique identifier
url string Full url of post based on base URL in settings
published timestamp Timestamp of when the post was published
created string Timestamp of when the post was created
updated timestamp Timestamp of when the post was last updated
scheduled timestamp Timestamp of when the post is scheduled to be published
status string draft, published, scheduled
title string
body string Full HTML body
summary string Plain-text summary
seo_title string Use in HTML title tag
meta_description string Use in meta and og description tags
author hash, author object
categories array, category objects
tags array, tag objects
featured_image CDN URL of featured image
featured_image_alt string

Create Blog Post via Write API

Example POST Request

curl -X POST \
  https://api.buttercms.com/v2/posts/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "author": {
    "email": "your@author.com" // You can also lookup by author "slug"
  },
  "categories": ["Recipes", "Meals"],
  "tags": ["Butter", "Sushi", "Really Good Recipes"],
  "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
  "featured_image_alt": "Featured image alt text example.",
  "slug": "this-is-a-blog-post",
  "title": "This is a blog post",
  "body": "<h1>Butter</h1><p>I am so hungry!</p>",
  "summary": "This is a blog post summary.",
  "seo_title": "This is a blog post",
  "meta_description": "This is a blog post to test the API.",
  "status": "published"
}'
curl -X POST \
  https://api.buttercms.com/v2/posts/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "author": {
    "email": "your@author.com" // You can also lookup by author "slug"
  },
  "categories": ["Recipes", "Meals"],
  "tags": ["Butter", "Sushi", "Really Good Recipes"],
  "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
  "featured_image_alt": "Featured image alt text example.",
  "slug": "this-is-a-blog-post",
  "title": "This is a blog post",
  "body": "<h1>Butter</h1><p>I am so hungry!</p>",
  "summary": "This is a blog post summary.",
  "seo_title": "This is a blog post",
  "meta_description": "This is a blog post to test the API.",
  "status": "published"
}'
curl -X POST \
  https://api.buttercms.com/v2/posts/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "author": {
    "email": "your@author.com" // You can also lookup by author "slug"
  },
  "categories": ["Recipes", "Meals"],
  "tags": ["Butter", "Sushi", "Really Good Recipes"],
  "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
  "featured_image_alt": "Featured image alt text example.",
  "slug": "this-is-a-blog-post",
  "title": "This is a blog post",
  "body": "<h1>Butter</h1><p>I am so hungry!</p>",
  "summary": "This is a blog post summary.",
  "seo_title": "This is a blog post",
  "meta_description": "This is a blog post to test the API.",
  "status": "published"
}'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;


void main() async{
  Map payload = {
      "author": {
        "email": "your@author.com" // You can also lookup by author "slug"
      },
      "categories": ["Recipes", "Meals"],
      "tags": ["Butter", "Sushi", "Really Good Recipes"],
      "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
      "featured_image_alt": "Featured image alt text example.",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<h1>Butter</h1><p>I am so hungry!</p>",
      "summary": "This is a blog post summary.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.post(
    url: 'https://api.buttercms.com/v2/posts/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
    {
      "author": {
        "email": "your@author.com" // You can also lookup by author "slug"
      },
      "categories": ["Recipes", "Meals"],
      "tags": ["Butter", "Sushi", "Really Good Recipes"],
      "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
      "featured_image_alt": "Featured image alt text example.",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<h1>Butter</h1><p>I am so hungry!</p>",
      "summary": "This is a blog post summary.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  `)

  req, err := http.NewRequest("POST", "https://api.buttercms.com/v2/posts/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
let payload = {
    "author": {
      "email": "your@author.com" // You can also lookup by author "slug"
    },
    "categories": ["Recipes", "Meals"],
    "tags": ["Butter", "Sushi", "Really Good Recipes"],
    "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
    "featured_image_alt": "Featured image alt text example.",
    "slug": "this-is-a-blog-post",
    "title": "This is a blog post",
    "body": "<h1>Butter</h1><p>I am so hungry!</p>",
    "summary": "This is a blog post summary.",
    "seo_title": "This is a blog post",
    "meta_description": "This is a blog post to test the API.",
    "status": "published"
}

fetch('https://api.buttercms.com/v2/posts/', {
  method: 'POST',
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));
import requests

payload = {
    "author": {
      "email": "your@author.com" # You can also lookup by author "slug"
    },
    "categories": ["Recipes", "Meals"],
    "tags": ["Butter", "Sushi", "Really Good Recipes"],
    "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
    "featured_image_alt": "Featured image alt text example.",
    "slug": "this-is-a-blog-post",
    "title": "This is a blog post",
    "body": "<h1>Butter</h1><p>I am so hungry!</p>",
    "summary": "This is a blog post summary.",
    "seo_title": "This is a blog post",
    "meta_description": "This is a blog post to test the API.",
    "status": "published"
}

response = requests.post("https://api.buttercms.com/v2/posts/", json=payload, headers={"Authorization": "Token your_write_api_token" })


require 'net/http'
require 'uri'
require 'json'

uri = URI.parse('https://api.buttercms.com/v2/posts/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
    "author": {
      "email": "your@author.com" // You can also lookup by author "slug"
    },
    "categories": ["Recipes", "Meals"],
    "tags": ["Butter", "Sushi", "Really Good Recipes"],
    "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
    "featured_image_alt": "Featured image alt text example.",
    "slug": "this-is-a-blog-post",
    "title": "This is a blog post",
    "body": "<h1>Butter</h1><p>I am so hungry!</p>",
    "summary": "This is a blog post summary.",
    "seo_title": "This is a blog post",
    "meta_description": "This is a blog post to test the API.",
    "status": "published"
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Post.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

<?php
$url = "https://api.buttercms.com/v2/posts/";

$payload = array(
    "author" => array(
      "email" => "your@author.com" // You can also lookup by author "slug"
    ),
    "categories" => ["Recipes", "Meals"],
    "tags" => ["Butter", "Sushi", "Really Good Recipes"],
    "featured_image" => "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
    "featured_image_alt" => "Featured image alt text example.",
    "slug" => "this-is-a-blog-post",
    "title" => "This is a blog post",
    "body" => "<h1>Butter</h1><p>I am so hungry!</p>",
    "summary" => "This is a blog post summary.",
    "seo_title" => "This is a blog post",
    "meta_description" => "This is a blog post to test the API.",
    "status" => "published"
);

$content = json_encode($payload);

$curl = curl_init($url);
curl_setopt($curl, CURLOPT_HEADER, false);
curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
curl_setopt($curl, CURLOPT_HTTPHEADER,
        array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
curl_setopt($curl, CURLOPT_POST, true);
curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

$json_response = curl_exec($curl);

curl_close($curl);
$response = json_decode($json_response, true);

print_r($response);
?>

var payload = {
  "author": {
    "email": "your@author.com" # You can also lookup by author "slug"
  },
  "categories": ["Recipes", "Meals"],
  "tags": ["Butter", "Sushi", "Really Good Recipes"],
  "featured_image": "https://farm1.staticflickr.com/836/42903355654_8faa21171a_m_d.jpg",
  "featured_image_alt": "Featured image alt text example.",
  "slug": "this-is-a-blog-post",
  "title": "This is a blog post",
  "body": "<h1>Butter</h1><p>I am so hungry!</p>",
  "summary": "This is a blog post summary.",
  "seo_title": "This is a blog post",
  "meta_description": "This is a blog post to test the API.",
  "status": "published"
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/posts/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "POST"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can create posts by using POST requests to the Butter /v2/posts/ API endpoint.

Authentication

See the authentication section for details on how to authenticate your requests.

Making requests

Requests should be HTTP POST requests made to https://api.buttercms.com/v2/posts/, with the Content-Type header set to application/json.

The body of your request should be a JSON object like the example to the right. Note this is the same structure as when you GET a post.

Body Fields
Attribute Description
title Required. The title of the post.
slug Required. The slug of the post.
status Optional. The status of the post. Defaults to draft. You cannot schedule a blog post via the write API at this time.
author Optonal. Author must exist in your account prior to POST. Should either be { "email" : "your@author.com" } or { "slug" : "firstname-lastname" }. Defaults to the organization owner.
categories Optional. Array of strings.
tags Optional. Array of strings.
featured_image

Optional. Can be a remote URL to an image.

The image will always be uploaded to the media library (the value of upload_images_to_media_library is ignored in this case).

featured_image_alt Optional.
body

Optional. Should be an string of escaped HTML.

In case it contains any remote URLs to images, the upload_images_to_media_library flag controls the behavior. See the flag's description below for more details.

summary Optional.
seo_title Optional.
meta_description Optional.
upload_images_to_media_library

Optional. Defaults to false.

If set to true, any image URLs in the body property (e.g. "body": "<img src=\"https://example.com/image.jpg\">") will be uploaded to the Butter Media Library and the original URL will be replaced with the media library one (e.g. "body": "<img src=\"https://example.com/image.jpg\">" → "body": "<img src=\"https://cdn.buttercms.com/{unique-id}\">").

If set to false, images won't be uploaded to the media library and the body property will contain the original remote URLs (e.g. "body": "<img src=\"https://example.com/image.jpg\">" → "body": "<img src=\"https://example.com/image.jpg\">").

Responses

A validated POST request will return a response with HTTP status code 202. Full post creation occurs asynchronously, meaning a successfully created post may not show immediately. Posts are validated prior to returning the API response but it is also possible that post creation may fail after returning a 202 response. If this happens please contact support.

The API will return HTTP status code 400 if your data does not pass the initial validation stage. This may happen if you are missing a field, missing a required field, or the remote URL for a media field returns a 404. Error explanations will be returned in a single JSON array.

Update Blog Post via Write API

Example PATCH Request

curl -X PATCH \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}'
curl -X PATCH \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}'
curl -X PATCH \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token' \
  -H 'Content-Type: application/json' \
  -d '{
    "slug": "the-new-post-slug",
    "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
  }'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  Map payload = {
    "slug": "the-new-post-slug",
    "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
  };

  String body = convert.jsonEncode(payload);

  http.Response response = await http.patch(
    url: 'https://api.buttercms.com/v2/posts/this-is-a-blog-post/',
    headers: {
      "Content-Type": "application/json", 
      "Authorization": "Token your_write_api_token"
      },
    body: body,
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "strings"
  "log"
)

func main() {
  payload := strings.NewReader(`
      {
        "slug": "the-new-post-slug",
        "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
      }
  `)

  req, err := http.NewRequest("PATCH", "https://api.buttercms.com/v2/posts/this-is-a-blog-post/", payload)

  req.Header.Add("Authorization", "Token your_write_api_token")

  req.Header.Add("Content-type", "application/json")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
let payload = {
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}

fetch('https://api.buttercms.com/v2/posts/this-is-a-blog-post/', {
  method: 'PATCH',
  headers: {
    "Authorization": "Token your_write_api_token",
    "Content-Type": "application/json",
  },
  body: JSON.stringify(payload),
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));
import requests


payload = {
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}

response = requests.patch("https://api.buttercms.com/v2/posts/this-is-a-blog-post/", json=payload, headers={"Authorization": "Token your_write_api_token" })

print(response.content)

require 'net/http'
require 'uri'
require 'json'


uri = URI.parse('https://api.buttercms.com/v2/posts/this-is-a-blog-post/')

header = {
    "Content-type": "application/json",
    "Authorization": "Token your_write_api_token"
}

payload = {
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Patch.new(uri.request_uri, header)
request.body = payload.to_json

response = http.request(request)

<?php
$url = "https://api.buttercms.com/v2/posts/this-is-a-blog-post/";
$payload = array(
  "slug" => "the-new-post-slug",
  "body" => "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
);

  $content = json_encode($payload);

  $curl = curl_init($url);
  curl_setopt($curl, CURLOPT_HEADER, false);
  curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($curl, CURLOPT_HTTPHEADER, array("Content-type: application/json", "Authorization: Token your_write_api_token" ));
  curl_setopt($curl, CURLOPT_CUSTOMREQUEST, 'PATCH');
  curl_setopt($curl, CURLOPT_POSTFIELDS, $content);

  $json_response = curl_exec($curl);

  curl_close($curl);
  $response = json_decode($json_response, true);

  print_r($response);
?>
var payload = {
  "slug": "the-new-post-slug",
  "body": "<h1>Updated</h1><p>This is a blog post was updated via API</p>"
}

// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/posts/this-is-a-blog-post/")
var request = URLRequest(url: requestUrl)
let bodyData = try? JSONSerialization.data(
    withJSONObject: payload, 
    options: []
)
request.httpMethod = "PATCH"
request.setValue("application/json", forHTTPHeaderField: "Content-Type")
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")
request.httpBody = bodyData

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can update existing blog posts by using a PATCH request to /v2/posts/your-post-slug endpoint. In the body of the request you can specify one or more fields you'd like to update.

Blog posts cannot be scheduled via the write API. If a scheduled timestamp or a status of scheduled is passed to the write API via PATCH, it will be ignored; this is so users can make updates to currently scheduled posts.

You can provide the optional upload_images_to_media_library attribute with a value of true if you'd like any image URLs in the body property to be uploaded to the Butter Media Library. See the same flag's description in Create Blog Post via Write API for more details.

Delete Blog Post via Write API

Example DELETE Request

curl -X DELETE \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token'
curl -X DELETE \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token'
curl -X DELETE \
  https://api.buttercms.com/v2/posts/this-is-a-blog-post/ \
  -H 'Authorization: Token your_write_api_token'
import 'dart:convert' as convert;
import 'package:http/http.dart' as http;

void main() async {
  http.Response response = await http.delete(
    url: 'https://api.buttercms.com/v2/posts/this-is-a-blog-post/',
    headers: {
      "Authorization": "Token your_write_api_token"
      },
  );

  print(convert.jsonDecode(response.body));
}
import (
  "net/http"
  "io/ioutil"
  "log"
)

func main() {
  req, err := http.NewRequest("DELETE", "https://api.buttercms.com/v2/posts/this-is-a-blog-post/", nil)

  req.Header.Add("Authorization", "Token your_write_api_token")

  client := &http.Client{}

  resp, err := client.Do(req)

  if err != nil {
    log.Fatalln(err)
  }

  body, _ := ioutil.ReadAll(resp.Body)
  log.Println(string([]byte(body)))
}
fetch('https://api.buttercms.com/v2/posts/this-is-a-blog-post/', {
  method: 'DELETE',
  headers: {
    "Authorization": "Token your_write_api_token",
  },
})
.then(json => console.log(json))
.catch(err => console.log("Request Failed", err));
import requests


response = requests.delete("https://api.buttercms.com/v2/posts/this-is-a-blog-post/", headers={"Authorization": "Token your_write_api_token" })

print(response.content)
require 'net/http'
require 'uri'


uri = URI.parse('https://api.buttercms.com/v2/posts/this-is-a-blog-post/')

header = {
    "Authorization": "Token your_write_api_token"
}

http = Net::HTTP.new(uri.host, uri.port)
request = Net::HTTP::Delete.new(uri.request_uri, header)

response = http.request(request)
<?php
  $url = "https://api.buttercms.com/v2/posts/this-is-a-blog-post/";

  $curl = curl_init($url);
  curl_setopt($curl, CURLOPT_HEADER, false);
  curl_setopt($curl, CURLOPT_RETURNTRANSFER, true);
  curl_setopt($curl, CURLOPT_HTTPHEADER, array("Authorization: Token your_write_api_token"));
  curl_setopt($curl, CURLOPT_CUSTOMREQUEST, 'DELETE');

  $json_response = curl_exec($curl);

  curl_close($curl);
  $response = json_decode($json_response, true);

  print_r($response);
?>
// Prepare URL Request Object
let requestUrl = URL(string: "https://api.buttercms.com/v2/posts/this-is-a-blog-post/")
var request = URLRequest(url: requestUrl)
request.httpMethod = "DELETE"
request.setValue("your_api_token_here", forHTTPHeaderField: "Authorization")

// Perform HTTP Request
let session = URLSession.shared
let task = URLSession.shared.dataTask(with: request) { (data, response, error) in

  if let error = error {
    print("Error took place \(error)")
  } else if let data = data {
    // Do something with returned data
  } else {
    // Handle unexpected error
  }
}

// Start request
task.resume()

You can delete an existing blog post by making a DELETE request to the /v2/posts/your-post-slug/ endpoint.

Get your Blog Posts

List all posts

Example request

curl -X GET 'https://api.buttercms.com/v2/posts/?page=1&page_size=10&exclude_body=false&author_slug=api-test&category_slug=test-category&tag_slug=test-tag&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

posts = ButterCMS::Post.all({
     "page": 1,
     "page_size": 10,
     "exclude_body": false,
     "author_slug": 'test-api',
     "category_slug": 'test-category',
     "tag_slug": 'test-tag'
})
var butter = require('buttercms')("your_api_token");

butter.post.list({
     "page": 1,
     "page_size": 10,
     "exclude_body": false,
     "author_slug": 'test-api',
     "category_slug": 'test-category',
     "tag_slug": 'test-tag'
})
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
     "page": "1",
     "page_size": "10",
     "exclude_body": "false",
     "author_slug": "test-api",
     "category_slug": "test-category",
     "tag_slug": "test-tag"
}

ButterCMS.GetPosts(params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchPosts([
     'page' => '1',
     'page_size' => '10',
     'exclude_body' => 'false',
     'author_slug' => 'test-api',
     'category_slug' => 'test-category',
     'tag_slug' => 'test-tag'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.posts.all({
     "page": "1",
     "page_size": "10",
     "exclude_body": "false",
     "author_slug": "test-api",
     "category_slug": "test-category",
     "tag_slug": "test-tag"
})
using ButterCMS;
PostsResponse posts = butterClient.ListPosts(
  page: 1, 
  pageSize: 10, 
  excludeBody: false, 
  authorSlug: "test-api", 
  categorySlug: "test-category",
  tagSlug: "test-tag"
);

// We also support Async requests for all C# calls
PostsResponse filteredPosts = await butterClient.ListPostsAsync();
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.posts.list({
     'page': '1',
     'page_size': '10',
     'exclude_body': 'false',
     'author_slug': 'test-api',
     'category_slug': 'test-category',
     'tag_slug': 'test-tag'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#posts
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");

Map<String,String> queryParams = new HashMap<String, String>() {{
  put("page", "1");
  put("page_size", "10");
  put("exclude_body", "false");
  put("author_slug", "test-api");
  put("category_slug", "test-category");
  put("tag_slug", "test-tag");
}} 

PostsResponse posts = butterClient.getPosts(queryParams);
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for blog posts for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getPosts(parameters: [ .preview(value:1)]) { result in
  switch result {
  case .sucess(let posts):
    posts.data.compactMap { print (*Post: \($0) \n*)}
  case .failure(let error):
    print (error)
  }
}

Example response

{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2020-10-08T18:29:19.987936Z",
      "updated": "2020-10-09T15:49:54.580309Z",
      "published": "2020-10-08T18:08:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
<ButterCMS::ButterCollection:0x007fd86c96de70 @meta=#<OpenStruct count=1, next_page=nil, previous_page=nil>, @items=[#<ButterCMS::Post:0x3fec364b6bc8> JSON: {
  "data": {
    "url": "http://www.example.com/blog/this-is-a-blog-post",
    "created": "2015-06-12T13:59:32.441289Z",
    "published": "2015-06-12T00:00:00Z",
    "author": {
      "first_name": "API",
      "last_name": "Test",
      "email": "apitest@buttercms.com",
      "slug": "api-test",
      "bio": "This is my bio.",
      "title": "API",
      "linkedin_url": "https://www.linkedin.com/in/API",
      "facebook_url": "https://www.facebook.com/API",
      "twitter_handle": "buttercmsapi",
      "profile_image": "https://buttercms.com/api.png"
    },
    "categories": [
      {
        "name": "test category",
        "slug": "test-category"
      }
    ],
    "tags": [
      {
        "name": "test tag",
        "slug": "test-tag"
      }
    ],
    "featured_image": null,
    "featured_image_alt": "",
    "slug": "this-is-a-blog-post",
    "title": "This is a blog post",
    "body": "<p class=\"\">This is a blog post to test the API.</p>",
    "summary": "This is a blog post to test the API.",
    "seo_title": "This is a blog post",
    "meta_description": "This is a blog post to test the API.",
    "status": "published"
  }
}]>
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2020-10-08T18:29:19.987936Z",
      "updated": "2020-10-09T15:49:54.580309Z",
      "published": "2020-10-08T18:08:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "pinterest_url": "https://www.pinterest.com/API",
        "instagram_url": "https://www.instagram.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
JSON: {
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
JSON: {
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
{
    "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "pinterest_url": "https://www.pinterest.com/API",
        "instagram_url": "https://www.instagram.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published"
    }
  ]
}
Post: Post(
  status: Optional(ButterCMSSDK.Status.PUBLISHED), 
  created: Optional(2021-07-19 12:24:21 +0000), 
  published: Optional(2021-07-19 12:24:00 +0000),
  title: "An Example blog post",
  slug: "example-post-1", 
  body: Optional("<p>I am a post"),
  summary: Optional("This is a blog post."),
  seoTitle: Optional("TEST"),
  metaDescription: Optional("This is a blog post to test the API."),
  featuredImage: nil,
  featuredImageAlt: Optional(""),
  url: Optional("test"),
  author: Optional(ButterCMSSDK.Author(
    slug: "sample-name",
    firstName: Optional("First"),
    lastName: Optional("last"),
    email: Optional("sample.email@sample.com"),
    bio: Optional("my bio"),
    title: Optional("title"),
    linkedinUrl: Optional(""),
    facebookUrl: Optional(""),
    pinterestUrl: Optional(""),
    instagramUrl: Optional(""),
    twitterHandle: Optional(""),
    profileImage: Optional(""),
    recentPosts: nil
    )),
  tags: Optional([ButterCSMSDK.Tag(
    slug: "example-tag",
    name: "Example Tag",
    recentPosts: nil,
  )]),
  categories: Optional([ButterCMSSDK.Category(
    slug: "example-category",
    name: "Example Category",
    recentPosts: nil,
  )])
)

Post: Post(
  status: Optional(ButterCMSSDK.Status.PUBLISHED), 
  created: Optional(2021-07-19 12:24:21 +0000), 
  published: Optional(2021-07-19 12:24:00 +0000),
  title: "An Example blog post",
  slug: "example-post-2", 
  body: Optional("<p>I am a post"),
  summary: Optional("This is a blog post."),
  seoTitle: Optional("TEST"),
  metaDescription: Optional("This is a blog post to test the API."),
  featuredImage: nil,
  featuredImageAlt: Optional(""),
  url: Optional("test"),
  author: Optional(ButterCMSSDK.Author(
    slug: "sample-name",
    firstName: Optional("First"),
    lastName: Optional("last"),
    email: Optional("sample.email@sample.com"),
    bio: Optional("my bio"),
    title: Optional("title"),
    linkedinUrl: Optional(""),
    facebookUrl: Optional(""),
    pinterestUrl: Optional(""),
    instagramUrl: Optional(""),
    twitterHandle: Optional(""),
    profileImage: Optional(""),
    recentPosts: nil
    )),
  tags: Optional([ButterCSMSDK.Tag(
    slug: "example-tag",
    name: "Example Tag",
    recentPosts: nil,
  )]),
  categories: Optional([ButterCMSSDK.Category(
    slug: "example-category",
    name: "Example Category",
    recentPosts: nil,
  )])
)

Returns a list of published posts. The posts are returned sorted by publish date, with the most recent posts appearing first. The endpoint supports pagination and filtering.

Arguments
Argument Default Description
page¹ 1 Used to paginate through older posts.
page_size¹ 10 Used to set the number of blog posts shown per page.
preview 1 Optional. Set to 1 to return all published and draft posts. i.e. &preview=1. If a blog post has been scheduled for future publication, it will not be returned from this endpoint when listing all posts unless preview=1, regardless of draft or published status.
exclude_body false When true, does not return the full post body. Useful for keeping response size down when showing list of blog posts.
author_slug Filter posts by an author's slug.
category_slug Filter posts by a category's slug.
tag_slug Filter posts by a tag's slug.
limit¹ 10 Used for Paginating. Defines the number of results returned.
offset¹ 0 Used for Paginating through result set.

¹ We support two types of pagination. You have to choose if you want to use page + page_size or limit + offset for getting entries. If you provide limit or offset we will ignore page and page_size.

Returns

A hash with a data property that contains an array of posts, and a meta property that contains the total number of posts and the next and previous page number if they exist.

Retrieve a post

Example request

curl -X GET 'https://api.buttercms.com/v2/posts/<slug>/?auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

post = ButterCMS::Post.find("hello-world")
var butter = require('buttercms')("your_api_token");

butter.post.retrieve("hello-world")
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
ButterCMS.GetPost("hello-world")
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchPost('hello-world');
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.posts.get('hello-world')
using ButterCMS;
PostResponse controversialPost = 
  butterClient.RetrievePost("hello-world");
// We also support Async requests for all C# calls
PostResponse safePost = 
  await butterClient.RetrievePostAsync("hello-world");
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.posts.retrieve("hello-world").then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#posts
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
PostResponse post = butterClient.getPost("hello-world");
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for blog posts for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")
}
butter.getPost(
  slug: "hello-world"
) // {Print the result}

Example response

{
  "meta": {
    "next_post": null,
    "previous_post": {
      "slug": "google-analytics-is-now-integrated-with-your-butter-blog",
      "title": "Google Analytics is now integrated with your Butter blog",
      "featured_image": "https://d2devwt40at1e2.cloudfront.net/api/file/etSDYJUIFDADGEEAQ/"
    }
  },
  "data": {
    "url": "http://www.example.com/blog/this-is-a-blog-post",
    "created": "2015-06-12T13:59:32.441289Z",
    "published": "2015-06-12T00:00:00Z",
    "author": {
      "first_name": "API",
      "last_name": "Test",
      "email": "apitest@buttercms.com",
      "slug": "api-test",
      "bio": "This is my bio.",
      "title": "API",
      "linkedin_url": "https://www.linkedin.com/in/API",
      "facebook_url": "https://www.facebook.com/API",
      "pinterest_url": "https://www.pinterest.com/API",
      "instagram_url": "https://www.instagram.com/API",
      "twitter_handle": "buttercmsapi",
      "profile_image": "https://buttercms.com/api.png"
    },
    "categories": [
      {
        "name": "test category",
        "slug": "test-category"
      }
    ],
    "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
    "featured_image": null,
    "featured_image_alt": "",
    "slug": "hello-world",
    "title": "This is a blog post",
    "body": "<p class=\"\">This is a blog post to test the API.</p>",
    "summary": "This is a blog post to test the API.",
    "seo_title": "This is a blog post",
    "meta_description": "This is a blog post to test the API.",
    "status": "published"
  }
}

Retrieves the details of a post. Supply the unique slug of the post.

Arguments
Argument Description
slug The slug of the post to be retrieved.
Returns

A hash with a data property that contains a post object, and a meta property that contains properties of the next and previous post if they exist.

Note that if you provide the exact slug of the post using the v2/posts/<slug>/ endpoint, it can always be retrieved, regardless of the post's status. However, if the post status is draft, or the post has been scheduled for future publishing, it will not show up when listing all posts unless the preview=1 parameter is passed.

Search Posts

Example Request

curl -X GET 'https://api.buttercms.com/v2/posts/search/?query=buttercmsapi&page=1&page_size=10&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

posts = ButterCMS::Post.search("buttercmsapi", {
 "page": 1,
 "page_size": 10
})
var butter = require('buttercms')("your_api_token");

butter.post.search("buttercmsapi", {
    "page": 1,
    "page_size": 10
}).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params := map[string]string{
    "page": "1",
    "page_size": "10"
}
ButterCMS.SearchPosts("buttercmsapi", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->searchPosts('buttercmsapi', [
 'page' => 1,
 'page_size' => 10
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.posts.search('buttercmsapi', {
 'page': 1,
 'page_size': 10
})
using ButterCMS;
PostsResponse posts = 
  butterClient.SearchPosts("buttercmsapi",
    page: 1,
    pageSize: 10
  );
// We also support Async requests for all C# calls
PostsResponse caffeinePosts = 
  await butterClient.SearchPostsAsync(query: "buttercmsapi", 
    page: 3, 
    pageSize: 5
  );
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.posts.search("buttercmsapi", {
    'page': '1',
    'page_size': '10'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#posts
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("query","search term");
}}
PostsResponse posts = butterClient.getPostSearch(queryParams);
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for blog posts for 
// the Swift SDK to consume, as their schema doesn't change.

// Note that the swift SDK is unique, in that the query 
// terms is passed as a string inside params.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.searchPosts(
  parameters: [
    .page(value: 1),
    .page_size(value: 10),
    .query(value: "buttercmsapi")
  ]
) // {Do something with result}

Example response

{
  "meta": {
    "count": 1,
    "next_page": null,
    "previous_page": null
  },
  "data": [
    {
      "url": "http://www.example.com/blog/this-is-a-blog-post",
      "created": "2015-06-12T13:59:32.441289Z",
      "published": "2015-06-12T00:00:00Z",
      "author": {
        "first_name": "API",
        "last_name": "Test",
        "email": "apitest@buttercms.com",
        "slug": "api-test",
        "bio": "This is my bio.",
        "title": "API",
        "linkedin_url": "https://www.linkedin.com/in/API",
        "facebook_url": "https://www.facebook.com/API",
        "twitter_handle": "buttercmsapi",
        "profile_image": "https://buttercms.com/api.png"
      },
      "categories": [
        {
          "name": "test category",
          "slug": "test-category"
        }
      ],
      "tags": [
        {
          "name": "test tag",
          "slug": "test-tag"
        }
      ],
      "featured_image": null,
      "featured_image_alt": "",
      "slug": "this-is-a-blog-post",
      "title": "This is a blog post",
      "body": "<p class=\"\">This is a blog post to test the API.</p>",
      "summary": "This is a blog post to test the API.",
      "seo_title": "This is a blog post",
      "meta_description": "This is a blog post to test the API.",
      "status": "published",
      "rank": 0.5
    }
  ]
}

Returns a list of posts that match the search query. The posts are returned sorted by relevancy and include their absolute rank value based on looking at the post title and body fields.

Arguments
Argument Default Description
query Search query
page 1
page_size 10
Returns

A hash with a data property that contains an array of posts, and a meta property that contains the total number of posts and the next and previous page number if they exist.

If no results are found, the API returns an empty array: "data": []

Authors

The author object

Attribute Description
slug string Unique identifier
first_name string
last_name string
email string
bio string
title string
linkedin_url string
facebook_url string
pinterest_url string
instagram_url string
twitter_handle string
profile_image string CDN URL of author's image.

List all authors

Example request

curl -X GET 'https://api.buttercms.com/v2/authors/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

authors = ButterCMS::Author.all({
    "include": "recent_posts"
})
var butter = require('buttercms')("your_api_token");

butter.author.list({"include": "recent_posts"})
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetAuthors(params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchAuthors(['include' => 'recent_posts']);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.authors.all({'include': 'recent_posts'})
IEnumerable<Author> authors = butterClient.ListAuthors(includeRecentPosts: true);
// Async
IEnumerable<Author> authorsWithPosts = 
  await butterClient.ListAuthorsAsync(includeRecentPosts: true);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.authors.list({
  'include': 'recent_posts'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#authors
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
}}
AuthorsResponse authors = butterClient.getAuthors(queryParams);
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for authors for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")
butter.getAuthors(
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

// Note that `data` is an array/list composed of a 
// number of author objects/dictionaries. 

{
  "data": [
    {
      "first_name": "API",
      "last_name": "Test",
      "email": "apitest@buttercms.com",
      "slug": "api-test",
      "bio": "This is my bio.",
      "title": "API",
      "linkedin_url": "https://www.linkedin.com/in/API",
      "facebook_url": "https://www.facebook.com/API",
      "pinterest_url": "https://www.pinterest.com/API",
      "instagram_url": "https://www.instagram.com/API",
      "twitter_handle": "buttercmsapi",
      "profile_image": "https://buttercms.com/api.png"
    }
  ]
}

Returns a list of authors.

Arguments
Argument Description
include Use include=recent_posts to include the author's recent posts in the response.
Returns

A hash with a data property that contains an array of authors.

Retrieve an author

Example request

curl -X GET 'https://api.buttercms.com/v2/authors/jennifer-smith/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

author = ButterCMS::Author.find("jennifer-smith", {
    "include": "recent_posts"
})
// https://github.com/ButterCMS/buttercms-java#authors
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
}}
AuthorResponse author = butterClient.getAuthor("jennifer-smith", queryParams);
var butter = require('buttercms')("your_api_token");

butter.author.retrieve("jennifer-smith", {
    "include": "recent_posts"
}).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetAuthor("jennifer-smith", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchAuthor('jennifer-smith', [
    'include' => 'recent_posts'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.authors.get('jennifer-smith',{
   'include': 'recent_posts'
})
Author sally = butterClient.RetrieveAuthor(
    "jennifer-smith",
    includeRecentPosts: true
);
// Async
Author tylerAndPosts = 
  await butterClient.RetrieveAuthorAsync(
    authorSlug: "jennifer-smith", 
    includeRecentPosts: true
  );
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.authors.retrieve("jennifer-smith", {
  'include': 'recent_posts'
}).then((response) {
  print(response);
});
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for authors for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getAuthor(
  slug: "jennifer-smith",
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

// Note that in contrast to above, `data` is a single
// object/dictionary.
{
  "data": {
    "first_name": "Jennifer",
    "last_name": "Smith",
    "email": "jennifersmith@buttercms.com",
    "slug": "jennifer-smith",
    "bio": "I love coffee!",
    "title": "President",
    "linkedin_url": "https://www.linkedin.com/in/jennifersmith",
    "facebook_url": "https://www.facebook.com/jennifersmith",
    "pinterest_url": "https://www.pinterest.com/jennifersmith",
    "instagram_url": "https://www.instagram.com/jennifersmith",
    "twitter_handle": "jennifersmith",
    "profile_image": "https://d2devwt40at1e2.cloudfront.net/api/file/etSDYJUIFDADGEEAQ.png"
  }
}

Retrieves an author's information. Supply the unique slug of the author.

Arguments
Argument Description
slug The slug of the author to be retrieved.
include Use include=recent_posts to include the author's recent posts in the response.
Returns

A hash with a data property that contains an author object.

Categories

The category object

Attribute Description
slug string Unique identifer
name string

List all categories

Example request

curl -X GET 'https://api.buttercms.com/v2/categories/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

categories = ButterCMS::Category.all({
    "include": "recent_posts"
})
var butter = require('buttercms')("your_api_token");

butter.category.list({
    "include": "recent_posts"
})
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetCategories(params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchCategories([
    'include' => 'recent_posts'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.categories.all({'include': 'recent_posts'})
IEnumerable<Category> categories = butterClient.ListCategories();
//Async
IEnumerable<Category> categoriesWithPosts = 
  await butterClient.ListCategoriesAsync(includeRecentPosts: true);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.categories.list({
  'include': "recent_posts"
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
  ...
}}
CategoriesResponse getCategories = butterClient.getCategories(queryParams);
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for categories for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getCategories(
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

{
  "data": [
    {
      "name": "test category",
      "slug": "test-category"
    }
  ]
}

Returns a list of blog categories. You can include each category's posts using the include=recent_posts parameter.

Arguments
Argument Description
include Use include=recent_posts to return a category's recent posts.
Returns

A hash with a data property that contains an array of categories.

Retrieve a category

Example request

curl -X GET 'https://api.buttercms.com/v2/categories/product-updates/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

category = ButterCMS::Category.find("product-updates", {
    "include": "recent_posts"
})
var butter = require('buttercms')("your_api_token");

butter.category.retrieve('product-updates', {
    "include": "recent_posts"
}).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetCategory("product-updates", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchCategory('product-updates', [
    'include' => 'recent_posts'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.categories.get('product-updates', {
    'include': 'recent_posts'
})
Category dotnetCategory = butterClient.RetrieveCategory("product-updates",
    includeRecentPosts: true
);
//Async
Category fsharpCategoryWithPosts = 
  await butterClient.RetrieveCategoryAsync(categorySlug: "product-updates", 
    includeRecentPosts: true
);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.categories.retrieve("product-updates", {
  'include': 'recent_posts'
}).then((response) {
  print(response);
});
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
}}
CategoryResponse getCategory = butterClient.getCategory("product-updates", queryParams);
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for categories for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getCategory(
  slug: "test-category",
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

{
  "data": {
    "name": "Product Updates",
    "slug": "product-updates"
  }
}

Retrieves the details of a category. Supply the unique slug of the category.

Arguments
Argument Description
slug The slug of the category to be retrieved.
include Use include=recent_posts to return a category's recent posts.
Returns

A hash with a data property that contains a catgory object.

Tags

The tag object

Attribute Description
slug string Unique identifer
name string

List all tags

Example request

curl -X GET 'https://api.buttercms.com/v2/tags/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

tags = ButterCMS::Tag.all({"include": "recent_posts"})
var butter = require('buttercms')("your_api_token");

butter.tag.list({"include": "recent_posts"})
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetTags(params)
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
  ...
}}
TagsResponse getTags = butterClient.getTags(queryParams);
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchTags(['include' => 'recent_posts']);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.tags.all({'include': 'recent_posts'})
IEnumerable<Tag> tags = butterClient.ListTags(includeRecentPosts: true);
//Async
IEnumerable<Tag> tagsWithPosts = 
  await butterClient.ListTagsAsync(includeRecentPosts: true);
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.tags.list({
  'include': 'recent_posts'
}).then((response) {
  print(response);
});
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for tags for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getTags(
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

{
  "data": [
    {
      "name": "test tag",
      "slug": "test-tag"
    }
  ]
}

Returns a list of blog tags. You can incude each tags's posts using the include=recent_posts parameter.

Arguments
Argument Description
include Use include=recent_posts to return a tags's recent posts.
Returns

A hash with a data property that contains an array of tags.

Retrieve a tag

Example request

curl -X GET 'https://api.buttercms.com/v2/tags/product-updates/?include=recent_posts&auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

category = ButterCMS::Tag.find("product-updates", {
    "include": "recent_posts"
})
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");
Map<String,String> queryParams = new HashMap<String,String>(){{
  put("include","recent_posts");
}}
TagResponse getTag = butterClient.getTag("product-updates",queryParams);
var butter = require('buttercms')("your_api_token");

butter.tag.retrieve('product-updates', {
    "include": "recent_posts"
}).then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
params = map[string]string{"include": "recent_posts"}
ButterCMS.GetTag("product-updates", params)
<?
use ButterCMS\ButterCMS;
$butterCms = new ButterCMS('your_api_token');
$butterCms->fetchTag('product-updates', [
    'include' => 'recent_posts'
]);
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.tags.get('product-updates', {
    'include': 'recent_posts'
})
Tag dotnetTag = butterClient.RetrieveTag(
    "product-updates",
    includeRecentPosts: true
);
//Async
Tag fsharpTagWithPosts = 
  await butterClient.RetrieveTagAsync(
    tagSlug: "product-updates", 
    includeRecentPosts: true
  );
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.tags.retrieve("product-updates", {
  "include": "recent_posts"
}).then((response) {
  print(response);
});
// Unlike with fetching pages, it is not necessary
// to construct and pass a struct for categories for 
// the Swift SDK to consume, as their schema doesn't change.

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "YOUR_API_KEY")

butter.getTag(
  slug: "product-updates",
  parameters: [.include(value: "recent_posts")]
) // {Do something with result}

Example response

{
  "data": {
    "name": "Product Updates",
    "slug": "product-updates"
  }
}

Retrieves the details of a tag. Supply the unique slug of the tag.

Arguments
Argument Description
slug The slug of the tag to be retrieved.
include Use include=recent_posts to return a tag's recent posts.
Returns

A hash with a data property that contains a tag object.

Feeds

Arguments
Argument Default Description
category_slug Filter posts by a category's slug.
tag_slug Filter posts by a tag's slug.

RSS

Example request

curl -X GET 'https://api.buttercms.com/v2/feeds/rss/?auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

feed = ButterCMS::Feed.find(:rss)

var butter = require('buttercms')("your_api_token");

butter.feed.retrieve('rss') .then(function(resp) { console.log(resp.data) }).catch(function(resp) { console.log(resp) });

import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
ButterCMS.GetFeed("rss")
<?
use ButterCMS\ButterCMS;
$butter = new ButterCMS('your_api_token');
// Returns a SimpleXMLElement object
$feed = $butter->fetchFeed('rss');
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.feeds.get('rss')
XmlDocument rssFeed = butterClient.GetRSSFeed();
//Async
XmlDocument rssFeed = await butterClient.GetRSSFeedAsync();
import 'package:buttercms_dart/buttercms_dart.dart';

Butter butter = Butter('your_api_token');

butter.feed.retrieve("jennifer-smith", 'include': "recent_posts" }).then((response) { print(response); });

// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");

Document rssFeed = butterClient.getRSS();

import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "Your_API_KEY")

butter.getFeeds( name:"rss", )

Example response

{
  "data": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd\">\n \n  <url><loc>http://www.example.com/blog/this-is-a-blog-post</loc></url>\n \n</urlset>"
}

Retrieve a fully generated RSS feed for your blog.

Returns

A hash with a data property that contains an RSS feed.

Atom

Example request

curl -X GET 'https://api.buttercms.com/v2/feeds/atom/?auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

feed = ButterCMS::Feed.find(:atom)
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");

Document atomFeed = butterClient.getAtom();
var butter = require('buttercms')("your_api_token");

butter.feed.retrieve('atom')
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
ButterCMS.GetFeed("atom")
<?
use ButterCMS\ButterCMS;
$butter = new ButterCMS('your_api_token');
// Returns a SimpleXMLElement object
$feed = $butter->fetchFeed('atom');
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.feeds.get('atom')
XmlDocument atomFeed = butterClient.GetAtomFeed();
//Async
XmlDocument atomFeed = await butterClient.GetAtomFeedAsync();
import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "Your_API_KEY")

butter.getFeeds(
  name:"atom",
)

Example response

{
  "data": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd\">\n \n  <url><loc>http://www.example.com/blog/this-is-a-blog-post</loc></url>\n \n</urlset>"
}

Retrieve a fully generated Atom feed for your blog.

Returns

A hash with a data property that contains an Atom feed.

Sitemap

Example request

curl -X GET 'https://api.buttercms.com/v2/feeds/sitemap/?auth_token=your_api_token'
require "buttercms-ruby"
ButterCMS::api_token = "your_api_token"

feed = ButterCMS::Feed.find(:sitemap)
// https://github.com/ButterCMS/buttercms-java#categories
import com.buttercms.IButterCMSClient;
import com.buttercms.ButterCMSClient;

IButterCMSClient butterClient = new ButterCMSClient("your_api_token");

XmlDocument siteMap = butterClient.getSiteMap();
var butter = require('buttercms')("your_api_token");

butter.feed.retrieve('sitemap')
  .then(function(resp) {
    console.log(resp.data)
  }).catch(function(resp) {
    console.log(resp)
  });
import (
    "github.com/buttercms/buttercms-go"
)
ButterCMS.SetAuthToken("your_api_token")
ButterCMS.GetFeed("sitemap")
<?
use ButterCMS\ButterCMS;
$butter = new ButterCMS('your_api_token');
// Returns a SimpleXMLElement object
$feed = $butter->fetchFeed('sitemap');
?>
from butter_cms import ButterCMS
client = ButterCMS('your_api_token')
client.feeds.get('sitemap')
XmlDocument siteMap = butterClient.GetSitemap();
//Async
XmlDocument siteMap = await butterClient.GetSitemapAsync();
import ButterCMSSDK
var butter = ButterCMSClient(apiKey: "Your_API_KEY")

butter.getFeeds(
  name:"sitemap",
)

Example response

{
  "data": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<urlset xmlns=\"http://www.sitemaps.org/schemas/sitemap/0.9\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"http://www.sitemaps.org/schemas/sitemap/0.9 http://www.sitemaps.org/schemas/sitemap/0.9/sitemap.xsd\">\n \n  <url><loc>http://www.example.com/blog/this-is-a-blog-post</loc></url>\n \n</urlset>"
}

Retrieve a fully generated sitemap for your blog.

Returns

A hash with a data property that contains an XML sitemap.

Webhooks

Page Webhook Body

POST http://yoururl.com/process_webbook

{
  "data": {
    "id": "example-page-slug",
    "buttercms_id": 1234,
    "page_type": "news",
    "editor": "John Doe",
    "name": "Example page",
    "timestamp": "2022-02-14T18:11:09",
    "locale": "en",
    "status": "draft",
    "updated": "2022-02-14T18:11:09.791061Z",
    "published": null
  }, 
  "webhook": {
    "event": "page.all", 
    "target": "http://yoururl.com/process_webbook"
  }
}

Collection Item Webhook Body

POST http://yoururl.com/process_webbook

{
  "data": {
    "id": "your_collection",
    "itemid": '/v2/content/?keys=your_collection[_id=1234]',
    "label": "Your Collection Item",
    "editor": "John Doe",
    "name": "Example page",
    "timestamp": "2022-02-14T18:11:09",
    "locale": "en",
    "status": "published"
  }, 
  "webhook": {
    "event": "collectionitem.all", 
    "target": "http://yoururl.com/process_webbook"
  }
}

Blog Post Webhook Body

POST http://yoururl.com/process_webbook

{
  "data": {
    "id": "example-blog-post-slug",
    "_id": 1234
  }, 
  "webhook": {
    "event": "post.all", 
    "target": "http://yoururl.com/process_webbook"
  }
}

Get notified when content changes. Configure webhooks in your account settings to POST change notifications to your application.

When account has localization, webhook payload will have locale if event happened only for one locale i.e. page.published.

Note the data section will always contain id but may differ in other attributes based on the object.

Event types

Event Triggered when a...
post.all blog post has any activity on it
post.published blog post is published
post.draft draft blog post is saved
post.delete published blog post is unpublished or deleted
page.all page has any activity on it
page.published page is published
page.draft draft page version is saved
page.delete published page is deleted
page.unpublished published page is unpublished
collectionitem.all item has any activity on it
collectionitem.published item is published
collectionitem.draft draft item is saved
collectionitem.delete published item is deleted
collectionitem.unpublish published item is unpublished

Image API

We have an integration with Filestack. You can leverage their robust set of Image transformation capabilities. Full docs are here.

After you upload an image, to create a thumbnail, here's an example: