You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WordPress REST API中如何自定义元值验证?

Alternative Approaches for Custom Meta Field Validation in WordPress REST API

Great question! The built-in schema validation in WordPress REST API can feel restrictive at times, but there are a few more workarounds beyond the two you’ve outlined. Let’s dive into them, plus expand on that pattern trick you mentioned—it’s more useful than you might think.

1. Use register_rest_field Instead of register_meta

Instead of relying on the default post controller’s auto-generated schema, you can create a custom REST field directly with register_rest_field. This gives you full control over validation via the update_callback parameter, where you can implement any custom logic you need.

Example code:

register_rest_field( 'your_custom_post_type', 'your_meta_key', array(
    'get_callback' => function( $post ) {
        return get_post_meta( $post['id'], 'your_meta_key', true );
    },
    'update_callback' => function( $value, $post ) {
        // Your custom validation logic here
        if ( ! preg_match( '/^[A-Z0-9]{8}$/', $value ) ) {
            return new WP_Error(
                'invalid_meta_value',
                'Your meta value must be 8 uppercase alphanumeric characters.',
                array( 'status' => 400 )
            );
        }

        // If validation passes, update the meta
        update_post_meta( $post->ID, 'your_meta_key', $value );
        return true;
    },
    'schema' => array(
        'type' => 'string',
        'description' => 'Custom meta field with custom validation',
    ),
) );

This approach lets you bypass the default schema validation entirely for that specific field and handle things exactly how you want.

2. Hook into rest_request_before_callbacks

You can intercept the entire REST request before the controller callbacks run using the rest_request_before_callbacks filter. This is great if you need to validate multiple fields or add cross-field validation logic.

Example:

add_filter( 'rest_request_before_callbacks', function( $response, $handler, $request ) {
    // Check if we're dealing with the correct endpoint and post type
    if ( $request->get_route() === '/wp/v2/your_custom_post_type/(?P<id>[\d]+)' && $request->get_method() === 'POST' ) {
        $meta_value = $request->get_param( 'your_meta_key' );
        
        // Custom validation
        if ( empty( $meta_value ) || strlen( $meta_value ) < 5 ) {
            return new WP_Error(
                'invalid_meta',
                'Meta value must be at least 5 characters long.',
                array( 'status' => 400 )
            );
        }
    }

    return $response;
}, 10, 3 );

This gives you a high-level way to validate data before it reaches the default controller’s logic.

3. Extend rest_validate_value_from_schema with a Filter

WordPress provides the rest_validate_value_from_schema filter, which lets you override or extend the default validation logic for any schema value. You can use this to add custom validation rules without rewriting entire controller methods.

For example, if you want to add a custom validation rule for a specific meta field’s schema:

add_filter( 'rest_validate_value_from_schema', function( $is_valid, $value, $schema, $param ) {
    // Check if this is our target meta field and schema has a custom rule
    if ( $param === 'your_meta_key' && isset( $schema['custom_validation'] ) ) {
        switch ( $schema['custom_validation'] ) {
            case 'even_number':
                $is_valid = is_numeric( $value ) && $value % 2 === 0;
                if ( ! $is_valid ) {
                    rest_add_validation_error( $param, 'Value must be an even number.' );
                }
                break;
        }
    }

    return $is_valid;
}, 10, 4 );

Then when registering your meta, add the custom flag to the schema:

register_meta( 'post', 'your_meta_key', array(
    'type' => 'integer',
    'single' => true,
    'show_in_rest' => array(
        'schema' => array(
            'type' => 'integer',
            'custom_validation' => 'even_number', // Custom flag
        ),
    ),
) );

This way, you can keep using register_meta but inject custom validation logic into the existing pipeline.

Don’t Sleep on the pattern Attribute

You mentioned the pattern property for string types, and it’s worth highlighting how powerful this can be for common validation needs. For example, validating a US zip code or a specific date format:

register_meta( 'post', 'custom_date', array(
    'type' => 'string',
    'single' => true,
    'show_in_rest' => array(
        'schema' => array(
            'type' => 'string',
            'pattern' => '^\d{4}-\d{2}-\d{2}$', // YYYY-MM-DD format
            'description' => 'Date in YYYY-MM-DD format',
        ),
    ),
) );

This uses JSON Schema’s pattern keyword, which supports full regular expressions—perfect for simple to moderately complex string validation without writing custom PHP.

Which Approach Should You Choose?

  • Use register_rest_field if you want full control over the field’s behavior (validation, retrieval, updates).
  • Use rest_request_before_callbacks for cross-field validation or validating multiple fields at once.
  • Use rest_validate_value_from_schema if you want to extend the default schema validation while keeping register_meta’s convenience.
  • Stick with pattern for straightforward string format validation—it’s the simplest solution when it fits your needs.

内容的提问来源于stack exchange,提问作者Josef Wittmann

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.11 07:43:46