integer

Validates that a field is an integer as accepted by PHP's FILTER_VALIDATE_INT filter.

Signature
integer  |  integer:strict

Parameters

ParameterTypeDescription
$strictoptionalstringLiteral flag. When present, only a value whose PHP type is integer passes; strings holding integer values are rejected.

Errors

Nothing on its own — the failure is recorded as a message, and Illuminate\Validation\ValidationException is raised only by validate() on a failing validator.

Changelog

  • PHP 12.xAdded the strict parameter (integer:strict), which rejects strings with integer values and passes only the integer type.

integer checks that a field is an integer in the sense PHP's FILTER_VALIDATE_INT filter means it: 42, "42", "-7" and "+3" pass; "4.5", "1e3", "42abc" and "" do not.

When to reach for it

  • Route or query parameters that are database ids, page numbers or offsets.
  • Counts and quantities that must not carry a fractional part.
  • Enum-like numeric codes, usually alongside in:1,2,3.

What trips people up

The framework documentation carries an explicit warning here: this rule does not verify the variable type, only that the value is of a type the integer filter accepts. Because FILTER_VALIDATE_INT is permissive about what it will coerce, the docs recommend combining it with numeric when you truly want "this is a number, and it is whole".

Second, nothing is cast. A field validated with integer still comes back from validated() as the string "42", which will make a strict comparison (===), a match arm, or a typed constructor argument behave differently from what you expect. Read it through $request->integer('quantity'), cast it in the model, or use integer:strict if the client should be sending a real JSON integer.

Example

Example · php
<?php

use Illuminate\Support\Facades\Validator;

$validator = Validator::make([
    'quantity' => '42',
    'discount' => '4.5',
], [
    'quantity' => ['required', 'integer', 'min:1'],
    'discount' => ['nullable', 'integer'],
]);

print_r($validator->errors()->toArray());

// Array
// (
//     [discount] => Array
//         (
//             [0] => The discount field must be an integer.
//         )
// )

var_dump($validator->valid()['quantity']);

// string(2) "42"   <- validated, but still a string

When to use it

  • Guard a page or per_page query parameter before it reaches a paginator.
  • Validate a quantity on an order line so a fractional value never reaches the database.
  • Check a foreign key posted from a select box, paired with exists.
  • Bound a numeric API version or code field with integer plus in.

Frequently asked questions

Why does the integer rule accept the string "42"?

Because the rule checks PHP's FILTER_VALIDATE_INT filter rather than the variable type, and form and query input always arrives as strings. Use integer:strict, added in Laravel 12, if you require a real integer type.

Does the integer validation rule cast the value to an int?

No. validated() returns the value unchanged, so "42" stays a string. Use $request->integer('field'), an explicit (int) cast, or an Eloquent cast on the model attribute.

Should I use integer or numeric for a quantity field?

Use both — ['required', 'numeric', 'integer'] — which is what the Laravel documentation recommends. numeric guarantees the value is a number and integer guarantees it has no fractional part.

More examples

Pairing integer with numeric

The documentation's own recommendation: state numeric alongside integer when the field must be a number as well as integer-shaped. perPage() shows the cast step — $request->integer() returns a real int with a fallback, so the paginator never receives a string.

Example · php
<?php

namespace App\Http\Requests;

use Illuminate\Foundation\Http\FormRequest;

class ListOrdersRequest extends FormRequest
{
    public function rules(): array
    {
        return [
            'page'     => ['sometimes', 'numeric', 'integer', 'min:1'],
            'per_page' => ['sometimes', 'numeric', 'integer', 'between:1, 100'],
        ];
    }

    public function perPage(): int
    {
        return $this->integer('per_page', 25);
    }
}

Strict integer on a JSON endpoint

With strict, only the field whose PHP type is integer survives; "7" as a JSON string fails. Reserve this for machine-to-machine endpoints — an HTML form posts every field as a string, so integer:strict would reject all of them.

Example · php
<?php

use Illuminate\Support\Facades\Validator;

$payload = json_decode('{"a": 7, "b": "7"}', true);

$validator = Validator::make($payload, [
    'a' => ['integer:strict'],
    'b' => ['integer:strict'],
]);

print_r($validator->errors()->keys());

// Array
// (
//     [0] => b
// )

Route model id in a controller

Shows integer used at two levels: on a foreign key before an exists lookup, and inside a wildcard path so every line item's quantity is checked. A failing validate() call throws ValidationException, which the framework turns into a 422 response for JSON clients.

Example · php
<?php

namespace App\Http\Controllers;

use Illuminate\Http\Request;

class InvoiceController extends Controller
{
    public function store(Request $request)
    {
        $data = $request->validate([
            'customer_id' => ['required', 'integer', 'exists:customers,id'],
            'line_items'  => ['required', 'array', 'min:1'],
            'line_items.*.quantity' => ['required', 'integer', 'min:1'],
        ]);

        echo count($data['line_items']), " line items accepted\n";
    }
}

Discussion

  • Be the first to comment on this lesson.