### Shared Static Client Setup Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Example of using a single, shared static client across multiple WordPress actions. ```APIDOC ## Shared Static Client Setup ### Description This example demonstrates how to configure a single, shared static `WordPressClient` instance that can be reused across various actions. This approach is beneficial for maintaining a consistent authentication setup throughout your application. ### Usage ```ts // src/actions/index.ts import { createCreatePostAction, createUpdatePostAction, createDeletePostAction, createCreateTermAction, createUpdateTermAction, createDeleteTermAction, createCreateUserAction, createUpdateUserAction, createDeleteUserAction, createGetAbilityAction, createRunAbilityAction, } from 'wp-astrojs-integration'; import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }); export const server = { createPost: createCreatePostAction(wp), updatePost: createUpdatePostAction(wp), deletePost: deletePostAction(wp), createCategory: createCreateTermAction(wp, { resource: 'categories' }), updateTag: createUpdateTermAction(wp, { resource: 'tags' }), deleteGenre: createDeleteTermAction(wp, { resource: 'genres' }), createUser: createCreateUserAction(wp), updateUser: createUpdateUserAction(wp), deleteUser: createDeleteUserAction(wp), getAbility: createGetAbilityAction(wp), runAbility: createRunAbilityAction(wp), deleteAbility: createDeleteAbilityAction(wp), }; ``` ``` -------------------------------- ### Start Local WordPress Instance Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/testing.mdx Use these commands to start and check the status of your local WordPress environment. `wp-env` handles port selection automatically. ```bash npm run wp:start npm run wp:status ``` -------------------------------- ### Shared Static Client Setup Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Example of using a single shared static client across multiple action factories for a consistent authentication setup. ```typescript // src/actions/index.ts import { createCreatePostAction, createUpdatePostAction, createDeletePostAction, createCreateTermAction, createUpdateTermAction, createDeleteTermAction, createCreateUserAction, createUpdateUserAction, createDeleteUserAction, createGetAbilityAction, createRunAbilityAction, } from 'wp-astrojs-integration'; import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }); export const server = { createPost: createCreatePostAction(wp), updatePost: createUpdatePostAction(wp), deletePost: createDeletePostAction(wp), createCategory: createCreateTermAction(wp, { resource: 'categories' }), updateTag: createUpdateTermAction(wp, { resource: 'tags' }), deleteGenre: createDeleteTermAction(wp, { resource: 'genres' }), createUser: createCreateUserAction(wp), updateUser: createUpdateUserAction(wp), deleteUser: createDeleteUserAction(wp), getAbility: createGetAbilityAction(wp), runAbility: createRunAbilityAction(wp), deleteAbility: createDeleteAbilityAction(wp), }; ``` -------------------------------- ### Setup Ability Actions Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/abilities.mdx Import and create ability action handlers using the provided factory functions and an authentication bridge. This setup is typically done in Astro's server export. ```typescript import { createDeleteAbilityAction, createGetAbilityAction, createRunAbilityAction, } from 'wp-astrojs-integration'; import { wordPressAuthBridge } from '../lib/auth/bridge'; export const server = { getAbility: createGetAbilityAction(wordPressAuthBridge.getClient), runAbility: createRunAbilityAction(wordPressAuthBridge.getClient), deleteAbility: createDeleteAbilityAction(wordPressAuthBridge.getClient), }; ``` -------------------------------- ### Install Coding Agent Skills Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md If using a coding agent, install the skills for both the fluent client and the Astro integration. ```bash npx skills add https://github.com/JUVOJustin/fluent-wp-client npx skills add https://github.com/JUVOJustin/astrojs-wp-integration ``` -------------------------------- ### Client-first Authentication Setup Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Recommended approach using a shared client resolver that depends on the current Astro request. ```APIDOC ## Client-first Authentication Setup ### Description This setup uses a shared client resolver, `wordPressAuthBridge.getClient`, which is ideal when authentication depends on the current Astro request. It allows for a single, request-aware client to be used across multiple actions. ### Usage ```ts import { createCreatePostAction, createCreateTermAction, createCreateUserAction, createDeletePostAction, createGetAbilityAction, createUpdatePostAction, } from 'wp-astrojs-integration'; import { wordPressAuthBridge } from '../lib/auth/bridge'; export const server = { createPost: createCreatePostAction(wordPressAuthBridge.getClient), updatePost: createUpdatePostAction(wordPressAuthBridge.getClient), deletePost: createDeletePostAction(wordPressAuthBridge.getClient), createCategory: createCreateTermAction(wordPressAuthBridge.getClient, { resource: 'categories' }), createUser: createCreateUserAction(wordPressAuthBridge.getClient), getAbility: createGetAbilityAction(wordPressAuthBridge.getClient), }; ``` ``` -------------------------------- ### Static Client (App Password) Setup Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Configuration for a static WordPress client using an application password for authentication. ```APIDOC ## Static Client (App Password) Setup ### Description This method configures a static `WordPressClient` using environment variables for the base URL and application password authentication. It's suitable for server-side operations where a consistent authentication method is required. ### Usage ```ts import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }); export const server = { createPost: createCreatePostAction(wp), updatePost: createUpdatePostAction(wp), }; ``` ``` -------------------------------- ### Live Collection Setup (SSR) Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Configure a live collection for SSR by defining a collection with a WordPress loader and schema. Ensure the WordPressClient is initialized with the base URL. ```typescript // src/live.config.ts import { defineLiveCollection } from 'astro:content'; import { WordPressClient } from 'fluent-wp-client'; import { postSchema } from 'fluent-wp-client/zod'; import { wordPressPostLoader } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.PUBLIC_WORDPRESS_BASE_URL, }); const posts = defineLiveCollection({ loader: wordPressPostLoader(wp), schema: postSchema, }); export const collections = { posts }; ``` -------------------------------- ### Static Client (JWT) Setup Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Setting up a static WordPress client for authentication using a JSON Web Token (JWT). ```APIDOC ## Static Client (JWT) Setup ### Description This configuration initializes a static `WordPressClient` using a JWT for authentication. Ensure the `WP_URL` and `WP_JWT_TOKEN` environment variables are correctly set. ### Usage ```ts import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { token: import.meta.env.WP_JWT_TOKEN, }, }); ``` ``` -------------------------------- ### Running WordPress Integration Tests Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/AGENTS.md Commands to start, stop, clean, and run various test suites for the WordPress integration project. Use `npm run wp:start` before running tests and `npm run wp:stop` afterwards. ```bash npm run wp:start npm test # All test projects (integration + static-build) npm run test:integration # Integration project only (loaders, actions, auth) npm run test:build # Static build project only npm run wp:stop npm run wp:clean ``` -------------------------------- ### Install WordPress Astro.js Integration Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Install the necessary packages for integrating WordPress with Astro.js. Ensure you are using compatible versions of fluent-wp-client and Astro. ```bash npm install wp-astrojs-integration fluent-wp-client ``` -------------------------------- ### Static Collection Setup (SSG) Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Set up a static collection for SSG by defining a collection with a static WordPress loader and schema. This is suitable for sites generated at build time. ```typescript // src/content.config.ts import { defineCollection } from 'astro:content'; import { WordPressClient } from 'fluent-wp-client'; import { postSchema } from 'fluent-wp-client/zod'; import { wordPressPostStaticLoader } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.PUBLIC_WORDPRESS_BASE_URL, }); const posts = defineCollection({ loader: wordPressPostStaticLoader(wp), schema: postSchema, }); export const collections = { posts }; ``` -------------------------------- ### Setup User Actions Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/users.mdx Register the user action factories in your Astro project's `src/actions/index.ts`. Ensure you have initialized the WordPress client with your credentials and base URL. ```typescript import { createCreateUserAction, createUpdateUserAction, createDeleteUserAction, } from 'wp-astrojs-integration'; import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }); export const server = { createUser: createCreateUserAction(wp), updateUser: createUpdateUserAction(wp), deleteUser: createDeleteUserAction(wp), }; ``` -------------------------------- ### Run WordPress Development Server Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Starts the local WordPress development server. Use `npm run wp:status` to find the active local URL and ports if `8888` is unavailable. ```bash npm run wp:start ``` -------------------------------- ### Setup Ability Action with Typed Response Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/abilities.mdx Configure a `runAbility` action to validate the response from WordPress using a Zod schema. This ensures the returned data conforms to the expected structure. ```typescript import { WordPressClient } from 'fluent-wp-client'; import { z } from 'astro/zod'; const optionResultSchema = z.object({ previous: z.string(), current: z.string(), }); export const server = { runAbility: createRunAbilityAction(new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }), { responseSchema: optionResultSchema, }), }; ``` -------------------------------- ### Live Collection with Custom Fetch Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Enhance live collection setup by passing a custom fetch function to WordPressClient for request instrumentation, caching, or proxying. ```typescript const wp = new WordPressClient({ baseUrl: import.meta.env.PUBLIC_WORDPRESS_BASE_URL, fetch: async (input, init) => { return fetch(input, init); }, }); const posts = defineLiveCollection({ loader: wordPressPostLoader(wp), schema: postSchema, }); ``` -------------------------------- ### Configure Static Content Collections Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Define Astro content collections using static loaders from fluent-wp-client. This setup pre-builds content for static sites. ```typescript // src/content.config.ts import { defineCollection } from 'astro:content'; import { WordPressClient } from 'fluent-wp-client'; import { categorySchema, pageSchema, postSchema } from 'fluent-wp-client/zod'; import { wordPressPostStaticLoader, wordPressPageStaticLoader, wordPressCategoryStaticLoader, wordPressTermStaticLoader, wordPressContentStaticLoader, } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.PUBLIC_WORDPRESS_BASE_URL, }); const posts = defineCollection({ loader: wordPressPostStaticLoader(wp), schema: postSchema, }); const pages = defineCollection({ loader: wordPressPageStaticLoader(wp), schema: pageSchema, }); const categories = defineCollection({ loader: wordPressCategoryStaticLoader(wp), schema: categorySchema, }); // Custom taxonomy const genres = defineCollection({ loader: wordPressTermStaticLoader(wp, { resource: 'genres' }), schema: categorySchema, }); // Custom post type (static) const products = defineCollection({ loader: wordPressContentStaticLoader(wp, { resource: 'products' }), schema: productSchema, }); export const collections = { posts, pages, categories, genres, products }; ``` -------------------------------- ### Get WordPress Client with Static Auth Fallback Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/auth-action-bridge.mdx Opt into static fallback when you require a single service-capable client. This method attempts to get the client, falling back to static auth if available. ```typescript const wp = await wordPressAuthBridge.getClient(Astro, { allowStaticAuthFallback: true, }); if (!wp) { return Astro.redirect('/login'); } ``` -------------------------------- ### Discover schemas at runtime Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Use runtime discovery when the WordPress schema is not known ahead of time, such as when dealing with custom post types or dynamic fields. This example shows how to explore the catalog, generate Zod schemas for content creation, and validate input. ```typescript import { WordPressClient } from 'fluent-wp-client'; import { zodFromJsonSchema, zodSchemasFromDescription } from 'fluent-wp-client/zod'; const wp = new WordPressClient({ baseUrl: 'https://example.com', auth: { username: 'admin', password: 'app-password' }, }); const catalog = await wp.explore(); const bookSchemas = zodSchemasFromDescription(catalog.content.books); const validatedBookInput = bookSchemas.create!.parse({ title: { raw: 'My new book' }, status: 'draft', }); await wp.content('books').create(validatedBookInput); const description = await wp.content('posts').describe(); const postCreateSchema = zodFromJsonSchema(description.schemas.create!); void postCreateSchema; ``` -------------------------------- ### Set Live Collection Cache Hint in Astro Page Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/caching.mdx Pass the live-loader cache hint directly into `Astro.cache.set()` within an Astro page. This example demonstrates fetching a book entry and setting its cache properties. ```astro ---import { getLiveEntry } from 'astro:content'; const { entry, error, cacheHint } = await getLiveEntry('books', { slug: Astro.params.slug }); if (error || !entry) { return Astro.redirect('/404'); } if (cacheHint) { Astro.cache.set(cacheHint); } Astro.cache.set({ maxAge: 300 }); ---

