Быстрый старт
Путь от нуля до опубликованной страницы. Понадобятся curl, jq и доступ администратора хотя бы к одному сайту сети. Все шаги обратимы: в конце страница и фрейм удаляются.
1. Выпустить токен
Откройте дашборд, войдите почтой или через Google, в меню пользователя выберите «Настройки» → «API-ключи» (https://onpress.pro/dashboard/settings/api) и в блоке «Токен API» нажмите «Выпустить токен». Токен показывается один раз — сразу скопируйте его. Выглядит так: op_ и 64 шестнадцатеричных символа.
Токен — это ваш пароль для API: у него нет своих прав, он действует от вашего имени на всех сайтах, где вы администратор. Повторный выпуск сразу убивает прежний токен. Подробно — в доступе.
2. Задать переменные
export OP_TOKEN=op_ВАШ_ТОКЕН
export API=https://onpress.pro/api/v2
Проверьте, что сервис жив и токен принят:
curl -s "$API/health"
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/me" | jq '{id: .user.id, name: .user.name, super: .user.is_super_admin, sites: .sites_count}'
{"ok":true,"db":true,"realm":"prod"}
{ "id": 42, "name": "Anna", "super": false, "sites": 3 }
401 missing_token или 401 invalid_token на втором запросе — токен не дошёл или неверный.
3. Узнать site_id своего сайта
Сайт в API v2 называется девятизначным идентификатором в пути: /api/v2/site/{site_id}/…. Узнать его можно тремя способами.
Карточка сайта по номеру блога. Если номер знаете (он виден в дашборде в разделе «Сайты» и в адресах wp-admin), карточка отдаст идентификатор:
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/sites/233" | jq '{site_id, blog_id, domain, home}'
{ "site_id": "x9HTLHECq", "blog_id": 233, "domain": "test.onpress.pro", "home": "https://test.onpress.pro" }
Список своих сайтов. Отдельной ручки списка в v2 нет; список отдаёт первая версия API, и она принимает тот же токен:
curl -s -H "Authorization: Bearer $OP_TOKEN" "https://onpress.pro/wp-json/onpress/v1/sites" \
| jq '.data[] | {id, domain}'
Номер из поля id подставьте в GET $API/sites/{id} — получите site_id.
В дашборде. Раздел «Данные» показывает адрес ручек сайта, site_id стоит прямо в нём.
export SITE=x9HTLHECq # ваш site_id
4. Посмотреть, что на сайте есть
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/site/$SITE/frames" | jq '[.frames[] | {slug, renders_on_request}]'
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/site/$SITE/pages?per_page=5" | jq '.items[] | {id, url, lang, frame: .frame.slug}'
Первый запрос — фреймы сайта (оболочки, шапка, подвал). Второй — первые пять страниц с адресами, языками и фреймами.
5. Загрузить фрейм
Фрейм — разметка, в которой будет собираться страница. Минимальная оболочка: заголовок из названия страницы и само содержимое.
curl -s -X POST "$API/site/$SITE/frames" \
-H "Authorization: Bearer $OP_TOKEN" -H 'Content-Type: application/json' \
-d "$(jq -n --arg html '<main class="start">
<h1 data-op-bind='"'"'{"text":"page.title"}'"'"'></h1>
<!-- onpress/content /-->
</main>' '{slug: "start", html: $html}')" \
| jq '{success, slug: .frame.slug, id: .frame.id, renders_on_request, live_reasons, warnings, bake: .bake.status}'
{
"success": true,
"slug": "start",
"id": "a2dc0bc0d2da6961",
"renders_on_request": true,
"live_reasons": ["inserts: op/content", "data-op-bind uses page.* tokens"],
"warnings": [],
"bake": "ok"
}
Атрибут data-op-bind держите в одинарных кавычках: внутри JSON двойные, и двойные кавычки атрибута оборвут его на первом же символе. renders_on_request: true значит, что фрейм зависит от страницы (в нём onpress/content) и собирается на каждом запросе. Слаг занят — придёт 409 slug_taken: возьмите другой или замените разметку существующего фрейма через PUT /frames/start.
6. Опубликовать страницу
Страница — markdown с frontmatter. Сохраните файл start.md:
---
name: "Первая страница"
slug: "start"
url: "/start/"
lang: "ru"
status: "publish"
frame: "start"
seo_title: "Первая страница на OnPress v2"
seo_description: "Проверка публикации через API."
---
Это **первая** страница, опубликованная через API v2.
## Что внутри
- заголовок взят из поля `name`;
- вид задаёт фрейм `start`;
- адрес — `/start/`.
Поле lang — слаг языка сайта. Посмотреть языки можно запросом GET $API/site/$SITE/languages; на сайте с одним языком его можно не указывать, язык по умолчанию подставится сам. Опубликуйте:
curl -s -X POST "$API/site/$SITE/pages/markdown" \
-H "Authorization: Bearer $OP_TOKEN" -H 'Content-Type: application/json' \
-d "$(jq -n --rawfile md start.md '{markdown: $md}')" \
| tee publish.json | jq '{success, updated, id, url, link, lang, printed, warnings}'
{
"success": true,
"updated": false,
"id": 6446,
"url": "/start/",
"link": "https://test.onpress.pro/ru/start/",
"lang": "ru",
"printed": {
"how": "on_request",
"url": "/start/",
"link": "https://test.onpress.pro/ru/start/",
"frame": { "id": "a2dc0bc0d2da6961", "slug": "start", "renders_on_request": true }
},
"warnings": []
}
url — путь страницы в дереве, link — адрес, по которому её отдаёт сайт. На тестовом сайте русский язык не основной, поэтому адрес идёт с префиксом /ru/. updated: false — страница создана. Повторная публикация того же файла найдёт страницу по слагу и родителю и обновит её: ответ придёт с updated: true, id останется прежним.
7. Открыть страницу
curl -s -o /dev/null -w '%{http_code}\n' "$(jq -r .link publish.json)"
Адрес берите из поля link ответа, а не собирайте сами: у страницы языка не по умолчанию он начинается с префикса языка (/ru/start/, если русский на сайте не основной), у языка по умолчанию префикса нет. 200 — страница собирается по шаблону фрейма. 404 на опубликованной странице почти всегда значит, что у неё нет фрейма или фрейм удалён: на сайте v2 страница без фрейма не показывается.
8. Прочитать обратно
# паспорт страницы, frontmatter и тело в markdown одним запросом
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/site/$SITE/pages/start" \
| jq '{id: .page.id, frame: .page.frame.slug, seo: .page.seo, markdown}'
# только тело — ровно тот формат, который принимает публикация
curl -s -H "Authorization: Bearer $OP_TOKEN" "$API/site/$SITE/pages/start/markdown" | jq -r .markdown > start.md
Выгрузка возвращает frontmatter с id и всеми полями, которые вы прислали. Правьте файл и публикуйте его тем же запросом из шага 6: круг «выгрузил — поправил — залил» не теряет ни поля, ни байта.
9. Поправить одно поле
Выдержку и фрейм можно поменять, не пересылая страницу:
curl -s -X PATCH "$API/site/$SITE/pages/start" \
-H "Authorization: Bearer $OP_TOKEN" -H 'Content-Type: application/json' \
-d '{"excerpt": "Короткое описание страницы"}' | jq '{changed, excerpt}'
{ "changed": ["excerpt"], "excerpt": { "from": "", "to": "Короткое описание страницы" } }
10. Убрать за собой
# в корзину можно и без force; force удаляет безвозвратно
curl -s -X DELETE "$API/site/$SITE/pages/start?force=true" \
-H "Authorization: Bearer $OP_TOKEN" | jq '{success, mode, removed: [.removed[].id]}'
curl -s -X DELETE "$API/site/$SITE/frames/start" \
-H "Authorization: Bearer $OP_TOKEN" | jq '{success, deleted, unbound_pages}'
{ "success": true, "mode": "delete", "removed": [6446] }
{ "success": true, "deleted": { "id": "a2dc0bc0d2da6961", "slug": "start", "block": "start", "element": null, "modifier": null }, "unbound_pages": [] }
Что дальше
- Как устроена платформа — почему всё именно так.
- Frontmatter: все поля и синтаксис markdown — что можно написать в странице.
- Фреймы и вставки — шапка, подвал, меню, списки.
- Рецепты — сайт с нуля, лендинг, документация, FAQ, многоязычность.