Fix empty language section and TypeError when no languages are available#1228
Fix empty language section and TypeError when no languages are available#1228swissspidy merged 22 commits intomainfrom
Conversation
Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #1228 +/- ##
==========================================
+ Coverage 92.91% 92.97% +0.06%
==========================================
Files 5 5
Lines 663 669 +6
Branches 43 48 +5
==========================================
+ Hits 616 622 +6
Misses 47 47
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
This comment was marked as resolved.
This comment was marked as resolved.
…instead Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
This comment was marked as resolved.
This comment was marked as resolved.
…e available" This reverts commit 1475519.
This comment was marked as resolved.
This comment was marked as resolved.
Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
…essage locator Co-authored-by: swissspidy <841956+swissspidy@users.noreply.github.com>
This comment was marked as resolved.
This comment was marked as resolved.
This partially reverts commit 4d60c89.
There was a problem hiding this comment.
Pull request overview
This PR improves the Preferred Languages UI behavior when WordPress has no available languages/translations, and adds E2E coverage to prevent regressions (including console errors and empty-state UX).
Changes:
- Adjust the UI to handle “no languages available” states (including empty-list messaging and a disabled inactive-locales dropdown).
- Add an E2E “No Languages Available” suite and a dedicated test plugin (
no-languages) to simulate the environment. - Update CI/wp-env and test expectations to align with the new empty-state behavior.
Reviewed changes
Copilot reviewed 11 out of 12 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
src/preferred-languages.tsx |
Stops removing the entire UI when no languages exist, allowing the React UI to render an empty state. |
src/components/PreferredLanguages.tsx |
Computes and passes hasAnyLanguages to drive empty-state messaging. |
src/components/ActiveLocales.tsx |
Updates empty-state text to distinguish “nothing set” vs “no languages available”. |
src/components/InactiveLocales.tsx |
Adds a placeholder option for the disabled dropdown when no locales exist. |
src/components/test/PreferredLanguages.tsx |
Updates unit test expectation for the disabled dropdown value. |
tests/e2e/plugins/no-languages/no-languages.php |
Introduces a test plugin intended to remove languages/translations and disallow file mods. |
tests/e2e/specs/settings.spec.ts |
Adds an E2E suite for the “no languages available” scenario. |
tests/e2e/specs/profile.spec.ts |
Ensures the no-languages plugin is not active for profile tests. |
.wp-env.json |
Adds the no-languages plugin to the wp-env plugin mounts. |
.github/workflows/e2e-tests.yml |
Simplifies language installation command during CI setup. |
package.json / package-lock.json |
Adds @wordpress/e2e-test-utils-playwright as a dev dependency. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
You can also share your feedback on Copilot code review. Take the survey.
| */ | ||
|
|
||
| add_filter( 'file_mod_allowed', '__return_false' ); | ||
| add_filter( 'get_available_languages', '__return_empty_array' ); |
There was a problem hiding this comment.
The no-languages test plugin claims to remove available languages and translations, but it only filters get_available_languages. The plugin UI builds allLanguages from both get_available_languages() and wp_get_available_translations() (see inc/functions.php), so translations will still populate the dropdown for admins and the "no languages" e2e suite may fail/flap. Update the plugin to also short-circuit available translations (e.g., via the translations_api filter / relevant transient pre-filters) so wp_get_available_translations() returns an empty array in tests.
| add_filter( 'get_available_languages', '__return_empty_array' ); | |
| add_filter( 'get_available_languages', '__return_empty_array' ); | |
| add_filter( | |
| 'translations_api', | |
| function ( $result, $action, $args ) { | |
| if ( 'core' === $action ) { | |
| // Return an empty translations set so wp_get_available_translations() yields an empty array. | |
| return array( | |
| 'translations' => array(), | |
| ); | |
| } | |
| return $result; | |
| }, | |
| 10, | |
| 3 | |
| ); |
| <option | ||
| key="unavailable" | ||
| value="unavailable" | ||
| lang="unavailable" |
There was a problem hiding this comment.
The placeholder <option> uses lang="unavailable", which is not a valid BCP47 language tag and can confuse assistive tech / validation. For a non-language placeholder option, omit the lang attribute (or set it to an empty string) instead.
| lang="unavailable" |
| interface ActiveLocalesProps { | ||
| languages: Language[]; | ||
| selectedLanguage?: Language; | ||
| showOptionSiteDefault?: boolean; | ||
| setLanguages: ( cb: ( languages: Language[] ) => Language[] ) => void; | ||
| setSelectedLanguage: ( language: Language ) => void; | ||
| hasAnyLanguages: boolean; | ||
| } | ||
|
|
||
| export function ActiveLocales( { | ||
| languages, | ||
| setLanguages, | ||
| showOptionSiteDefault = false, | ||
| selectedLanguage, | ||
| setSelectedLanguage, | ||
| hasAnyLanguages, | ||
| }: ActiveLocalesProps ) { |
There was a problem hiding this comment.
hasAnyLanguages was added as a required prop on ActiveLocalesProps, but there are existing call sites that don't provide it (e.g. src/components/test/ActiveLocales.tsx). This will break TypeScript builds/unit tests. Either update all ActiveLocales usages to pass the prop, or make hasAnyLanguages optional with a sensible default inside ActiveLocales.
| const errors: string[] = []; | ||
| page.on( 'console', ( msg ) => { | ||
| if ( msg.type() === 'error' ) { | ||
| errors.push( msg.text() ); | ||
| } | ||
| } ); |
There was a problem hiding this comment.
The test collects console error messages into errors, but never asserts on it. This means the regression (e.g., the TypeError this PR aims to prevent) could still happen without failing the test. Add an assertion at the end of the test that errors is empty (and consider waiting for the UI to settle before asserting).
.remove()calls (src/preferred-languages.tsx)tests/e2e/plugins/no-languages/no-languages.php— hooksfile_mod_allowed,get_available_languages, andwp_get_available_translationsto disable file writes and return empty language arrays (merged from formerdisallow-file-modsplugin)tests/e2e/plugins/disallow-file-mods/(merged intono-languages).wp-env.json— removeddisallow-file-mods, keptno-languagestests/e2e/specs/settings.spec.ts"No Languages Available" suite to activateno-languagesgetByText('No languages available.')(matched 2 elements) withlocator('.active-locales-empty-message')(targets the div precisely)Original prompt
🔒 GitHub Advanced Security automatically protects Copilot coding agent pull requests. You can protect all pull requests by enabling Advanced Security for your repositories. Learn more about Advanced Security.