Trongate PHP Framework Docs
Introduction
Quick Start
Basic Concepts
Understanding Routing
Intercepting Requests
Module Fundamentals
Database Operations
Templates
Helpers
Form Handling
Form Validation
Working With Files
Image Manipulation
Working With Dates & Times
Language Control
Security
Tips And Best Practices

Form Validation Introduction

In Trongate v2, form validation is handled by the validation module located at modules/validation/. The Trongate v2 validation module delivers enterprise-grade validation with zero configuration - handling everything from simple required fields to complex custom validation rules, complete with automatic CSRF protection and effortless multilingual support.

How It Works: The Three-Step Pattern

Every validation instance follows the same simple pattern:

  1. Set rules - Define what each field must satisfy
  2. Run validation tests - Check submitted data against your rules
  3. Handle the result - Display errors or process valid data
PHP
// 1. SET RULES
$this->validation->set_rules('username', 'username', 'required|min_length[3]|max_length[30]');
$this->validation->set_rules('email_address', 'email address', 'required|valid_email');

// 2. RUN VALIDATION
$result = $this->validation->run();

// 3. HANDLE RESULT
if ($result === true) {
    // Validation passed - fetch posted data, save and redirect
    $data = [
        'username' => post('username', true),
        'email_address' => post('email_address', true)
    ];
    
    $this->db->insert($data, 'members');
    redirect('members/manage');
} else {
    // Validation failed - redisplay form with errors
    $this->create();
}

Displaying Errors: Three Scenarios

Trongate provides three distinct ways to display validation errors. The helper function plays a pivotal role by automatically selecting the appropriate output format based on its first argument.

Scenario How to Invoke Best For Clears Session?
General Errors validation_errors() Simple forms, login pages, admin panels Yes - all errors
Inline Errors validation_errors('field_name') Long forms, multi-step forms, better UX No - allows multiple field calls
JSON Response validation_errors(422) API endpoints, AJAX forms, mobile apps Yes + exits script

How the helper decides: Pass nothing for general errors, a field name string for inline errors, or an HTTP status code (400-499) for JSON. The helper handles the rest automatically.

Scenario 1: General Errors

Display all errors at once, typically at the top of your form:

View File
<h1>Create Account</h1>
<?= validation_errors() ?>

<?php
echo form_open('users/submit');
echo form_label('Email');
echo form_input('email', $email);
echo form_label('Password');
echo form_password('password');
echo form_submit('submit', 'Register');
echo form_close();
?>

Scenario 2: Inline Errors

Display errors next to specific fields for better user experience:

View File
<?php
echo form_open('users/submit');

echo form_label('Full Name');
echo validation_errors('full_name');
echo form_input('full_name', $full_name);

echo form_label('Email');
echo validation_errors('email');
echo form_email('email', $email);

echo form_submit('submit', 'Register');
echo form_close();
?>

Pro tip: Inline errors don't clear the entire session. You can call validation_errors('field') for multiple different fields throughout your form.

Scenario 3: JSON Response (APIs)

Return structured JSON for API endpoints or AJAX requests:

PHP
public function api_create(): void {
    $this->validation->set_rules('email', 'email', 'required|valid_email');
    $this->validation->set_rules('name', 'name', 'required|min_length[2]');
    
    if ($this->validation->run() === false) {
        validation_errors(422); // Sets HTTP 422, returns JSON, exits
    }
    
    // Only executes if validation passed
    echo json_encode(['success' => true, 'user_id' => $new_id]);
}

JSON output:

JavaScript
[
  {
    "field": "email",
    "messages": ["The email field must contain a valid email address."]
  },
  {
    "field": "name",
    "messages": ["The name field must be at least 2 characters long."]
  }
]

Important: JSON responses terminate script execution with exit(). No code after validation_errors(422) will run.

Setting Validation Rules

Trongate supports two syntax styles for defining rules. Choose the one that fits your needs.

Option 1: Pipe Syntax (Concise)

Ideal for simple forms and quick prototyping:

PHP
$this->validation->set_rules('username', 'username', 'required|min_length[3]|max_length[20]');
$this->validation->set_rules('email', 'email address', 'required|valid_email');
$this->validation->set_rules('age', 'age', 'required|integer|greater_than[0]');

Option 2: Array Syntax (Organized)

Ideal for complex forms and programmatic rule building:

PHP
$rules = [
    'username' => [
        'label' => 'username',
        'required' => true,
        'min_length' => 3,
        'max_length' => 20
    ],
    'email' => [
        'label' => 'email address',
        'required' => true,
        'valid_email' => true
    ],
    'age' => [
        'label' => 'age',
        'required' => true,
        'integer' => true,
        'greater_than' => 0
    ]
];

$result = $this->validation->run($rules);

Common Built-In Rules

Rule Description
requiredField cannot be empty
min_length[n]Minimum character length
max_length[n]Maximum character length
valid_emailValid email format
numericMust be a number
integerMust be an integer
matches[field]Must match another field (e.g., password confirmation)

See Validation Rules Reference for the complete list including date/time and file upload rules.

Special Case: Checkbox Validation

Checkboxes behave differently because unchecked boxes submit nothing. An unchecked checkbox returns '' (empty string) from post().

PHP
// REQUIRED checkbox  -  user MUST check it
$this->validation->set_rules('terms', 'terms and conditions', 'required');

// OPTIONAL checkbox  -  no validation rule needed
// Simply convert the value for database storage
$data['newsletter'] = (int) (bool) post('newsletter', true); // 0 or 1

Complete Working Example

Here's a full implementation using the create/update pattern:

PHP
class Users extends Trongate {

    public function create(): void {
        $update_id = segment(3, 'int');
        $submit = post('submit');

        // Load data from POST (new record or validation error) or DB (editing)
        if (($update_id === 0) || ($submit === 'Submit')) {
            $data = $this->model->get_data_from_post();
        } else {
            $data = $this->model->get_data_from_db($update_id);
        }

        $data['headline'] = ($update_id === 0) ? 'Create User' : 'Update User';
        $data['form_location'] = str_replace('/create', '/submit', current_url());
        
        $this->view('create', $data);
    }

    public function submit(): void {
        // Set validation rules
        $this->validation->set_rules('username', 'username', 'required|min_length[3]|max_length[20]');
        $this->validation->set_rules('email', 'email address', 'required|valid_email');
        $this->validation->set_rules('password', 'password', 'required|min_length[8]');

        if ($this->validation->run() === true) {
            // Success: save and redirect
            $data = $this->model->get_data_from_post();
            $update_id = segment(3, 'int');

            if ($update_id === 0) {
                $this->db->insert($data, 'users');
                set_flashdata('User created successfully');
            } else {
                $this->db->update($update_id, $data, 'users');
                set_flashdata('User updated successfully');
            }

            redirect('users/manage');
        } else {
            // Failure: redisplay form with errors
            $this->create();
        }
    }
}

Key Points

  • Validation rules are set with and executed with
  • Use lowercase field labels for natural error messages: "The email address field is required"
  • Always use post('field', true) to get cleaned, trimmed values
  • CSRF protection is automatic - every POST form is protected
  • Errors survive redirects via session storage
  • Optional fields skip validation when empty - only validate what matters

Validation lifecycle: Validation fails → errors stored in session → form redisplays with errors. Validation passes → data saves → flashdata set → redirect to success page.

What's Next

The following pages cover everything you need to master form validation:

We're continually improving the Trongate documentation. If anything is incorrect, unclear, incomplete, or could be better, we'd genuinely appreciate your input.

Share your thoughts in the Documentation Feedback.

Leave Feedback About This Page