laravel/framework · error · InvalidArgumentException

Non-numeric value passed to increment method.

Error message

Non-numeric value passed to increment method.

What it means

Thrown by increment when $amount fails is_numeric(). increment generates `SET col = col + amount`; a non-numeric amount (string text, null, array, object) would produce invalid SQL or wrong bindings. Note the default is 1, so this only fires when the caller explicitly passes a bad value.

Source

Thrown at src/Illuminate/Database/Query/Builder.php:4431

        return $this->connection->affectingStatement(
            $this->grammar->compileUpsert($this, $values, (array) $uniqueBy, $update),
            $bindings
        );
    }

    /**
     * Increment a column's value by a given amount.
     *
     * @param  string  $column
     * @param  float|int  $amount
     * @return int<0, max>
     *
     * @throws \InvalidArgumentException
     */
    public function increment($column, $amount = 1, array $extra = [])
    {
        if (! is_numeric($amount)) {
            throw new InvalidArgumentException('Non-numeric value passed to increment method.');
        }

        return $this->incrementEach([$column => $amount], $extra);
    }

    /**
     * Increment the given column's values by the given amounts.
     *
     * @param  array<string, float|int|numeric-string>  $columns
     * @param  array<string, mixed>  $extra
     * @return int<0, max>
     *
     * @throws \InvalidArgumentException
     */
    public function incrementEach(array $columns, array $extra = [])
    {
        foreach ($columns as $column => $amount) {
            if (! is_numeric($amount)) {

View on GitHub (pinned to bd6b5437e6)

Solutions

  1. Cast or validate the input: `$amount = (float) $request->input('n', 1); if (!is_numeric($request->input('n'))) abort(422);`.
  2. Provide an explicit numeric default: `->increment('views', 1)`.
  3. Use a numeric-string check (`is_numeric`) on raw input before calling.
  4. Reject empty/null with a request validation rule like `'n' => 'sometimes|numeric|min:0'`.

Example fix

// before
$post->increment('views', $request->input('views'));
// when views is null or 'lots' => Non-numeric value passed to increment method.

// after
$request->validate(['views' => 'sometimes|numeric|min:0']);
$post->increment('views', (float) $request->input('views', 1));
Defensive patterns

Strategy: validation

Validate before calling

if (! is_numeric($amount)) {
    throw new \InvalidArgumentException('increment amount must be numeric, got: '.get_debug_type($amount));
}
$model->increment($column, (float) $amount);

Type guard

function isNumericAmount(mixed $amount): bool
{
    return is_int($amount) || is_float($amount) || (is_string($amount) && is_numeric($amount));
}

Try / catch

// Validate the amount before calling; catching is rarely useful for a programming/type error.

Prevention

When it happens

Trigger: `->increment('views', $request->views)` where views is a string like 'five' or null. Passing a numeric string is fine (is_numeric accepts '5'), but letters fail. Passing a float cast of a non-numeric string yields 0, which is numeric, so the real danger is unclosed form fields yielding null/empty.

Common situations: Counter endpoints receiving unvalidated JSON; analytics hooks incrementing by user-supplied weights; nullable columns read back as null and fed back into increment.

Related errors


AI-assisted analysis of laravel/framework@bd6b5437e6 (2026-08-06). Data as JSON: /data/errors/0afc7c0534620984.json. Report an issue: GitHub.