{entry.data.title.rendered}

``` -------------------------------- ### Generate Zod Schemas and Types Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Use the `fluent-wp-client` CLI to generate Zod schemas and TypeScript declarations from your WordPress site. This is the first step towards a typesafe setup. ```bash npx fluent-wp-client schemas \ --url https://example.com \ --zod-out src/generated/wp-schemas.ts \ --types-out src/generated/wp-types.d.ts ``` -------------------------------- ### Create Typed WordPress Actions in Astro Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Configure Astro server actions with generated schemas for input validation and response validation. This example demonstrates creating typed actions for post creation and updates. ```typescript import { createCreatePostAction, createUpdatePostAction, } from 'wp-astrojs-integration'; import { wp } from '../lib/wp'; import { postsCreateSchema, postsUpdateSchema, postsItemSchema, } from '../generated/wp-schemas'; export const server = { createPost: createCreatePostAction(wp, { schema: postsCreateSchema, responseSchema: postsItemSchema, }), updatePost: createUpdatePostAction(wp, { schema: postsUpdateSchema, responseSchema: postsItemSchema, }), }; ``` -------------------------------- ### Create a Shared WordPress Client Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Set up a shared WordPress client instance using `fluent-wp-client`. Ensure the `PUBLIC_WORDPRESS_BASE_URL` environment variable is configured. ```typescript import { WordPressClient } from 'fluent-wp-client'; export const wp = new WordPressClient({ baseUrl: import.meta.env.PUBLIC_WORDPRESS_BASE_URL, }); ``` -------------------------------- ### Create Post with All Available Fields Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/posts.mdx Demonstrates calling `actions.createPost` with all possible fields, including title, content, excerpt, status, slug, date, author, featured media, categories, tags, sticky, format, comment status, and ping status. ```typescript const { data } = await Astro.callAction(actions.createPost, { title: 'Full Example', content: '

