Real-time liveblogging plugin for WordPress with a React-based editor and a comment-backed entry store.
| Property | Value |
|---|---|
| Main file | liveblog.php |
| Text domain | liveblog |
| Version | 1.12.0 |
| Requires PHP | 7.4+ |
| Requires WP | 6.4+ |
| Default branch | develop |
| Maintenance branch | 2.x (parallel modernized line; do not cross-port without checking) |
liveblog/
├── liveblog.php # Main plugin file
├── classes/ # Legacy PHP classes (WPCOM_Liveblog_*)
├── src/
│ ├── react/ # React/Redux front-end (Lexical editor, live polling)
│ ├── admin/ # Admin-side JavaScript
│ └── styles/ # SCSS stylesheets
├── templates/ # PHP templates rendered to the front end
├── languages/ # Translation files (.pot, .po, .mo)
├── tests/
│ ├── Unit/ # Unit tests (no WordPress dependency)
│ └── Integration/ # Integration tests (require wp-env)
├── docs/ # End-user and developer reference
└── .github/workflows/ # CI: cs-lint, unit, integration, js-unit, lint, build, deploy
WPCOM_Liveblog(liveblog.php) — the central class. Heavily static. Owns most plugin wiring, the legacy<permalink>/liveblog/*AJAX endpoints (ajax_*methods), and the post-state machinery.WPCOM_Liveblog_Rest_Api(classes/class-wpcom-liveblog-rest-api.php) — registers the modernliveblog/v1REST routes used by the React front end.WPCOM_Liveblog_Entry(classes/class-wpcom-liveblog-entry.php) — wraps a single entry. Each entry is a WordPress comment.WPCOM_Liveblog_Entry_Query(classes/class-wpcom-liveblog-entry-query.php) — query API for retrieving entries by time, ID, key-event status, etc.WPCOM_Liveblog_Entry_Extend_Feature_*— feature classes for#hashtags,/commands,@authors,:emoji:.WPCOM_Liveblog_Entry_Key_Events— key-event widget and shortcode logic.WPCOM_Liveblog_Cron— auto-archive scheduling.WPCOM_Liveblog_Socketio*— optional WebSocket integration via Redis and the external liveblog-sockets-app.WPCOM_Liveblog_Lazyloader— lazy-loading entries on the front end.WPCOM_Liveblog_AMP*— AMP integration.WPCOM_Liveblog_WP_CLI—wp liveblogcommands (currentlyfix-archive).
- Runtime PHP:
composer/installers. WebSocket users also pull inpredis/predisandrase/socket.io-emitter. - Dev:
automattic/vipwpcs,phpunit/phpunit,yoast/wp-test-utils,php-parallel-lint,phpcompatibility/phpcompatibility-wp. - Front end: React 18, Lexical 0.43.x, Redux + Redux-Observable,
@wordpress/scriptsfor builds.
composer cs # PHPCS check (WordPress + VIP standards)
composer cs-fix # PHPCBF auto-fix
composer lint # PHP syntax lint
composer test:unit # unit tests (no WordPress)
composer test:integration # integration tests (requires wp-env)
composer test:integration-ms # multisite integration tests
composer coverage # tests with HTML coverage report
npm run build # build front-end assets via wp-scripts
npm run lint:js # ESLint
npm run lint:css # Stylelint
npm test # JavaScript unit tests (Jest)
npx wp-env start # start local WordPress on http://localhost:8888- Branch from
develop. Usefeature/<thing>orfix/<thing>naming. PRs targetdevelop. - Commits. Use the
/commitskill. Conventional Commits format. Explain why over what. - PRs. Use the
/prskill. The repo uses merge commits (not squash). - Code style. WordPress + VIP standards via PHPCS. Tabs for indentation. Run
composer csbefore pushing. - Tests. Unit tests for isolated logic, integration tests for anything that touches WordPress. Use the
Yoast\WPTestUtilsbase classes. - i18n. All user-facing strings use the
liveblogtext domain.
- Comment-based storage. Liveblog entries are stored as WordPress comments, not custom post types or custom tables. This is deliberate: cache invalidation on a comment-backed store scales much better than a post-backed one. Do not switch.
- Each entry change is a new entry. Updates and deletions insert a new entry that "replaces" the old one. This lets us cache the timestamp-bounded polling endpoints indefinitely without per-edit invalidation.
- Timestamp-bounded polling URLs. Endpoints take the form
/liveblog/<start>/<end>/, returning entries in that window. Closed ranges are cacheable forever. - AJAX polling by default, WebSockets optional. The plugin polls for updates by default. WebSocket support via Redis and Socket.IO is opt-in (
LIVEBLOG_USE_SOCKETIO) and only used for public posts. - Two parallel branches.
developis the legacy-architecture mainline.2.xis a parallel modernized branch (DDD layout undersrc/php/, DI container, namespaced classes). Security fixes and important bug fixes are typically backported by hand. Architectural changes do not cross-port automatically. - WordPress.org deployment. A GitHub Actions workflow deploys to the WordPress.org SVN repository. Do not modify SVN assets manually.
- Do not edit
vendor/,node_modules/orbuild/. They are regenerated. - Do not bring 2.x architecture (DI container, namespaced services, DDD layers) into
develop. The two branches are intentionally separate. - Run
composer csbefore committing. CI rejects PHPCS violations. - Integration tests require
npx wp-env startto be running. Otherwise they fail at bootstrap. - Comment storage conflicts. Entries are comments, so be careful with comment moderation, filtering, or other plugins that modify comment queries.
- Two version sources. Versions live in
liveblog.php(header +LIVEBLOG_VERSIONconstant) andpackage.json. Keep them in sync at release time. - Template tags are public API. Helper functions exposed to themes (e.g.
wpcom_liveblog_get_output()) are part of the public surface; do not rename or remove without a deprecation cycle. - Static state in
WPCOM_Liveblog. The class holds static state ($post_id,$is_rest_api_call, cached$entry_query). Reset these explicitly in tests that need a clean slate.