Özel sürüm önizlemesiGerçek ödeme alınmazSürüm ayrıntıları ↗

EN · ÖZGÜN DEPO BELGESİ

WordPress yönetim adaptörü

Özgün İngilizce metin. Komutlar ve kanıtlar, belgede belirtilen revizyona ve ortama aittir.

product/licensing/wordpress-admin/README.md

Bu sayfada

Original WordPress entitlement admin prototype

This standalone original plugin binds the existing entitlement client and fixed HTTP transport to explicit WordPress administrator actions. It is separate from the inherited paid cache, the original free cache and upstream licensing APIs. An original premium entitlement does not grant upstream software rights. There is no checkout, payment verification, customer account, license recovery, automatic installer or frontend/cache integration.

Operator configuration

Keep this directory alongside the original client.php and transport.php, for example beneath an installed original-entitlement/ plugin directory. Activate wordpress-admin/plugin.php. The operator must define a trusted configuration in wp-config.php or an equivalent private deployment configuration:

define('ORIGINAL_ENTITLEMENT_ADMIN_CONFIG', [
    'service_origin' => 'https://licenses.operator.example',
    'public_keys' => ['fixture-v1' => $operatorPublicVerificationPem],
    'cache_directory' => '/private/operator/entitlement-cache',
]);

The service address and verification keys never come from a posted field. The public PEM must come from the trusted operator, not the licensing HTTP response. The cache directory must already exist, be writable, and resolve outside both WordPress’s installation and content roots. Use a genuinely private filesystem location: the plugin cannot detect every additional directory a server publishes. The existing entitlement client locks and verifies local files, with bounded signed deadlines and denial handling. No private signing keys belong in WordPress.

The installed origin is derived from network_home_url() for multisite and home_url() for single-site and normalized to an HTTPS origin. Domain/subdomain/port changes fail closed against the saved identity. Paths are not independent activations; network installations share one network identity and require manage_network_options. Single-site installations require manage_options. Domain ownership must first be independently verified and approved on the backend by an operator. There is no automatic site migration.

Explicit workflow

  1. Open Settings → Original entitlement (network Settings for multisite). GET renders only locally verified status and key fingerprints. No HTTP occurs.
  2. Paste an original license and Save license. Only this action stores the credential and a randomly generated 256-bit installation key. Re-saving the same license preserves the installation key. Credentials are held in a single WordPress option (autoload disabled) or network site option and read back to confirm persistence. They are not rendered in HTML or sent as URL parameters. This is database credential storage, not an encrypted secret vault; protect database backups and any object-cache copies under normal operator controls.
  3. Activate installation explicitly posts to /activate, then verifies and persists /entitlement. Backend origin approvals, ownership and site limits remain authoritative. Refresh verified status calls /entitlement only.
  4. Deactivate installation posts /deactivate, then obtains a signed inactive denial. Backend ownership remains bound. A server outage cannot create or extend a grant. If refresh fails after a state change, existing client deadlines remain bounded; retry explicitly to observe the signed denial.
  5. Check original update metadata validates the existing client’s server response. Only version and SHA-256 are stored/displayed; the bearer download token is discarded. Nothing downloads, installs, or hooks a WordPress updater.

Every mutation checks POST, capability and a WordPress nonce before constructing configuration, storage or transport. The binding repeats this gate for direct callers. No init, frontend, cron, REST, cache read/write or automatic refresh hook is registered. A failed action redirects with a generic result; posted keys and raw transport errors are not placed in the redirect or notice.

Changing the license generates another installation identity. Deactivate the old license first when freeing its slot is intended. Operator key replacement, installation recovery, checkout/customer support, uninstall cleanup and an actual premium product installer remain deliberate future work, not claimed workflows.

Focused tests and fixture-only HTTP

php -n product/licensing/wordpress-admin/test.php

The test uses WordPress API doubles and a real ephemeral RSA signer. It covers permission, nonce and GET rejection before effects, failed option writes, installation persistence, redacted/local-only status, explicit activate and signed refresh, sanitized update metadata, signed deactivation, installed-origin changes, multisite capability and rejection of an HTTP service/web-root cache. Boot checks allow only the admin menu and admin-post hooks and verify zero transport calls. No keys or fixture credentials are committed.

For a separate CLI integration fixture only, ORIGINAL_ENTITLEMENT_ADMIN_FIXTURE must be exactly true and WP_CLI must be true. A trusted config may then set fixture_loopback => true, an exact http://127.0.0.1:PORT service origin, and a fixture_site HTTPS origin preapproved on the synthetic backend. This exception is unavailable to web/admin requests. It allows the parent integration runner to exercise the actual local backend without modifying TLS or network settings. Use only an ephemeral original ZIP and temporary credentials. The Python service is a reference fixture; the API-compatible Go backend is the runnable service documented in ../go/README.md.

Real WordPress ↔ Go fixture validation

real-wordpress-go.php is a bounded WP-CLI test against an actual local Go service. It requires ORIGINAL_ADMIN_DISPOSABLE_FIXTURE=1, the fixture-admin superadmin, and ORIGINAL_ADMIN_FIXTURE_CONFIG pointing to a private /dev/shm/original-admin-fixture/config.json. The operator handoff contains only synthetic license_key, trusted public_pem, and exact numeric-loopback service_origin. The backend must already approve https://original-admin.fixture.test for that license and expose a synthetic original ZIP. Prepare the sibling client.php, transport.php, binding and cache/ directory readable/writable by the WordPress fixture UID. Do not execute on a real site: this stores the two original-admin network option keys.

Run the flow, then read its persisted denial in a separate WordPress process:

wp eval-file /dev/shm/original-admin-fixture/wordpress-admin/real-wordpress-go.php --user=fixture-admin --allow-root
wp eval-file /dev/shm/original-admin-fixture/wordpress-admin/real-wordpress-go.php verify-denial --user=fixture-admin --allow-root

The actual disposable multisite run passed on WordPress 6.8.3 / PHP 8.3.28 using UID 33 and the Go service on shared-container loopback. It verified real WordPress capability and nonce rejection before effects, GET mutation rejection, identity save/stable resave, activation, RSA entitlement refresh, local GET-mode status with zero HTTP and redacted keys, explicit check, verified update metadata without bearer persistence, and deactivation. Exactly six explicit backend calls occurred: /activate, /entitlement, /entitlement, /updates, /deactivate, /entitlement. A second WP process verified the persisted signed inactive denial with zero backend calls. No inherited/free cache configuration, plugin, drop-in, SQL schema or paid license API changed. Root integration owns fixture cleanup. This is real WordPress API/Go HTTP evidence, not a browser-admin-page or payment checkout test. Fixture credentials and private keys are excluded from the repository.

For the actual paid-plugin adapter and explicit bounded download/updater/optional refresh interfaces, see README.paid.md.