WordPress AI Client: building an image generation plugin

WordPress 7.0 just dropped, and with it comes the built-in WordPress AI Client. It is about time. For the last two years, I have watched developers hack together messy cURL requests and juggle half a dozen SDKs just to get a simple prompt into OpenAI or Anthropic. It was a maintenance nightmare that made site migrations a headache.

The new API gives you a standardized abstraction layer. You no longer write code for “OpenAI” or “Gemini,” you write for the capability. If the site owner swaps their provider in the new Settings > Connectors screen, your plugin keeps working without you touching a single line of code. That also means we can build portable AI features that scale.

Understanding the WordPress AI Client architecture

The core idea is “provider agnostic.” Your plugin describes what it needs (an image, a summary, a translation), and WordPress handles the how. This runs through the wp_ai_client_prompt() function, which returns a fluent builder object. The builder lets you chain requirements like aspect ratios, temperature, and model preferences.

I recently wrote about the WordPress 7.0 AI architecture. Today we are building an actual image generation tool for the Media Library.

Building the image generation logic

When building with the WordPress AI Client, I always wrap my logic in a helper function. That makes it easier to run support checks before we ever hit the API. Here is how I structured the prompt builder for this plugin:

<?php
use WordPress\AiClient\Files\Enums\FileTypeEnum;
use WordPress\AiClient\Files\Enums\MediaOrientationEnum;

/**
 * Configures the AI Client for image generation.
 * 
 * @param string $prompt      The user's text description.
 * @param string $orientation Optional orientation (square, landscape, portrait).
 * @return WP_AI_Client_Prompt_Builder
 */
function bbioon_get_image_prompt( string $prompt, string $orientation = '' ) {
    $builder = wp_ai_client_prompt()
        ->with_text( $prompt )
        ->as_output_file_type( FileTypeEnum::inline() );

    if ( ! empty( $orientation ) ) {
        $builder->as_output_media_orientation( MediaOrientationEnum::from( $orientation ) );
    }

    return $builder;
}

Note that I am using FileTypeEnum::inline(). It returns base64-encoded data, so we can show an immediate preview in the admin UI before the user decides to save it to the database. That way we avoid cluttering the Media Library with “hallucinated” garbage the user did not actually want.

Gating features with support checks

One of the biggest “gotchas” with the WordPress AI Client is assuming it is always ready. Just because the code is in core does not mean the user has configured a connector. If you enqueue your scripts without checking support, you will end up with a broken “Generate” button and a frustrated client.

We use the is_supported_for_image_generation() method for this. It is a deterministic check: it does not cost an API credit and it does not make a network request. It just checks whether any active connector supports the requested capability.

<?php
function bbioon_enqueue_ai_assets( $hook_suffix ) {
    if ( 'upload.php' !== $hook_suffix ) {
        return;
    }

    // Don't load if the current provider can't actually do this.
    $prompt_check = bbioon_get_image_prompt( 'test' );
    if ( ! $prompt_check->is_supported_for_image_generation() ) {
        return;
    }

    wp_enqueue_script( 'bbioon-ai-generator' );
}
add_action( 'admin_enqueue_scripts', 'bbioon_enqueue_ai_assets' );

Exposing the AI Client via REST API

To make this interactive, we need a custom REST endpoint. The GenerativeAiResult object returned by the client is serializable, so we can pass it directly to rest_ensure_response(). That keeps our controller methods lean.

<?php
function bbioon_rest_generate_image( WP_REST_Request $request ) {
    $prompt      = $request->get_param( 'prompt' );
    $orientation = $request->get_param( 'orientation' );

    $builder = bbioon_get_image_prompt( $prompt, $orientation );
    $result  = $builder->generate_image_result();

    if ( is_wp_error( $result ) ) {
        return $result; // WordPress handles the 400/500 status automatically.
    }

    return rest_ensure_response( $result );
}

For more on how these endpoints integrate with the centralized Connectors UI, see the official Make Core documentation.

The future of WordPress development

Building with the WordPress AI Client is about more than calling an LLM. It follows the “WordPress way”: lean on the built-in abstraction and your plugins stay stable and portable across providers. If you have held off on AI because the API situation was so fragmented, 7.0 is a good point to start shipping.

If this WordPress AI Client work is eating up your dev hours, I can handle it. I have been wrestling with WordPress since the 4.x days.

Final takeaway

Standardizing your AI setup now saves you technical debt later. Stop hardcoding API keys and use the Connectors API instead. The full source code for this build is on the official WP AI Client GitHub.

author avatar
Ahmad Wael
I'm a WordPress and WooCommerce developer with 15+ years of experience building custom e-commerce solutions and plugins. I specialize in PHP development, following WordPress coding standards to deliver clean, maintainable code. Currently, I'm exploring AI and e-commerce by building multi-agent systems and SaaS products that integrate technologies like Google Gemini API with WordPress platforms, approaching every project with a commitment to performance, security, and exceptional user experience.