PHP

Robust Input Validation and Sanitization in PHP

Implement strong server-side input validation and sanitization in PHP to ensure data integrity and prevent various security vulnerabilities from user-provided data.

<?php
// Simulate form submission data
$_POST = [
    'username' => '  John Doe  ',
    'email'    => 'invalid-email',
    'age'      => '25',
    'comment'  => '<script>alert("XSS!");</script>Hello & World!',
    'product_id' => 'abc',
    'referrer' => 'http://malicious.com/?data=<script>alert(1)</script>',
];

function validateAndSanitizeInput($input) {
    $errors = [];
    $sanitizedData = [];

    // Username: Trim whitespace, strip tags (basic), ensure length
    $sanitizedData['username'] = filter_var(trim($input['username'] ?? ''), FILTER_SANITIZE_STRING, FILTER_FLAG_STRIP_LOW | FILTER_FLAG_STRIP_HIGH);
    if (empty($sanitizedData['username'])) {
        $errors['username'] = 'Username is required.';
    } elseif (strlen($sanitizedData['username']) < 3 || strlen($sanitizedData['username']) > 50) {
        $errors['username'] = 'Username must be between 3 and 50 characters.';
    }

    // Email: Sanitize and validate email format
    $sanitizedData['email'] = filter_var($input['email'] ?? '', FILTER_SANITIZE_EMAIL);
    if (!filter_var($sanitizedData['email'], FILTER_VALIDATE_EMAIL)) {
        $errors['email'] = 'Invalid email format.';
    }

    // Age: Sanitize to integer, validate range
    $sanitizedData['age'] = filter_var($input['age'] ?? '', FILTER_SANITIZE_NUMBER_INT);
    if (!filter_var($sanitizedData['age'], FILTER_VALIDATE_INT, ['options' => ['min_range' => 18, 'max_range' => 99]])) {
        $errors['age'] = 'Age must be an integer between 18 and 99.';
    }

    // Comment: Strip tags, encode special characters (for display later)
    // For storage, usually just strip tags or use a markdown parser.
    // For display, always escape HTML.
    $sanitizedData['comment_for_db'] = htmlspecialchars(strip_tags($input['comment'] ?? ''));
    if (empty($sanitizedData['comment_for_db'])) {
        // Can be empty, but good to check if it's required
    }

    // Product ID: Validate as an integer only (e.g., from URL parameter)
    $sanitizedData['product_id'] = filter_var($input['product_id'] ?? '', FILTER_VALIDATE_INT);
    if ($sanitizedData['product_id'] === false) { // filter_var returns false on failure for FILTER_VALIDATE_INT
        $errors['product_id'] = 'Product ID must be an integer.';
    }

    // Referrer URL: Sanitize URL, optionally validate if it's from an allowed domain
    $sanitizedData['referrer'] = filter_var($input['referrer'] ?? '', FILTER_SANITIZE_URL);
    if (!filter_var($sanitizedData['referrer'], FILTER_VALIDATE_URL)) {
        $errors['referrer'] = 'Invalid referrer URL format.';
    }
    // Optional: Check if referrer is from an allowed domain
    // $parsedUrl = parse_url($sanitizedData['referrer']);
    // if (isset($parsedUrl['host']) && !in_array($parsedUrl['host'], ['allowed-domain.com'])) {
    //     $errors['referrer'] = 'Referrer not from an allowed domain.';
    // }


    return ['data' => $sanitizedData, 'errors' => $errors];
}

$processed = validateAndSanitizeInput($_POST);

if (empty($processed['errors'])) {
    echo "Validation successful! Sanitzed data:
";
    echo json_encode($processed['data'], JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES);
    // Proceed with saving data to database or further processing
} else {
    echo "Validation errors found:
";
    echo json_encode($processed['errors'], JSON_PRETTY_PRINT | JSON_UNESCAPED_SLASHES);
    // Display errors to the user
}
?>
How it works: This PHP snippet demonstrates robust server-side input validation and sanitization using `filter_var` and other PHP functions. It processes simulated form data, trimming whitespace, validating data types (email, integer), checking lengths, and stripping potentially malicious HTML tags from comments. This layered approach ensures that only clean and expected data formats are processed by the application, preventing common vulnerabilities like XSS (when displaying) and ensuring data integrity before persistence.

Need help integrating this into your project?

Our team of expert developers can help you build your custom application from scratch.

Hire DigitalCodeLabs