Post body as raw HTML.

', excerpt: 'Short summary shown in listings.', status: 'publish', // 'publish' | 'draft' | 'pending' | 'private' | 'future' slug: 'full-example', date: '2026-03-01T10:00:00', // ISO 8601 — used for scheduled posts author: 1, // user ID featured_media: 42, // attachment ID categories: [3, 7], tags: [12], sticky: false, format: 'standard', // 'standard' | 'aside' | 'gallery' | 'video' | … comment_status: 'open', ping_status: 'closed', }); ``` -------------------------------- ### Run Tests in Watch Mode Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Starts the test runner in watch mode, automatically re-running tests on file changes. ```bash npm run test:watch ``` -------------------------------- ### Build Project Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Builds the Astro project for production deployment. ```bash npm run build ``` -------------------------------- ### Create WordPress Client from Resolved Config Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/auth-action-bridge.mdx Use this when you need to manually create the WordPress client. It first resolves the client configuration and then instantiates the client. ```typescript import { WordPressClient } from 'fluent-wp-client'; const clientConfig = await wordPressAuthBridge.getClientConfig(Astro); if (!clientConfig) { return Astro.redirect('/login'); } const wp = new WordPressClient(clientConfig); ``` -------------------------------- ### Set WordPress Catalog URL Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Define the `WP_CATALOG_URL` environment variable in your `.env` file to specify the WordPress API endpoint. This variable is used during Astro setup. ```bash WP_CATALOG_URL=https://cms.example.com ``` -------------------------------- ### Import WordPress Schema Functions Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Import functions to get Zod schemas for WordPress resources, content, and terms. Use these to validate data fetched from WordPress. ```typescript import { getWordPressContentSchemas, getWordPressResourceSchemas, getWordPressTermSchemas, withWordPressActionSchemas, } from 'virtual:wp-astrojs/schemas'; ``` -------------------------------- ### Create Catalog-Backed WordPress Client Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Import and create a WordPress client using the virtual module, seeded with the stored catalog. This client can be used with loaders and actions. ```typescript import { createWordPressClient } from 'virtual:wp-astrojs/catalog'; export const wp = createWordPressClient({ baseUrl: import.meta.env.WP_CATALOG_URL, }); ``` -------------------------------- ### Run All Test Projects Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Executes all test suites for the project. ```bash npm test ``` -------------------------------- ### Login Payload Schema Definition Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/auth-action-bridge.mdx Define the login payload schema using Zod for input validation. This example shows how to import and type the login input schema. ```typescript import { z } from 'astro/zod'; import { wordPressLoginInputSchema } from 'wp-astrojs-integration'; type LoginPayload = z.input; ``` -------------------------------- ### Fetch All Pages Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Use `getLiveCollection` to retrieve all pages. Maps over the entries to create navigation links. ```astro --- ``` ```astro const { entries: pages } = await getLiveCollection('pages'); ``` ```astro --- ``` ```astro ``` -------------------------------- ### Basic Auth with App Passwords Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Configure a WordPressClient for live collection loading using basic authentication with app passwords. Ensure WP_URL, WP_USERNAME, and WP_APP_PASSWORD environment variables are set. ```typescript // src/live.config.ts import { defineLiveCollection } from 'astro:content'; import { WordPressClient } from 'fluent-wp-client'; import { postSchema } from 'fluent-wp-client/zod'; import { wordPressPostLoader, } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD, }, }); const posts = defineLiveCollection({ loader: wordPressPostLoader(wp), schema: postSchema, }); ``` -------------------------------- ### Override Collection Behavior with Loader Options Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Customize the behavior of a WordPress collection by providing `loaderOptions`, such as `mapEntry` to transform individual entries. This example trims whitespace from book titles. ```typescript export const collections = { mappedBooks: defineWordPressCollection('books', { client: wp, loaderOptions: { mapEntry: (book) => ({ ...book, title: { ...book.title, rendered: book.title.rendered.trim() }, }), }, }), }; ``` -------------------------------- ### Create a Custom Taxonomy Term Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/terms.mdx Create a term for a custom taxonomy like 'genres' by configuring the `createCreateTermAction` with the correct resource. This example demonstrates creating a 'Science Fiction' genre. ```typescript import { WordPressClient } from 'fluent-wp-client'; import { createCreateTermAction } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD }, }); const createGenre = createCreateTermAction(wp, { resource: 'genres' }); const created = await Astro.callAction(createGenre, { name: 'Science Fiction', slug: 'science-fiction', }); ``` -------------------------------- ### Fetch Static Content in Astro Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Use `getCollection` to fetch all entries for a statically loaded collection at build time. This is suitable for content that changes infrequently. ```astro --- // src/pages/blog/index.astro import { getCollection } from 'astro:content'; // Fetch all posts (loaded at build time) const posts = await getCollection('posts'); --- ``` -------------------------------- ### createPost with Meta Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/posts.mdx Creates a new post and includes associated meta fields. Meta fields must be registered in WordPress with `show_in_rest: true`. ```APIDOC ## createPost with Meta ### Description Creates a new post and allows for the inclusion of registered meta fields. Ensure meta fields are registered in WordPress with `show_in_rest: true`. ### Method POST (assumed based on action pattern) ### Endpoint `/actions/createPost` (assumed based on action pattern) ### Parameters #### Request Body - **title** (string) - Required - The title of the post. - **content** (string) - Required - The content of the post. - **status** (string) - Required - The status of the post (e.g., 'publish'). - **meta** (object) - Optional - An object containing meta fields. Keys must be registered with `show_in_rest: true` in WordPress. - **reading_time** (integer) - Example meta field. - **source_url** (string) - Example meta field. ### Request Example ```json { "title": "Post with meta", "content": "

