Skip to content

Build/Test Tools: Treat DB_COLLATE and WP_DEVELOPMENT_MODE as dynamic constants. - #12958

Open
CallumBW95 wants to merge 1 commit into
WordPress:trunkfrom
CallumBW95:phpstan/dynamic-constants-db-collate-development-mode
Open

Build/Test Tools: Treat DB_COLLATE and WP_DEVELOPMENT_MODE as dynamic constants.#12958
CallumBW95 wants to merge 1 commit into
WordPress:trunkfrom
CallumBW95:phpstan/dynamic-constants-db-collate-development-mode

Conversation

@CallumBW95

Copy link
Copy Markdown

DB_COLLATE and WP_DEVELOPMENT_MODE both vary per installation, but neither is listed in dynamicConstantNames. PHPStan therefore resolves each to the empty string it happens to be given during analysis:

  • DB_COLLATE comes from wp-config-sample.php, pulled in via scanFiles, where it is define( 'DB_COLLATE', '' );.
  • WP_DEVELOPMENT_MODE comes from tests/phpstan/bootstrap.php, where it is define( 'WP_DEVELOPMENT_MODE', '' );.

Any conditional guarding either constant is then analysed as having a constant result, which accounts for the three baselined errors below. The conditionals are correct as written, so this change touches configuration only and leaves every source file alone.

Adding both constants to dynamicConstantNames resolves the three errors and empties two baselines. Those files are deleted along with their includes entries in phpstan.neon.dist.

Identifier Location Expression
ternary.alwaysFalse class-wp-debug-data.php:1548 DB_COLLATE ? DB_COLLATE : __( 'Empty value' )
ternary.alwaysFalse class-wp-debug-data.php:1634 WP_DEVELOPMENT_MODE ? WP_DEVELOPMENT_MODE : __( 'Disabled' )
booleanAnd.rightAlwaysFalse class-wpdb.php:846 defined( 'DB_COLLATE' ) && DB_COLLATE

Taking these errors at face value would suggest deleting the branch PHPStan considers unreachable. That would be a regression. It would drop the reported value on any site that sets either constant, and in wpdb::init_charset() it would force utf8_general_ci on multisite whatever collation the site has configured.

Why these two belong on the list

WP_DEVELOPMENT_MODE accepts 'core', 'plugin', 'theme', 'all', or an empty string to disable, as documented on wp_get_development_mode() in wp-includes/load.php. It is defined in tests/phpstan/bootstrap.php immediately alongside WP_DEBUG, WP_DEBUG_DISPLAY, WP_DEBUG_LOG, WP_CACHE, SCRIPT_DEBUG, MEDIA_TRASH and SHORTINIT, and all seven of those are already in dynamicConstantNames.

Core's own development environment also disagrees with the value the analysis assumes. tools/local-env/scripts/install.js writes WP_DEVELOPMENT_MODE from LOCAL_WP_DEVELOPMENT_MODE, which .env.example sets to core. A checkout installed with npm run env:install has the constant set to a non-empty value while PHPStan reads it as ''.

DB_COLLATE is set per site in wp-config.php and is empty only in the shipped sample file. DB_CHARSET sits next to it and is read the same way.

Background

dynamicConstantNames arrived in [61699] (2026-02-20), the changeset that integrated PHPStan into the core development workflow. git log -S against base.neon shows that neither constant has appeared on the list at any point, so these errors have been baselined since the baselines were first generated.

Testing instructions

  1. On trunk, npm run typecheck:php reports [OK] No errors, because all three occurrences are baselined.
  2. Delete tests/phpstan/baselines/ternary.alwaysFalse.neon and tests/phpstan/baselines/booleanAnd.rightAlwaysFalse.neon along with their includes entries, then run it again. PHPStan reports:
    • Ternary operator condition is always false. twice in src/wp-admin/includes/class-wp-debug-data.php
    • Right side of && is always false. in src/wp-includes/class-wpdb.php
  3. With this branch applied, npm run typecheck:php reports [OK] No errors with both baselines gone and no new errors elsewhere.
  4. npm run test:php is unchanged: 30774 tests, 4559286 assertions, 86 warnings, 44 skipped, identical before and after.

The usual risk when adding to dynamicConstantNames runs the other way. Making a value unknown can surface new errors in code that relied on PHPStan narrowing it. The full run above found none.

Trac ticket: https://core.trac.wordpress.org/ticket/65817

Use of AI Tools

AI assistance: Yes
Tool(s): Claude Code
Model(s): Claude Opus 5
Used for: tracing the three baselined errors back to the constant values supplied by scanFiles and bootstrap.php, git log -S archaeology against base.neon, and drafting this description. The diagnosis that this is a configuration issue rather than a source defect, the configuration change itself, the baseline regeneration, and verification against full PHPStan and PHPUnit runs were reviewed and confirmed by me in a local development environment.

… constants.

Both constants vary per installation, but PHPStan resolved each to the empty
string it is given during analysis: `DB_COLLATE` from `wp-config-sample.php`,
pulled in via `scanFiles`, and `WP_DEVELOPMENT_MODE` from
`tests/phpstan/bootstrap.php`. Conditionals guarding either were therefore
reported as having a constant result.

`WP_DEVELOPMENT_MODE` accepts 'core', 'plugin', 'theme', 'all', or an empty
string, and `DB_COLLATE` is set per site in `wp-config.php`, so both belong in
`dynamicConstantNames` alongside comparable entries such as `WP_DEBUG` and
`SCRIPT_DEBUG`.

This resolves three baselined errors and empties two baselines, which are
removed along with their `includes` entries in `phpstan.neon.dist`:

* `ternary.alwaysFalse`: two occurrences in `class-wp-debug-data.php`.
* `booleanAnd.rightAlwaysFalse`: one occurrence in `class-wpdb.php`.

No source changes are needed; the conditionals were already correct and only
the analysis was wrong.

Props CallumBW95.
See #65817.
@github-actions

Copy link
Copy Markdown

The following accounts have interacted with this PR and/or linked issues. I will continue to update these lists as activity occurs. You can also manually ask me to refresh this list by adding the props-bot label.

Core Committers: Use this line as a base for the props when committing in SVN:

Props callumbw95.

To understand the WordPress project's expectations around crediting contributors, please review the Contributor Attribution page in the Core Handbook.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant