technical
WordPress 6.7 AI Abilities API — Analisis de superficie de ataque por Prompt Injection WordPress 6.7 AI Abilities API — A Prompt Injection Attack Surface Analysis
TL;DR
WordPress 6.7 incluye un AI Client con una “Abilities API” que permite a modelos de IA ejecutar funciones PHP en el servidor. Realizamos una auditoria completa del codigo fuente: 146 archivos del SDK, la capa adaptadora, y las 3 abilities core. La implementacion es razonablemente segura — pero el diseno crea una superficie de ataque masiva de prompt injection → ejecucion de codigo que escalara con el ecosistema de plugins.
Que auditamos
WordPress 6.7.2 incluye una nueva capa de integracion con IA:
wp-includes/php-ai-client/— 146 archivos PHP. SDK compatible con PSR para proveedores de IA.wp-includes/ai-client/— 6 archivos adaptadores. HTTP client, cache, eventos y Abilities.wp-includes/abilities-api/— El sistema de registro.WP_Abilityenvuelve un callback PHP con validacion y permisos.- 3 abilities core:
core/get-site-info,core/get-user-info,core/get-environment-info.
Todo se carga en cada request via wp-settings.php. No esta detras de un feature flag. Es core.
Como la IA ejecuta codigo en el servidor
Plugin activa wp_ai_client_prompt()
↓
PromptBuilder arma prompt + herramientas
↓
Request HTTP al proveedor de IA
↓
Modelo responde con FunctionCall:
{ name: "wpab__core__get_user_info", args: {} }
↓
Resolver verifica whitelist + permisos
↓
$ability->execute() → codigo PHP real
La IA decide QUE llamar y CON QUE ARGUMENTOS.
Lo que WordPress hizo bien
- Permission callbacks obligatorios — sin callback, la ability falla cerrado.
- Validacion por JSON Schema — el mismo validador de la REST API.
- HTTP seguro —
wp_safe_remote_requestpreviene SSRF. - Whitelist por constructor — el modelo no puede llamar abilities fuera de la lista.
- Verificacion de clases —
class_exists()antes de instanciacion dinamica.
Lo que podria salir mal
Hallazgo 1: get-user-info solo requiere is_user_logged_in()
Cualquier suscriptor puede filtrar user_login, roles y user_id via IA. Compara con get-site-info y get-environment-info que requieren manage_options.
Hallazgo 2: Prompt Injection → Tool Use
El ataque:
- Atacante crea contenido con prompt injection (comentario, resena, formulario)
- Usuario legitimo activa procesamiento de IA sobre ese contenido
- El prompt inyectado manipula al modelo para llamar abilities
- Las abilities se ejecutan con los permisos del usuario actual
Ejemplo con WooCommerce: un gerente resume una resena que contiene prompt injection oculto → la IA crea un cupon de 100% descuento. La validacion de schema pasa. Los permisos pasan. El ataque funciona.
Hallazgo 3: Sin rate limiting
execute_abilities() procesa TODAS las function calls en un mensaje. Sin limite. Un modelo manipulado podria invocar docenas de funciones.
Hallazgo 4: Random debil en fallback criptografico
Si AUTH_SALT no esta definido: $salt = (string) rand(); — predecible.
La bomba de tiempo
Los 60,000+ plugins de WordPress van a registrar abilities. Cada ability con permisos debiles = nueva superficie de ataque. Esto es la nueva SQL injection.
Recomendaciones
Plugin devs: traten args de IA como input hostil. Capability minima. Log todo.
Operadores: define('WP_AI_SUPPORT', false); si no lo necesitan.
WordPress core: agregar max_ability_calls_per_response, documentar el riesgo.
Si tu aplicacion usa WordPress y quieres una evaluacion profesional, consulta nuestros planes de pentesting.
Metodologia
Analisis automatizado con nuestro 0-day hunter (1,884 archivos PHP en 6 segundos): 199 hallazgos → 72 POP chains → 81 patrones WP → 4 preocupaciones confirmadas. Seguido de analisis manual profundo del codigo fuente.
TL;DR
WordPress 6.7 ships an AI Client with an “Abilities API” that lets AI models execute PHP functions on the server. We performed a full source code audit: 146 SDK files, the adapter layer, and the 3 core abilities. The core implementation is reasonably secure — but the design creates a massive prompt injection → code execution attack surface that will scale with the plugin ecosystem.
What we audited
WordPress 6.7.2 includes a new AI integration layer:
wp-includes/php-ai-client/— 146 PHP files. PSR-compliant SDK for AI providers.wp-includes/ai-client/— 6 adapter files. HTTP client, cache, events, and Abilities.wp-includes/abilities-api/— Registration system.WP_Abilitywraps a PHP callback with validation and permissions.- 3 core abilities:
core/get-site-info,core/get-user-info,core/get-environment-info.
Everything loads on every request via wp-settings.php. Not behind a feature flag. It’s core.
How AI executes server-side code
Plugin triggers wp_ai_client_prompt()
↓
PromptBuilder assembles prompt + tools
↓
HTTP request to AI provider
↓
Model responds with FunctionCall:
{ name: "wpab__core__get_user_info", args: {} }
↓
Resolver checks whitelist + permissions
↓
$ability->execute() → actual PHP code
The AI decides WHAT to call and WITH WHAT ARGUMENTS.
What WordPress got right
- Permission callbacks mandatory — no callback means the ability fails closed.
- JSON Schema validation — same battle-tested REST API validator.
- Safe HTTP —
wp_safe_remote_requestprevents SSRF. - Constructor-scoped whitelist — model can’t call abilities outside the list.
- Class verification —
class_exists()before dynamic instantiation.
What could go wrong
Finding 1: get-user-info only requires is_user_logged_in()
Any subscriber can leak user_login, roles, and user_id via AI. Compare with get-site-info and get-environment-info which require manage_options.
Finding 2: Prompt Injection → Tool Use
The attack:
- Attacker creates content with prompt injection (comment, review, form submission)
- Legitimate user triggers AI processing on that content
- Injected prompt manipulates model into calling abilities
- Abilities execute with the current user’s permissions
Example with WooCommerce: shop manager summarizes a review containing hidden prompt injection → AI creates a 100% discount coupon. Schema validation passes. Permission check passes. Attack succeeds.
Finding 3: No rate limiting
execute_abilities() processes ALL function calls in a message. No limit. A manipulated model could invoke dozens of functions.
Finding 4: Weak random in crypto fallback
If AUTH_SALT is not defined: $salt = (string) rand(); — predictable.
The time bomb
WordPress’s 60,000+ plugins will register abilities. Every ability with weak permissions = a new attack surface. This is the new SQL injection.
Recommendations
Plugin devs: treat AI args as hostile input. Minimum capability checks. Log everything.
Operators: define('WP_AI_SUPPORT', false); if you don’t need it.
WordPress core: add max_ability_calls_per_response, document the risk.
If your application uses WordPress and you want a professional evaluation, check our pentesting plans.
Methodology
Automated analysis with our 0-day hunter (1,884 PHP files in 6 seconds): 199 findings → 72 POP chains → 81 WP patterns → 4 confirmed concerns. Followed by deep manual source code review.