Body.

", "status": "publish", "meta": { "reading_time": 5, "source_url": "https://example.com/original" } } ``` ### Response #### Success Response (200) - **data** (object) - Contains the result of the create operation. ``` -------------------------------- ### Static Client with Request-Aware Auth Headers Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Configuring a static client with dynamic authentication headers based on request details. ```APIDOC ## Static Client with Request-Aware Auth Headers ### Description This setup uses a static `WordPressClient` but employs a custom `authHeaders` function to dynamically generate authentication headers for each request. This is useful for integrations requiring custom signing or token generation based on request parameters. ### Usage ```ts import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, authHeaders: ({ method, url, body }) => { // Replace with your signer implementation const signature = createSignedAuthHeader({ method, url: url.toString(), body }); return { Authorization: signature, }; }, }); // Note: `createSignedAuthHeader` is a user-defined function and not part of the package. ``` ``` -------------------------------- ### Session-Based Auth for Authenticated Routes Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Access user-specific content and drafts within an Astro page using session-based authentication. This example assumes Astro.locals.wp is already configured with an authenticated WordPressClient. ```astro --- Astro.cache.set(false); const wp = Astro.locals.wp; const user = await wp.users().me(); const drafts = await wp.content('posts').list({ status: 'draft' }); ---

{user.name}

