fix(ios): review adjustments for #419#440
Closed
jkmassel wants to merge 23 commits intofeat/improve-media-uploads-and-errorsfrom
Closed
fix(ios): review adjustments for #419#440jkmassel wants to merge 23 commits intofeat/improve-media-uploads-and-errorsfrom
jkmassel wants to merge 23 commits intofeat/improve-media-uploads-and-errorsfrom
Conversation
Bumps [@wordpress/wordcount](https://github.com/WordPress/gutenberg/tree/HEAD/packages/wordcount) from 4.41.0 to 4.42.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/wordcount/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/wordcount@4.42.0/packages/wordcount) --- updated-dependencies: - dependency-name: "@wordpress/wordcount" dependency-version: 4.42.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [@wordpress/primitives](https://github.com/WordPress/gutenberg/tree/HEAD/packages/primitives) from 4.41.0 to 4.42.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/primitives/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/primitives@4.42.0/packages/primitives) --- updated-dependencies: - dependency-name: "@wordpress/primitives" dependency-version: 4.42.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
* build(deps): Bump @wordpress/rich-text from 7.41.0 to 7.42.0 Bumps [@wordpress/rich-text](https://github.com/WordPress/gutenberg/tree/HEAD/packages/rich-text) from 7.41.0 to 7.42.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/rich-text/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/rich-text@7.42.0/packages/rich-text) --- updated-dependencies: - dependency-name: "@wordpress/rich-text" dependency-version: 7.42.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> * build: Generate @wordpress/rich-text patch --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: David Calhoun <github@davidcalhoun.me>
…#409) Bumps [@wordpress/global-styles-engine](https://github.com/WordPress/gutenberg/tree/HEAD/packages/global-styles-engine) from 1.8.0 to 1.9.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/global-styles-engine@1.9.0/packages/global-styles-engine) --- updated-dependencies: - dependency-name: "@wordpress/global-styles-engine" dependency-version: 1.9.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
* feat: Authorize AJAX with application passwords Include authorization header in AJAX requets, as we do not have cookies to send in the mobile app environment. * refactor: Rename AJAX and api-fetch configuration utilities * fix: Configure AJAX after the library loads If we configure AJAX before loading the library, the configuration is overridden. * test: Fix test imports and assertions * fix: Set the global WordPress admin AJAX URL This global is often used by WordPress Admin page scripts. * test: Assert AJAX configuration * feat: Allow configuring the Android asset loader domain Useful when needing to allow CORS for specific domains. * docs: Note AJAX support requirements * docs: Note AJAX CORS errors in troubleshooting documentation * fix: Add type checks before wrapping wp.ajax methods (#282) Address PR feedback about potential race condition. The code now checks if `window.wp.ajax.send` and `window.wp.ajax.post` are functions before wrapping them. This prevents TypeError when calling the wrapped function if the original method was undefined during configuration. Update tests to verify that missing methods remain undefined rather than being wrapped with an undefined reference. Co-authored-by: Claude <noreply@anthropic.com> * feat: conditionally reinstate VideoPress bridge When `videopress/video` is not in `allowed_block_types`, initialize the VideoPress AJAX bridge to handle `core/video` blocks extended to rely upon VideoPress upload services. AJAX auth is always initialized. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: filter lodash-js-after inline script from editor assets WordPress's `lodash-js-after` inline script calls `_.noConflict()` to restore `window._` to Underscore.js. Since GutenbergKit excludes core WordPress assets from the editor assets endpoint but doesn't load Underscore, this wipes `window._` to `undefined`. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat: vendor and load wp-util.js GutenbergKit excludes core WordPress assets from the editor assets endpoint, so wp-util.js (which provides wp.ajax and wp.template) must be vendored and loaded directly. Load it via dynamic import at the end of initializeWordPressGlobals() after jQuery and lodash are on window, since its IIFE captures jQuery via closure at execution time. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: align wp.ajax wrapper signatures with wp-util The wp.ajax.send and wp.ajax.post wrappers accepted a single options argument, but wp-util's implementation accepts (action, options). Align the wrapper signatures so the action argument is forwarded correctly. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: use home URL for iOS demo app site URL Use `homeUrlString()` instead of `siteUrlString()` from the REST API root response. The `url` field often returns `http://` for WordPress.com sites, while `home` returns the actual public-facing `https://` URL. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * feat: alias wp.media.ajax and wp.media.post to wp.ajax WordPress core sets these aliases in media-models.js, which GutenbergKit doesn't load. Alias them after auth wrapping so media uploads use the authenticated AJAX methods. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * build: Use wp-util from production WordPress release Avoid including latest changes from the WordPress/wordpress-develop repository. * docs: Expand inline comments * refactor: scope AJAX auth to same-site requests via ajaxPrefilter Replace jQuery.ajaxSetup and wp.ajax.send/post wrappers with a single jQuery.ajaxPrefilter that only injects the Authorization header when the request URL starts with the configured siteURL. This prevents leaking credentials to cross-origin requests and avoids argument normalization issues with the previous wp.ajax wrapper approach. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: strip trailing slash from siteURL before building AJAX URLs Prevents double-slash in constructed URLs (e.g., `https://example.com//wp-admin/admin-ajax.php`) when siteURL is provided with a trailing slash. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: warn instead of logging success when jQuery is unavailable for AJAX auth The ajaxPrefilter silently no-ops via optional chaining when jQuery is missing, but the debug log still claims auth was configured. Guard with an early return and warning so the log accurately reflects what happened. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: use origin-based matching for AJAX auth header injection Replace `startsWith(siteURL)` with `URL.origin` comparison so that scheme, host, and port must all match exactly. This prevents credential leakage to lookalike domains (e.g. `https://example.com.evil.com`). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs: separate AJAX config examples from Android requirement Move the iOS and Android code examples out of the Android-specific requirement so they are not visually nested under that bullet point. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: remove redundant AJAX setup from VideoPress bridge configureAjax() now initializes wp.ajax, wp.ajax.settings, and the AJAX URL before the VideoPress bridge runs, making the duplicate setup in initializeVideoPressAjaxBridge() unnecessary. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: add defensive guards to AJAX configuration - Wrap `new URL(siteURL)` in try/catch so a malformed siteURL logs a warning instead of throwing. - Guard `configureMediaAjax` against missing `wp.ajax.send`/`post` (e.g., if wp-util.js failed to load). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: validate assetLoaderDomain in Android EditorConfiguration Throw IllegalArgumentException if the value contains a scheme, path, or is blank, so callers get a clear error instead of a malformed asset URL at runtime. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs: add vendor README documenting wp-util.js source Record the upstream commit hash and rationale for vendoring so future maintainers know where the file came from and when to update it. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: add https scheme to WP.com site URL in Android demo app Account.WpCom.username stores just the hostname (e.g., "dcpaid.wordpress.com") since it is extracted via URI.host during OAuth. ConfigurationItem was using this bare hostname as siteUrl, producing invalid AJAX endpoints. Prepend "https://" to match the self-hosted flow, which receives a full URL from the callback. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: extract duplicated AJAX URL into local variable Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * docs: remove lint/format exclusion note from vendor README Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: derive Android WebView asset domain from site URL Derive the WebViewAssetLoader domain from the configured siteURL instead of defaulting to the synthetic appassets.androidplatform.net domain. This makes REST API and admin-ajax.php requests same-origin, eliminating CORS restrictions without requiring server-side headers. - Restrict shouldOverrideUrlLoading to /assets/ paths on the asset domain so arbitrary site pages don't load inside the WebView. - Reorder shouldInterceptRequest to check the cache interceptor before the asset loader, preventing cached JS/CSS from being short-circuited when both share the site domain. - Remove the now-unnecessary assetLoaderDomain configuration option from EditorConfiguration. - Update AJAX documentation to reflect the simplified setup. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude <noreply@anthropic.com>
* refactor: consolidate @WordPress mocks in __mocks__ directory Add shared mock stubs for @WordPress packages that crash when imported in the test environment. Flatten existing directory-based mocks (i18n, components) to top-level files for consistency. Remove exports that have no effect on test outcomes — the files themselves are still needed to prevent Vitest from importing the real modules. Tests declare vi.mock('module') without a factory to use the shared stub, and override locally only when test-specific behavior is needed. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * refactor: remove unnecessary vi.mock() calls from existing tests Remove @wordpress/preferences (editor.test.jsx) and @wordpress/i18n (editor-load-notice, offline-indicator) mocks that have no effect on test outcomes. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: coordinate bridge readiness and editor visibility for onEditorLoaded Replace the IntersectionObserver in use-editor-visible with a new useEditorReady hook that coordinates two conditions before signaling the native host via onEditorLoaded: 1. All window.editor.* bridge methods are assigned (from useHostBridge) 2. The editor content is visible in the viewport (via IntersectionObserver on the VisualEditor/TextEditor root element) useEditorReady returns a callback ref (for DOM attachment observation), a standard ref (for imperative access in useHostBridge), and a markBridgeReady callback. The callback ref is forwarded to VisualEditor/TextEditor via forwardRef so the observer fires when the actual editor content is in the viewport — not just the wrapper div. The editorLoaded() call is deferred by one frame via requestAnimationFrame so the browser has painted the editor content before the native host starts the fade-in animation. Remove the now-unused useEditorVisible hook and add the missing window.editor.focus cleanup on unmount. The error path in editor-environment.js retains its own editorLoaded() call since useEditorReady won't run when initialization fails. Addresses CMM-2008 and CMM-2009. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * fix: add isReady guards to iOS JS bridge calls Add isReady guards to undo(), redo(), dismissTopModal(), isCodeEditorEnabled, appendTextAtCursor(), getContent(), and getTitleAndContent(). Previously only setContent() was guarded. Reset isReady to false in controllerWebContentProcessDidTerminate so JS bridge calls are blocked until the editor re-emits onEditorLoaded after a WebView process crash and reload. Fire-and-forget methods silently return when not ready. Async throwing methods (getContent, getTitleAndContent) throw EditorNotReadyError so callers can handle the case explicitly. Addresses CMM-2008 and CMM-2009. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test: add tests for bridge setup ordering guarantees Verify window.editor.* methods are assigned and markBridgeReady is called, and that all methods are cleaned up on unmount. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* ci: add CodeQL workflow for Swift analysis on macOS The default CodeQL setup only runs on Linux runners, which can't build this project's Swift package (requires Xcode/iOS SDK). This adds a dedicated workflow using macos-15 runners with path filtering so it only runs when Swift code changes. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * ci: add workflow_dispatch trigger to CodeQL Swift workflow Allows manual triggering from the Actions tab for testing. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * ci: trigger CodeQL Swift workflow with trivial whitespace change Remove trailing newline to trigger the path-filtered workflow on this PR. This can be reverted after verifying the workflow passes. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * ci: replace Swift-only workflow with full CodeQL workflow The default CodeQL setup and custom workflows can't coexist, so this replaces the default setup with a single workflow covering all languages. Swift runs on macos-15 with Xcode 16.3 (for Swift 6.2); JS, Kotlin, and Actions run on ubuntu-latest with autobuild. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * ci: fix Swift Xcode version and disable default CodeQL setup - Use Xcode 26.0.1 (Swift 6.2) instead of Xcode 16.3 (Swift 6.1) - Disabled default CodeQL setup via API since custom and default workflows cannot coexist - Reverted back to Swift-only + all-languages workflow Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
…#414) Bumps the npm_and_yarn group with 1 update in the / directory: [lodash](https://github.com/lodash/lodash). Updates `lodash` from 4.17.23 to 4.18.1 - [Release notes](https://github.com/lodash/lodash/releases) - [Commits](lodash/lodash@4.17.23...4.18.1) --- updated-dependencies: - dependency-name: lodash dependency-version: 4.18.1 dependency-type: direct:production dependency-group: npm_and_yarn ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
* refactor: Move editor loading UI into GutenbergView GutenbergView previously extended WebView directly and delegated all loading UI (progress bar, spinner, error states) to consumers via the EditorLoadingListener interface. This forced every app embedding the editor to implement its own loading UI boilerplate. This change makes GutenbergView extend FrameLayout instead, containing an internal WebView plus overlay views for loading states: - EditorProgressView (progress bar + label) during dependency fetching - ProgressBar (circular/indeterminate) during WebView initialization - EditorErrorView (new) for error states The view manages its own state transitions with 200ms fade animations, matching the iOS EditorViewController pattern. The EditorLoadingListener interface is removed entirely — consumers no longer need loading UI code. Changes: - GutenbergView: WebView -> FrameLayout with internal WebView child - New EditorErrorView for displaying load failures - Delete EditorLoadingListener (no longer needed) - Simplify demo EditorActivity by removing ~90 lines of loading UI - Update tests to use editorWebView accessor for WebView properties - Delete unused activity_editor.xml layout Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Cancel in-flight view animations in onDetachedFromWindow Prevents withEndAction callbacks from firing on detached views if the editor is closed mid-animation. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Remove unused LoadingState enum from GutenbergView Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> Remove unused ASSET_LOADING_TIMEOUT_MS constant from GutenbergView Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * Clear openMediaLibraryListener and logJsExceptionListener in onDetachedFromWindow These two listeners were not being nulled out during teardown, inconsistent with all other listener cleanup in the same method. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * Update AGP * Add required constructor * Enforce valid postId using the type system * fix: use webView reference in dispatchConnectivityEvent After the FrameLayout refactor, `this.evaluateJavascript` no longer compiles since GutenbergView is no longer a WebView. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * fix: update detekt baseline and tests for FrameLayout refactor The Detekt baseline referenced `GutenbergView : WebView` which no longer matches after the FrameLayout change. Two tests also referenced `webViewClient` directly on GutenbergView instead of via `editorWebView`. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
* fix: normalize namespace trailing slash in RESTAPIRepository on both platforms Ensures namespaces like "sites/123" (without trailing slash) produce the same URLs as "sites/123/" so callers don't need to worry about the convention. Adds tests on both platforms to verify. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * fix: use try? in namespace URL tests to avoid mock decoding failures The mock HTTP client returns empty data, causing JSON decoding errors that prevented the namespace URL assertions from being reached. Since these tests only verify URL construction, try? is appropriate. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com> Co-authored-by: David Calhoun <github@davidcalhoun.me>
* fix: coerce post ID 0 to nil on both platforms and JS bridge WordPress uses 0 as a sentinel for "no post" in several contexts; passing it through causes incorrect API requests and editor state. This treats post ID 0 as nil/absent across Android, iOS, and the JS bridge layer, with unit tests on both platforms. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com> * test: add JS unit tests for post ID 0 coercion Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com> Co-authored-by: David Calhoun <github@davidcalhoun.me>
…422) Increase the `waitForClearToTakeEffect` polling timeout from 1s to 5s and add `.timeLimit(.minutes(1))` to the two clear-related tests. `URLCache.removeAllCachedResponses()` is internally asynchronous and CI environments with slower I/O can exceed the previous 1s window. Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
* build(deps): Bump @wordpress/blocks from 15.15.0 to 15.16.0 Bumps [@wordpress/blocks](https://github.com/WordPress/gutenberg/tree/HEAD/packages/blocks) from 15.15.0 to 15.16.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/blocks/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/blocks@15.16.0/packages/blocks) --- updated-dependencies: - dependency-name: "@wordpress/blocks" dependency-version: 15.16.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> * build: Re-generate @wordpress/rich-text patch --------- Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com> Co-authored-by: David Calhoun <github@davidcalhoun.me>
Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 8.0.0 to 8.0.3. - [Release notes](https://github.com/vitejs/vite/releases) - [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite/commits/create-vite@8.0.3/packages/vite) --- updated-dependencies: - dependency-name: vite dependency-version: 8.0.3 dependency-type: direct:development update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Bumps [@wordpress/style-engine](https://github.com/WordPress/gutenberg/tree/HEAD/packages/style-engine) from 2.42.0 to 2.43.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/style-engine/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/style-engine@2.43.0/packages/style-engine) --- updated-dependencies: - dependency-name: "@wordpress/style-engine" dependency-version: 2.43.0 dependency-type: direct:production update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
#428) Bumps [@wordpress/prettier-config](https://github.com/WordPress/gutenberg/tree/HEAD/packages/prettier-config) from 4.41.0 to 4.43.0. - [Release notes](https://github.com/WordPress/gutenberg/releases) - [Changelog](https://github.com/WordPress/gutenberg/blob/trunk/packages/prettier-config/CHANGELOG.md) - [Commits](https://github.com/WordPress/gutenberg/commits/@wordpress/prettier-config@4.43.0/packages/prettier-config) --- updated-dependencies: - dependency-name: "@wordpress/prettier-config" dependency-version: 4.43.0 dependency-type: direct:development update-type: version-update:semver-minor ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
…ry (#430) Bumps the npm_and_yarn group with 1 update in the / directory: [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite). Updates `vite` from 8.0.3 to 8.0.5 - [Release notes](https://github.com/vitejs/vite/releases) - [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md) - [Commits](https://github.com/vitejs/vite/commits/v8.0.5/packages/vite) --- updated-dependencies: - dependency-name: vite dependency-version: 8.0.5 dependency-type: direct:development dependency-group: npm_and_yarn ... Signed-off-by: dependabot[bot] <support@github.com> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
#432) * fix(android): include restBase and restNamespace in GBKit post payload The api-fetch filterEndpointsMiddleware blocks server fetches for the post being edited (preventing them from overwriting local edits with stale or context-mismatched data). The middleware bails out early when either restBase or restNamespace is missing from window.GBKit.post: if ( id === undefined || ! restNamespace || ! restBase ) { return next( options ); // lets the request through } iOS already populates these from EditorConfiguration.postType (PostTypeDetails struct), but Android's GBKitGlobal.Post only had { id, type, status, title, content }. As a result, when the editor mounted with an existing post ID, WordPress core data fetched the post via GET /wp/v2/posts/{id} unfiltered, and the response (without context=edit) overwrote the title and content set from the native host with empty values — causing the editor to briefly show the loaded post before clearing it. Adds restBase and restNamespace fields to GBKitGlobal.Post and derives them from the postType slug ("post" → "posts", "page" → "pages", custom types pluralized). Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com> * test(android): assert restBase and restNamespace in GBKitGlobal payload Adds coverage for the restBase/restNamespace fields recently added to GBKitGlobal.Post, including the heuristic pluralization for custom post types. * fix(api-fetch): apply post fallbacks in filterEndpointsMiddleware The middleware previously bailed out when window.GBKit.post was missing restBase or restNamespace, letting the editor's GET /wp/v2/posts/{id} request through unfiltered. The response (without context=edit) then clobbered the host-provided title and content. Apply the same fallback contract that getPost() already uses ('posts' / 'wp/v2'), centralized in a new POST_FALLBACKS export so both consumers stay in sync. Hosts that omit those fields now get the filter applied with sensible defaults instead of silently slipping past. * docs(api-fetch): note follow-up for filterEndpointsMiddleware Captures a @todo explaining that this middleware could likely be removed in favor of properly seeding entity content into the store on initialization, and links to the historical commit that added it. --------- Co-authored-by: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
) * fix: normalize data store attributes to plain strings in JS bridge The WordPress data store's `getEditedPostContent()` may return `{raw, rendered}` objects instead of plain strings because it uses `getEditedEntityRecord` (which preserves the object shape) rather than `getRawEntityRecord` (which extracts `.raw`). Add `normalizeAttribute()` to always extract the raw string before returning values to the native host via `getTitleAndContent()`. Also remove the redundant `getContent()` bridge method and its iOS public API — `getTitleAndContent()` is the single accessor for editor state. * fix: harden normalizeAttribute and extend test coverage - Make normalizeAttribute explicitly handle null/undefined instead of relying on typeof null === 'object' with optional chaining - Coerce non-string primitives to strings via String() - Normalize postTitleRef/postContentRef initialization defensively - Normalize block content in appendTextAtCursor - Add unit tests for edge cases: null, undefined, {raw: null}, {raw: undefined}, arrays, non-string primitives - Add unit tests for changed flag correctness with object values - Add unit tests for appendTextAtCursor (object content, string content, no block selected, unsupported block type) - Add changed flag assertions to E2E object-injection regression tests * fix: restore getContent() as convenience accessor Restore the getContent() bridge method on both JS and iOS. It is used in contexts where the editor has no title field (e.g. comment editors). Both implementations delegate to getTitleAndContent() so normalization happens in one place. * test: use project-level mocks for WordPress packages in host bridge tests * fix: use Array.isArray for explicit array handling in normalizeAttribute
Change `bytesWritten` from `Int` to `Int64` for consistency with `expectedContentLength` and `maxBodySize`, which are already `Int64`.
Expose maxRequestBodySize on MediaUploadServer.start() and add an integration test that sends an oversized request and verifies the response includes both a 413 status and CORS headers.
Contributor
Author
|
Recreating with correct base — branch had extra commits from trunk. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Suggested changes from reviewing #419.
Changes
1. Use
Int64forHTTPRequestParser.bytesWrittenbytesWrittenwasIntwhileexpectedContentLengthandmaxBodySizeare alreadyInt64. This is consistent on all Apple platforms today (whereIntis 64-bit), but usingInt64explicitly matches the convention used throughout the parser and avoids unnecessaryInt64(...)casts at comparison sites.2. Add end-to-end test for 413 + CORS headers
The core motivation for the drain+handler routing in #419 is that 413 responses include CORS headers so the WebView's
fetch()can read them. This adds an integration test that sends an oversized request toMediaUploadServerand verifies both the 413 status code and theAccess-Control-Allow-Originheader.To support this,
MediaUploadServer.start()now exposes amaxRequestBodySizeparameter (defaulting to the existing 4 GB), so the test can use a small limit without sending gigabytes of data.Related issues
OutputStream.writereturn value 0 treated as fatal in bound stream writersMediaUploadServertests silently skip when server can't bind