feat: add bundled XDN/XPA delivery client package [AIS-147]#27
Closed
Lisa White (whitelisab) wants to merge 11 commits into
Closed
feat: add bundled XDN/XPA delivery client package [AIS-147]#27Lisa White (whitelisab) wants to merge 11 commits into
Lisa White (whitelisab) wants to merge 11 commits into
Conversation
Creates @contentful/experiences-client — an internal workspace package that wraps @contentful/experience-delivery and encapsulates XDN vs. XPA endpoint selection behind a createExperienceClient() factory. preview: false routes to the XDN (https://xdn.contentful.com) client; preview: true routes to the XPA preview endpoint (https://preview.xdn.contentful.com). Both adapter packages now list @contentful/experiences-client as a workspace dependency, and @contentful/experience-delivery is removed as a direct dep from both example apps whose delivery-client helpers are updated to use the factory. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Customers import from the framework adapter they already have installed. The @contentful/experiences-client internal package is now a hidden transitive dep, not something callers reference directly. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Eliminates manual property forwarding — view, fragment, and any future top-level clients on the Fern-generated base are inherited automatically. Also drops accessToken from the public interface (no reason to expose a credential on the client object). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Prevents accidental npm publish via nx release. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This reverts commit 8084c19.
- New packages/client/README.md explaining the factory, XDN/XPA selection, and why it's a separate package - AGENTS.md: repo layout, package roles table, and delivery-client design decision updated to reflect bundled client approach - Root README: install line drops @contentful/experience-delivery, getting started example uses createExperienceClient, workspace table adds client - adapter-react README: install line, public API listing, and quick reference updated to match Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Chase Poirier (chasepoirier)
left a comment
Contributor
There was a problem hiding this comment.
I'm wondering, do you think we need an additional package defined in this monorepo or could we just simply have the https://github.com/contentful/contentful-experience-delivery.js be used directly from each adapter?
Looking at the current source code of the new client package, it seems to be a simple wrapper around the existing delivery client with a helper function to instantiate an instance of the class.
We could simplify a lot of code here by not having an additional package, unless do you think this new client package will grow significantly over time?
6 tasks
Lisa White (whitelisab)
marked this pull request as draft
July 10, 2026 22:53
Lisa White (whitelisab)
added a commit
that referenced
this pull request
Jul 14, 2026
…IS-147] (#30) * feat(client): scaffold packages/client with ContentfulViewDeliveryClient re-export Creates the packages/client workspace package (@contentful/experiences-client). Replaces the ExperienceClient class approach from PR #27 — re-exports ContentfulViewDeliveryClient directly from @contentful/experience-delivery so consumers have full client access without a separate install. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * feat(client): add fetchExperience with flat discriminated union signature fetchExperience accepts either inline credentials ({ accessToken, preview?, spaceId, environmentId, experienceId }) or a pre-created ContentfulViewDeliveryClient ({ client, spaceId, environmentId, experienceId }). Inline path constructs the client internally with XDN or XPA base URL based on the preview flag. Pre-created client path is pass-through, enabling reuse across calls. When personalization is passed, dispatches to getExperienceWithOverrides and opts into sourceMap automatically. Returns PortableRenderPlan | null (null when payload has no nodes). Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * feat(adapters): re-export ContentfulViewDeliveryClient and fetchExperience Both @contentful/experiences-react and @contentful/experiences-svelte now re-export ContentfulViewDeliveryClient and fetchExperience from @contentful/experiences-client, so consumers install only the framework adapter and never touch @contentful/experience-delivery or @contentful/experiences-client directly. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * feat(examples): migrate to fetchExperience from adapter; drop @contentful/experience-delivery Both example apps now import fetchExperience and ContentfulViewDeliveryClient from their framework adapter rather than @contentful/experience-delivery directly. The separate resolveExperience call is removed — fetch and resolve happen in one step via fetchExperience. delivery-client.ts in each example wraps the SDK call with a thin page-level helper that reads env vars and passes the config. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * feat(examples): inline fetchExperience directly into page files; drop delivery-client wrappers Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * chore: update lock file for @contentful/experiences-client; apply prettier Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * fix(client): add project.json for NX build graph; use ContentfulViewDelivery namespace for request type Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * refactor(client): remove personalization placeholder; call getExperience unconditionally Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * docs: update READMEs and AGENTS for fetchExperience + packages/client Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * chore: fix prettier formatting on AGENTS.md Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com> * refactor(client): split fetchExperience into 3 positional args; replace preview with host Signature is now `fetchExperience(experienceOptions, clientOptions, resolveOptions)`, with `ClientOptions` a discriminated union of `{ accessToken, host? }` or `{ client }`. `host` is a full base URL string that's passed through as `baseUrl`; XPA vs XDN endpoint selection is now the caller's concern. Defaults to XDN when omitted. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com> * feat(client): add createClient helper mapping accessToken/host to token/baseUrl createClient is a functional constructor over ContentfulViewDeliveryClient that maps the SDK's option names (accessToken, host) to the delivery client's underlying names (token, baseUrl). Other options pass through unchanged. fetchExperience's inline-creds branch now routes through createClient, making it the single source of truth for the name mapping. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com> * refactor(client): let empty-nodes payloads flow to the resolver; expose NotFoundError fetchExperience no longer treats an empty-nodes payload as "not found" — the resolver handles empty nodes gracefully and returns a valid PortableRenderPlan. Return type narrows from `PortableRenderPlan | null` to `PortableRenderPlan`. To keep the missing-experience case as a proper 404 (not a 500), NotFoundError is now re-exported from the client + adapter packages. Example call sites wrap fetchExperience in try/catch and route NotFoundError to their framework's 404 idiom (notFound() in Next, error(404) in SvelteKit). Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com> * docs: update READMEs and AGENTS for new fetchExperience signature Covers the three review-driven changes: - 3 positional args (experienceOptions, clientOptions, resolveOptions) - createClient helper + host string in place of preview boolean - Empty-nodes payloads pass through; NotFoundError re-exported for the missing-experience case Adds design-decision entries in AGENTS.md capturing the *why* behind each choice so future contributors don't re-litigate them. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com> --------- Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
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.
AIS-147
Summary
packages/client(@contentful/experiences-client) — a new internal workspace package that extendsContentfulViewDeliveryClientand addsspaceId,environmentId, andpreviewfields;preview: falseroutes to the XDN endpoint,preview: trueroutes to the XPA preview endpointcreateExperienceClientfrom both@contentful/experiences-reactand@contentful/experiences-svelteso customers install only the framework adapter —@contentful/experience-deliveryis no longer a direct customer dependencynextjs,sveltekit) to usecreateExperienceClientfrom their respective adapter package; updates AGENTS.md, root README, and adapter-react README to reflect the new architectureTest plan
npx vitest run packages/client/src— 7 unit tests pass (XDN selection, XPA selection, missing credentials errors, view client exposed)cd packages/client && npx tsup— builds cleanly with ESM output and.d.tsdeclarations@contentful/experience-deliveryno longer appears inexamples/nextjs/package.jsonorexamples/sveltekit/package.jsoncreateExperienceClientis importable from@contentful/experiences-reactand@contentful/experiences-svelteGenerated with Claude Code