Some checks failed
continuous-integration/drone/push Build is failing
Enrolls wordpress as a maintained recipe (operator request 2026-08-03): - tests/wordpress/: recipe_meta (install-wizard-aware health 200/302, 900s deploy timeout for mariadb+core-copy first boot, WARM_CANONICAL), custom suite: health check, install-wizard completion + REST API round-trip (?rest_route= vs /wp-json/ splits DB vs .htaccess failure layers), and the sec4.3 post round-trip (XML-RPC write -> REST read -> permalink HTML, unique marker). PARITY.md documents the baseline (no recipe-maintainer parity corpus for wordpress). - nix/modules/bridge.nix: POLL_REPOS += recipe-maintainers/wordpress (!testme bridge enrollment; deploy to the cc-ci host follows separately after the in-flight /upgrade-all run - test-before-switch policy). Mirror recipe-maintainers/wordpress created + main synced to coopcloud upstream (adcd0e9f) with published tags. used-recipes.md gains 'wordpress weekly' in the orchestrator repo.
66 lines
2.6 KiB
Python
66 lines
2.6 KiB
Python
"""wordpress — §4.3 create-an-object + read-it-back: publish a post, read it back twice.
|
|
|
|
Flow:
|
|
1. `ensure_installed` (idempotent — run-scoped admin credentials from _wp.py).
|
|
2. Create a post with a unique marker title via **XML-RPC** `wp.newPost` (stdlib
|
|
xmlrpc.client; XML-RPC ships enabled in WP and authenticates with the admin
|
|
user/password directly — no cookie/nonce dance).
|
|
3. Read it back via the **public REST API** (`?rest_route=/wp/v2/posts/<id>`) — a different
|
|
subsystem than the one that wrote it — asserting id + rendered title match.
|
|
4. Fetch the public permalink `/?p=<id>` and assert the marker is in the served HTML.
|
|
|
|
Non-vacuous: the marker round-trips app → mariadb → app across three distinct read paths;
|
|
a post that didn't persist, a broken DB, or a wedged PHP-FPM fails at the layer that broke.
|
|
"""
|
|
|
|
from __future__ import annotations
|
|
|
|
import os
|
|
import ssl
|
|
import sys
|
|
import uuid
|
|
import xmlrpc.client
|
|
|
|
sys.path.insert(0, os.path.dirname(__file__))
|
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), "..", "..", "..", "runner"))
|
|
from _wp import ADMIN_PW, ADMIN_USER, ensure_installed, fetch_text # noqa: E402
|
|
from harness import http as harness_http # noqa: E402
|
|
|
|
_CTX = ssl.create_default_context()
|
|
_CTX.check_hostname = False
|
|
_CTX.verify_mode = ssl.CERT_NONE
|
|
|
|
|
|
def test_create_post_and_read_back(live_app):
|
|
ensure_installed(live_app)
|
|
|
|
marker = f"ccci-post-{uuid.uuid4().hex[:8]}"
|
|
proxy = xmlrpc.client.ServerProxy(f"https://{live_app}/xmlrpc.php", context=_CTX)
|
|
post_id = proxy.wp.newPost(
|
|
0,
|
|
ADMIN_USER,
|
|
ADMIN_PW,
|
|
{
|
|
"post_title": marker,
|
|
"post_content": f"cc-ci round-trip body for {marker}",
|
|
"post_status": "publish",
|
|
},
|
|
)
|
|
assert post_id and str(post_id).isdigit(), f"wp.newPost returned no post id: {post_id!r}"
|
|
|
|
# Read back via the public REST API (different subsystem than XML-RPC)
|
|
status, body = harness_http.http_get(
|
|
f"https://{live_app}/?rest_route=/wp/v2/posts/{post_id}", timeout=60
|
|
)
|
|
assert status == 200, f"GET rest_route /wp/v2/posts/{post_id} HTTP {status}: {body!r}"
|
|
assert isinstance(body, dict) and str(body.get("id")) == str(post_id), (
|
|
f"read-back id mismatch: {body!r}"
|
|
)
|
|
rendered = (body.get("title") or {}).get("rendered", "")
|
|
assert marker in rendered, f"read-back title {rendered!r} missing marker {marker!r}"
|
|
|
|
# And the public permalink serves the marker in HTML
|
|
status, raw = fetch_text(f"https://{live_app}/?p={post_id}")
|
|
assert status == 200, f"GET /?p={post_id} HTTP {status}"
|
|
assert marker in raw, f"permalink page does not contain the marker {marker!r}"
|