# CBX on WordPress — Platform Guide

> > Audience: integrators and developers running CBX on WordPress · Scope: how the > WordPress edition is wired — the adapter plugin, routing/URLs, the /cb-api…

Source: CBX documentation, version 4.0 preview (unreleased). Canonical page: https://docs.configbox.at/docs/4.0-preview/platform/wordpress/wordpress_platform_guide. Last updated 2026-08-03.

---
> **Audience:** integrators and developers running CBX on WordPress · **Scope:** how the
> WordPress edition is wired — the adapter plugin, routing/URLs, the `/cb-api/` endpoint,
> identity bridging, host CSS, WP-CLI, and migrations · **Last reviewed:** 2026-07-25
>
> **Store admins:** the task-oriented manual is the [Admin Guide](https://docs.configbox.at/docs/4.0-preview/admin-guide/) —
> its [CBX on WordPress](https://docs.configbox.at/docs/4.0-preview/admin-guide/getting-started/platform/cbx-on-wordpress)
> article covers logging in, the menu, and the shortcode in plain language. This document is the
> technical counterpart.

**TL;DR** — Unlike on Magento 2, CBX on WordPress is the **full application**: it brings
its own product lists, cart, checkout, orders and customer area. WordPress contributes hosting,
identity and the admin shell; a **thin adapter plugin** (`configbox.php` and friends, in the
plugin root) bridges WP's hooks to the shared, platform-agnostic app in
`wp-content/plugins/configbox/app/` (the component submodule). Storefront URLs are backed by
**hidden custom post types** that CBX maintains itself; XHR calls use the pretty
**`/cb-api/<controller>/<task>`** endpoint; `wp configbox …` mirrors the Joomla console
commands.

---

## 1. The two layers

| Layer | Files | Lives in |
|---|---|---|
| **WordPress adapter** | `configbox.php` (hooks, routing, CPTs, shortcode, admin menu), `cli.php` (WP-CLI wrapper), `templates/general.php` (loader template), `uninstall.php` | The plugin root — host-repo code, packaged with every WordPress release |
| **CBX app** | `app/…` — the shared component (identical code on Joomla/Magento 2) | The component submodule |

The app's own WordPress-specific bindings sit *inside* the component, behind the platform
abstraction: `app/external/kenedo/platforms/wordpress/` (the `KenedoPlatformWordpress` class),
`app/helpers/wordpress.php` (`ConfigboxWordpressHelper` — the WP-post sync), and
`app/observers/Wordpress.php`. Platform-specific behavior belongs there, not inline in shared
code.

## 2. Boot

- `configbox_init_kenedo()` (adapter) runs on WordPress's `init` hook and calls
  `initKenedo('com_configbox')`. Kenedo auto-detects the `wordpress` platform.
- Everything is gated by `shouldInitCb()`, which skips CBX entirely for requests that
  never need it (WP cron, heartbeat, Elementor AJAX, background queues). Respect the gate when
  adding hooks.
- A request "is a CBX request" when it carries `option=com_configbox` — the whole adapter
  pipeline keys off that request param, exactly like Joomla's component routing.

## 3. Storefront routing and URLs

WordPress has no component/frontname router, so the adapter builds one out of stock WP parts:

- **Hidden custom post types** back the SEF URLs: `cb_product_list`, `cb_product`, `cb_page`
  (configurator pages) and `cb_internal` (cart, account). CBX maintains these rows
  itself: `app/observers/Wordpress.php` reacts to admin saves/copies and calls
  `ConfigboxWordpressHelper::makePageFor…()` to insert/update the matching post per language.
  Never edit these posts by hand — they are regenerated from CBX data.
- `getRoute()` (`platforms/wordpress/general.php`) turns internal
  `index.php?option=com_configbox&view=…` URLs into the post permalinks, and translates the
  Kenedo params to WP conventions for everything else: `view`/`controller` → `page`,
  `controller.task` → `action`. In the admin area it targets `admin.php`, or `admin-ajax.php`
  for view-only/raw output.
- The CPT slug (`/cb_product/…`) is stripped from permalinks (`cb_remove_slug`), and
  `cb_parse_request` widens the main query's post-type search so the slugless URLs resolve.
- On CBX requests the adapter suppresses WP's 404 handling (`pre_handle_404`), clears the
  404 query-var that `parse_request` sets for unresolvable paths, and vetoes canonical
  redirects — the request must reach CBX untouched.
- Rendering goes through a **loader template**: `template_include` swaps in
  `templates/general.php`, which runs `configbox_execute_controller_task()` — the WP
  equivalent of Joomla's component dispatch (controller/task resolution, output buffering,
  observer-filtered output).

### The `/cb-api/` endpoint

Frontend XHR/API calls use `/cb-api/<controller>/<task>` — the same shape as Joomla's
`/cb-api` frontname route (see the [Joomla SEF doc](https://docs.configbox.at/docs/4.0-preview/platform/joomla/sef_urls)).
There is **no rewrite rule**: `configbox_cb_api_inject_params()` (top of `configbox.php`) runs
before anything else, recognizes the path, and injects the classic request params
(`option`, `controller`, `task`, `page`, `action`, `output_mode=view_only`) into the
superglobals — from there on the request is indistinguishable from a query-string URL. The
app side (`getEndpointUrl()`) only emits `/cb-api/` URLs when that adapter function exists
(feature detection), so an older adapter falls back to query-string endpoints. Admin XHRs
always keep going through `admin-ajax.php` for the admin context.

The **REST resource API** rides the same translation: `/cb-api/v1[/<path…>]` (any depth, dots
allowed — `openapi.json`, `schemas/read/product.json`) routes to the `apiv1` controller's single
`dispatch` task with everything after `v1/` in `cb_api_path`, mirroring the `v1` branch of
Joomla's system-plugin router. Since 2026-08-03 the WordPress adapter carries this branch, so
the token commands (`wp configbox token-*`) and the `api-export` artifacts refer to endpoints
that actually answer on WordPress.

## 4. Embedding via shortcode

`[configbox view=… id=…]` renders a CBX view inside any ordinary WP page:
`productlist` (legacy alias `productlisting`), `product`, `configuratorpage`, `cart`,
`checkout`, `user`. The shortcode boots Kenedo and returns the view HTML in place.

## 5. Identity bridging

- WP is the identity provider. The `wp_login` hook maps the WP user to the CBX user
  (`ConfigboxUserHelper`) and **moves a guest cart onto the logged-in user**; `wp_logout` logs
  the CB user out and resets the cart. Don't bypass these hooks.
- CBX user rows are created **lazily** (on first need), not at WP login.
- The CB "username" is the **billing e-mail**, which may differ from the WP login name —
  `KenedoPlatformWordpress::authenticate()` and `login()` therefore resolve the WP user by
  e-mail first, then by login name.

## 6. The admin area

The CBX backend runs inside wp-admin: `add_menu_page()` registers the **CBX** menu
(capability `edit_pages`), and every CB admin screen is dispatched through
`configbox_execute_controller_task()`. Admin XHRs are registered as `wp_ajax_<page>.<task>`
actions; for `output_mode=view_only` responses the adapter ends the request itself so
admin-ajax's trailing `0` never reaches the client.

## 7. Host CSS adaptation

WordPress themes — block themes especially — bleed into ConfigBox's markup, so the app ships
per-host correction stylesheets and serves them itself:
`KenedoPlatformWordpress::getHostStyleSheetUrls()` returns `hosts/wordpress-admin.css` in
wp-admin and `hosts/wordpress-site.css` on the site, and `KenedoView` emits them with every
ConfigBox view. The adapter plugin enqueues **nothing** — its old `assets/css/adapter.css` was
folded into `hosts/wordpress-site.css` so all host adaptation lives in one platform-driven
mechanism. Put new WordPress-only CSS corrections there, not in the plugin.
Full reference: [`technical/com_configbox_host_stylesheets.md`](https://docs.configbox.at/docs/4.0-preview/technical/host_stylesheets).

## 8. WP-CLI

`wp configbox …` mirrors the Joomla console commands one-for-one (thin wrapper `cli.php` →
shared `ConfigboxCliHelper`): `cache-clear`, `charset` (`--status`), `migrate` (`--status`,
`--clear-failed-flag`), `migrate-unblock`, `run-task`, `config-get/set/list`,
`sysvar-get/set/list` — plus `custom`, the dispatcher for **site-specific commands from the
customization layer** (`wp-content/plugins/configbox-customization/cli/commands.php` — the layer's
WordPress location; run `wp configbox custom` bare to list them — see
[`customization/com_configbox_custom_cli_commands.md`](https://docs.configbox.at/docs/4.0-preview/customization/custom_cli_commands)).
Host gotchas:

- The acting-user selector is **`--cb-user`** (WP-CLI reserves the global `--user` flag).
- The `migrate*` and `charset` commands define `CB_SUPPRESS_AUTO_UPDATES` at plugin load so
  booting Kenedo does not auto-apply the very migrations they are meant to report on/control —
  and so that a read-only `--status` call stays read-only.
- `wp cache flush` also purges the CBX caches (cache-generation stamp bump), matching
  `bin/magento cache:flush` behavior on Magento 2.

Full reference: [`technical/com_configbox_cli_commands.md`](https://docs.configbox.at/docs/4.0-preview/technical/cli_commands).

## 9. Migrations on WordPress

Update scripts (`app/helpers/updates/`) auto-apply on **every request that boots Kenedo —
including every `wp` CLI invocation** (except the suppressed `migrate*`/`charset`/`cache flush` commands
above). Logs land under the uploads dir:
`wp-content/uploads/cb-logs/configbox/configbox_upgrade_errors.log` (not `docroot/logs/` as on
Joomla). **WP-post-backed data changes are different**: renaming/creating the hidden CPT rows
is done in the adapter as an `init`-hook function guarded by a `get_option()` flag (see
`configbox_migrate_product_list_posts()` for the pattern), not as an update script. Full
reference: [`technical/com_configbox_migrations.md`](https://docs.configbox.at/docs/4.0-preview/technical/migrations).

## 10. Multilingual

The post-sync helper maintains one post per language, and CBX's own content strings live in its
EAV `configbox_strings` store — WP `.po`/`.mo` files are not involved. There is **no WPML
integration**: CBX handles its multilingual content itself.

## 11. Requirements & lifecycle

Activation checks (and deactivates on failure): PHP 7.1–8.4 (8.0 excluded), WordPress 5.0–6.99
(the ceiling is enforced, so a WordPress 7.0 host refuses activation until it is raised),
the ionCube loader (15+ on PHP 8.4, 14+ on 8.3, 13+ below), and the usual PHP extensions
(gd, mbstring, mysqli, xml, zip, openssl, …). Uninstall (delete via the Plugins screen) runs
`uninstall.php`, which drops all `configbox_*`/`cbcheckout_*` tables (removing referencing
foreign-key constraints first); the hidden CPT rows are not cleaned up.