{drafts.length} drafts

``` -------------------------------- ### Define WordPress Collection with Catalog Loader Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Configure Astro content collections using the WordPress integration's loader and schema, which are derived from the catalog. This example shows defining a 'posts' collection. ```typescript import { defineCollection } from 'astro:content'; import { postSchema } from 'fluent-wp-client/zod'; import { wordPressPostStaticLoader } from 'wp-astrojs-integration'; import { wp } from './lib/wp'; export const collections = { posts: defineCollection({ loader: wordPressPostStaticLoader(wp), schema: postSchema, }), }; ``` -------------------------------- ### Create Published Post with Astro Action Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/posts.mdx Create a live published post by calling the `actions.createPost` action with `status: 'publish'`. You can optionally include excerpt, categories, and tags. ```typescript const { data } = await Astro.callAction(actions.createPost, { title: 'Hello World', content: '

My first post.

', excerpt: 'A short summary.', status: 'publish', categories: [3], // category IDs tags: [12, 15], // tag IDs }); ``` -------------------------------- ### Use Generated Schemas in Astro Actions Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Create Astro actions with type safety by using generated Zod schemas for request and response validation. This example demonstrates creating posts and books. ```typescript import { createCreatePostAction } from 'wp-astrojs-integration'; import { wp } from '../lib/wp'; import { postsCreateSchema, postsItemSchema, booksCreateSchema, booksItemSchema, } from '../generated/wp-schemas'; export const server = { createPost: createCreatePostAction(wp, { schema: postsCreateSchema, responseSchema: postsItemSchema, }), createBook: createCreatePostAction(wp, { resource: 'books', schema: booksCreateSchema, responseSchema: booksItemSchema, }), }; ``` -------------------------------- ### Static Client with JWT Token Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Set up a static WordPress client using a JWT token for authentication. Requires the WP_URL and WP_JWT_TOKEN environment variables. ```typescript import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { token: import.meta.env.WP_JWT_TOKEN, }, }); ``` -------------------------------- ### Use Generated Schemas in Astro Content Collections Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Define Astro content collections using generated Zod schemas for type safety. This example shows how to configure collections for posts and books. ```typescript import { defineCollection, defineLiveCollection } from 'astro:content'; import { wordPressPostStaticLoader, wordPressContentLoader, } from 'wp-astrojs-integration'; import { wp } from './lib/wp'; import { postsItemSchema, booksItemSchema, } from './generated/wp-schemas'; export const collections = { posts: defineCollection({ loader: wordPressPostStaticLoader(wp), schema: postsItemSchema, }), books: defineLiveCollection({ loader: wordPressContentLoader(wp, { resource: 'books' }), schema: booksItemSchema, }), }; ``` -------------------------------- ### Call Cache Invalidation Action Examples Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/caching.mdx Demonstrates how to call the `wpCacheInvalidate` action with different entity types. Provide the `id`, `entity`, and specific type information like `post_type` or `taxonomy` as needed. ```typescript await actions.wpCacheInvalidate({ id: 42, entity: 'post', post_type: 'book', }); await actions.wpCacheInvalidate({ id: 8, entity: 'term', taxonomy: 'genre', }); await actions.wpCacheInvalidate({ id: 3, entity: 'user', }); ``` -------------------------------- ### Create a User Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/users.mdx Call the `createUser` action with the necessary user details. Required fields include `username`, `email`, and `password`. ```typescript const { data, error } = await Astro.callAction(actions.createUser, { username: 'editor-jane', email: 'jane@example.com', password: 'strong-password', name: 'Jane Editor', roles: ['editor'], }); ``` -------------------------------- ### Static Client with Request-Aware Auth Headers Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx Configure a static WordPress client with custom authentication headers generated dynamically. The `createSignedAuthHeader` function must be implemented by the user. ```typescript import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, authHeaders: ({ method, url, body }) => { // Replace with your signer implementation const signature = createSignedAuthHeader({ method, url: url.toString(), body }); return { Authorization: signature, }; }, }); ``` -------------------------------- ### Execute Term Helpers Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/terms.mdx Utilize raw execute helpers for direct term manipulation, useful in testing or custom integrations. This example demonstrates creating, updating, and deleting a tag using these helpers. ```typescript import { executeCreateTerm, executeUpdateTerm, executeDeleteTerm, } from 'wp-astrojs-integration'; import { WordPressClient } from 'fluent-wp-client'; const wp = new WordPressClient({ baseUrl: 'https://example.com', auth: { username: 'admin', password: 'app-password' }, }); const created = await executeCreateTerm(wp, { name: 'Release Notes' }, { resource: 'tags' }); await executeUpdateTerm(wp, { id: created.id, slug: 'release-notes' }, { resource: 'tags' }); await executeDeleteTerm(wp, { id: created.id, force: true }, { resource: 'tags' }); ``` -------------------------------- ### Verify Published npm Package Contents Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/AGENTS.md Use this command to preview the contents of the npm package before publishing. This helps ensure the correct files are included in the distribution. ```bash npm pack --dry-run ``` -------------------------------- ### Run Integration and Build Tests Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/testing.mdx Execute integration tests, static build validation, or run all tests. The `npm test` command covers both integration and build projects. ```bash npm run test:integration npm run test:build # or run both projects npm test ``` -------------------------------- ### Define Typed Collections with WordPress Loaders Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/typesafe-integration.mdx Use generated `*ItemSchema` for collection entry validation. This example shows how to define static and live collections for posts, pages, and custom resources like books, integrating WordPress data loaders. ```typescript import { defineCollection, defineLiveCollection } from 'astro:content'; import { wordPressPostStaticLoader, wordPressPageLoader, wordPressContentLoader, } from 'wp-astrojs-integration'; import { wp } from './lib/wp'; import { postsItemSchema, pagesItemSchema, booksItemSchema, } from './generated/wp-schemas'; export const collections = { posts: defineCollection({ loader: wordPressPostStaticLoader(wp), schema: postsItemSchema, }), pages: defineLiveCollection({ loader: wordPressPageLoader(wp), schema: pagesItemSchema, }), books: defineLiveCollection({ loader: wordPressContentLoader(wp, { resource: 'books' }), schema: booksItemSchema, }), }; ``` -------------------------------- ### Fetch Single Post by Slug Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Use `getLiveEntry` with a slug parameter to fetch a single post for a detail page. Includes a redirect to a 404 page if the post is not found. ```astro --- // src/pages/blog/[slug].astro import { getLiveEntry } from 'astro:content'; import WPContent from 'wp-astrojs-integration/components/WPContent.astro'; const { slug } = Astro.params; const { entry: post } = await getLiveEntry('posts', { slug }); if (!post) { return Astro.redirect('/404'); } ---

``` -------------------------------- ### Configure Static Loaders with Build-Time Filters Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Apply filters to static loaders during collection configuration to scope which entries are fetched at build time. Pagination is handled automatically by `listAll()`. ```typescript // src/content.config.ts // Only fetch posts in the "tutorials" category (ID 5) const tutorials = defineCollection({ loader: wordPressPostStaticLoader(wp, { filter: { categories: [5] }, }), schema: postSchema, }); // Only fetch a specific subset of pages by ID const keyPages = defineCollection({ loader: wordPressPageStaticLoader(wp, { filter: { include: [1, 2, 3] }, }), schema: pageSchema, }); // Only fetch non-empty categories, ordered by post count const activeCategories = defineCollection({ loader: wordPressCategoryStaticLoader(wp, { filter: { hideEmpty: true, orderby: 'count', order: 'desc' }, }), schema: categorySchema, }); // CPT with search scope const featuredBooks = defineCollection({ loader: wordPressContentStaticLoader(wp, { resource: 'books', filter: { search: 'award' }, }), schema: bookSchema, }); ``` -------------------------------- ### Check Code Formatting with Biome Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/AGENTS.md Run this command after making code changes to ensure adherence to formatting standards. Biome will report any issues. ```bash npm run format:check ``` -------------------------------- ### Typed Term Creation with Schema Overrides Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/terms.mdx Define custom input validation using `schema` and response parsing with `responseSchema` when creating terms. This example extends the default term schema to include a `custom_label` and specifies a response schema for the 'genre' taxonomy. ```typescript import { z } from 'astro/zod'; import { WordPressClient } from 'fluent-wp-client'; import { createCreateTermAction, createTermInputSchema } from 'wp-astrojs-integration'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, auth: { username: import.meta.env.WP_USERNAME, password: import.meta.env.WP_APP_PASSWORD }, }); const createGenre = createCreateTermAction(wp, { resource: 'genres', schema: createTermInputSchema.extend({ custom_label: z.string().optional(), }), responseSchema: z.object({ id: z.number().int().positive(), taxonomy: z.literal('genre'), name: z.string(), }), }); ``` -------------------------------- ### WPContent Component for Gutenberg Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Utilizes the WPContent component to render WordPress content, supporting Gutenberg block styling and image handling. Requires importing the WPContent component and setting the PUBLIC_WORDPRESS_BASE_URL environment variable. ```astro --- import WPContent from 'wp-astrojs-integration/components/WPContent.astro'; const { entry: post } = await getLiveEntry('posts', { slug }); ---

``` -------------------------------- ### Fetch Public Content with Direct Client and Route Caching Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Use this snippet to fetch public WordPress content directly using `getContentTool` and apply Astro's route caching. Ensure `WP_URL` is set in your environment variables. ```typescript import type { APIRoute } from 'astro'; import { WordPressClient } from 'fluent-wp-client'; import { getContentTool } from 'fluent-wp-client/ai-sdk'; const wp = new WordPressClient({ baseUrl: import.meta.env.WP_URL, }); export const GET: APIRoute = async (context) => { const tool = getContentTool(wp, { contentType: 'posts', }); if (!tool.execute) throw new Error('Content tool is not executable.'); const result = await tool.execute({ slug: 'hello-world' }, { toolCallId: 'read-post', messages: [], }); context.cache.set({ maxAge: 300, swr: 60 }); return Response.json(result); }; ``` -------------------------------- ### Display Blog Posts with Categories Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Fetches posts and categories from content collections to display a blog index with category navigation. Ensure 'posts' and 'categories' collections are defined. ```astro ---// src/pages/blog/index.astro import { getLiveCollection } from 'astro:content'; const [posts, categories] = await Promise.all([ getLiveCollection('posts', { perPage: 10 }), getLiveCollection('categories'), ]); const postEntries = posts.entries ?? []; const categoryEntries = categories.entries ?? []; ---
{postEntries.map((post) => ( ))}
``` -------------------------------- ### Create WordPress Post with Meta Fields Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/posts.mdx Use the `createPost` action to create a new post and include custom meta fields. Meta fields must be registered in WordPress with `show_in_rest: true`. ```typescript // Meta fields must be registered in WordPress with show_in_rest: true: // // register_post_meta('post', 'reading_time', // 'show_in_rest' => true, // 'single' => true, // 'type' => 'integer', // ]); const { data } = await Astro.callAction(actions.createPost, { title: 'Post with meta', content: '

Body.

', status: 'publish', meta: { reading_time: 5, source_url: 'https://example.com/original', }, }); ``` -------------------------------- ### Display Product Catalog Grouped by Category Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Fetches products and custom product categories from content collections to create a shop layout. Products are filtered and displayed under their respective categories. Assumes 'products' and 'product-categories' collections exist and products have a 'product_categories' field. ```astro ---// src/pages/shop/index.astro import { getLiveCollection } from 'astro:content'; const { entries: products } = await getLiveCollection('products', { orderby: 'title', order: 'asc' }); // Group by category if using custom taxonomies const { entries: categories } = await getLiveCollection('product-categories'); ---
{categories.map((cat) => { const catProducts = products.filter(p => p.data.product_categories?.includes(cat.data.id) ); return (

{cat.data.name}

); })}
``` -------------------------------- ### Fetch Public Content with Live Loader and Route Caching Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md This snippet demonstrates fetching public WordPress content through an Astro live collection, allowing the endpoint to benefit from live-loader cache hints. It requires providing either an `id` or `slug` for lookup and handles potential errors and cache hints from `getLiveEntry`. ```typescript import { getLiveEntry } from 'astro:content'; import { getContentTool } from 'fluent-wp-client/ai-sdk'; export const GET: APIRoute = async (context) => { const tool = getContentTool(wp, { contentType: 'posts', fetch: async (input) => { if (!input.id && !input.slug) { throw new Error('Provide either id or slug to read a post.'); } const lookup = input.id ? { id: input.id } : { slug: input.slug }; const { entry, error, cacheHint } = await getLiveEntry('posts', lookup); if (error) throw error; if (cacheHint) context.cache.set(cacheHint); return { item: entry?.data }; }, }); if (!tool.execute) throw new Error('Content tool is not executable.'); const result = await tool.execute({ slug: 'hello-world' }, { toolCallId: 'read-post', messages: [], }); context.cache.set({ maxAge: 300, swr: 60 }); return Response.json(result); }; ``` -------------------------------- ### Run Integration Tests Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/README.md Runs integration tests, focusing on actions, loaders, and authentication. ```bash npm run test:integration ``` -------------------------------- ### Apply Catalog Schemas to Create/Update Post Actions Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Integrate catalog-derived schemas for 'books' resource into create and update post actions. This uses 'virtual:wp-astrojs/schemas' to apply default schemas. ```typescript import { createCreatePostAction, createUpdatePostAction } from 'wp-astrojs-integration'; import { withWordPressActionSchemas } from 'virtual:wp-astrojs/schemas'; import { wp } from '../lib/wp'; export const server = { createBook: createCreatePostAction( wp, withWordPressActionSchemas('books', { resource: 'books' }), ), updateBook: createUpdatePostAction( wp, withWordPressActionSchemas('books', { resource: 'books' }), ), }; ``` -------------------------------- ### Available Loaders Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Lists the available loaders for different WordPress entities, including live, static, and schema types. ```APIDOC ## Available Loaders | Entity | Live loader | Static loader | Schema | |---|---|---|---| | Posts | `wordPressPostLoader` | `wordPressPostStaticLoader` | `postSchema` | | Pages | `wordPressPageLoader` | `wordPressPageStaticLoader` | `pageSchema` | | Media | `wordPressMediaLoader` | `wordPressMediaStaticLoader` | `mediaSchema` | | Categories | `wordPressCategoryLoader` | `wordPressCategoryStaticLoader` | `categorySchema` | | Tags | `wordPressTagLoader` | `wordPressTagStaticLoader` | `categorySchema` | | Custom taxonomies | `wordPressTermLoader` | `wordPressTermStaticLoader` | `categorySchema` | | Users | `wordPressUserLoader` | `wordPressUserStaticLoader` | `authorSchema` | | Custom post types | `wordPressContentLoader` | `wordPressContentStaticLoader` | `contentWordPressSchema` (extend as needed) | ``` -------------------------------- ### Executing Raw Actions with execute* Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/actions/index.mdx The `execute*` pattern allows direct invocation of action helpers, bypassing the Astro runtime. This is useful for testing or targeting different REST resources like custom post types. ```typescript import { WordPressClient } from 'fluent-wp-client'; import { executeCreatePost } from 'wp-astrojs-integration/actions'; const wp = new WordPressClient({ baseUrl: 'https://example.com', auth: { username, password }, }); const product = await executeCreatePost( wp, { title: 'My Product', status: 'publish' }, { resource: 'products' }, ); ``` -------------------------------- ### Configure WordPress Catalog Discovery Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/catalog.mdx Enable and configure catalog discovery by passing an options object to the wordpress function. Customize refresh behavior, required status, environment variable prefix, included content types, and cache file location. ```typescript wordpress({ catalog: { enabled: true, refresh: 'build', required: true, envPrefix: 'WP_CATALOG_', include: ['content', 'terms', 'resources', 'abilities'], cacheFile: 'wp-astrojs/catalog.json', }, }); ``` -------------------------------- ### Basic HTML Rendering Source: https://github.com/juvojustin/astrojs-wp-integration/blob/main/docs/reading-content.mdx Renders the title, content, and excerpt of a WordPress post directly as HTML. Ensure the 'entry' object is correctly fetched. ```astro --- const { entry: post } = await getLiveEntry('posts', { slug }); ---

```