Add Custom Field Validation to WordPress Post Types
In the previous tutorial, we covered creating a custom flight controller and forms. Let's extend the forms with field validation for the seat post type that saves its fields to a custom table.
Add Validation
Start by adding form field validation to the \App\Controllers\SeatController
using the onValidateSave()
method. You can add validation to forms in a few ways using the validator TypeRocket comes with. In this tutoral, we will instead use the \TypeRocket\Http\Fields
class. The \TypeRocket\Http\Fields
class makes use of the validator but adds a few extra features to simplify the process of applying validation on a page request.
To create a custom \TypeRocket\Http\Fields
class use the galaxy CLI.
php galaxy makes:fields SeatFields
Remember, we are now saving data to a custom table and when the form is submitted the data.Row
field's information is grouped under data
. Keep this in mind as you work with custom grouped fields and validation. If the fields were not grouping data
throughout this tutoral can be skipped.
Lets, review one of the fields from the tutorial and change the field type. This will give us a text field which we can use to test the validation system.
// Change from
echo $form->select('data.Row')->searchable()->setOptions(range(1, 15), 'flat');
// To
echo $form->text('data.Row');
Now, open the FlightFields
under app/Http/Fields/SeatFields.php
and add the validation we want. Note, we are prefixing the rule with data
because the custom fields in the request are grouped into data
. Make the data.row
field required with a max charater length of 2 and leave $run
as null
. Also, add $modelFieldsGroup = 'data'
because when a model recives the fields it needs to know the fields are grouped.
<?php
namespace App\Http\Fields;
use TypeRocket\Http\Fields;
class SeatFields extends Fields
{
/** @var bool Validate & redirect on errors immediately */
protected $run = null;
protected $modelFieldsGroup = 'data';
/**
* @return array
*/
protected function fillable() {
return [];
}
/**
* @return array
*/
protected function rules() {
return ['data.row' => 'required|numeric|max:2'];
}
}
Apply Validation
Now, just import the new FlightFields
into the onValidateSave
method on the \App\Controllers\SeatController
. When there is invalid input we will show the errors and leave the custom fields unsaved by returning false
an failed validation.
public function onValidateSave($type, Seat $seat, SeatFields $fields)
{
$validator = $fields->validate();
if($validator->failed()) {
// Post types will always save the WordPress core data.
// Validation is only for custom TypeRocket fields.
$validator->prependToFlashErrorMessage('No fields saved. Only date and status saved.');
$fields->runAndRespond('response');
return false;
}
return true;
}
Now, when there is a field input error the user will be shown the error messages. Keep in mind post types limit use to validation on the custom fields only.
Keeping Old Fields and Showing Field Errors
Next, in the post type registration, useErrors()
, to the forms and keep the old fields, useOld()
. Also, lets improve the design and wrap the fields in a UI form container.
$form = tr_form()->useErrors()->useOld();
$form->setFields(
$form->text('data.Row'),
$form->radio('data.Letter')->setOptions(['A','C','D','F'], 'flat')->setDefault('A')
);
echo $form->fieldsWrapperString();
Next, apply a required asterisk to the row field.
$form->text('data.Row')->markLabelRequired()
Finished!