Arr::pull

Reads a value from an array and removes that key in one step.

Signature
public static function pull(&$array, $key, $default = null)

Parameters

ParameterTypeDescription
$&$arrayarrayThe array to read from and mutate. Passed by reference, so it must be a variable.
$$keystring|intThe key to pull. Dot notation is supported because the implementation delegates to Arr::get and Arr::forget.
$$defaultoptionalmixed= nullReturned when the key is absent. Resolved through value(), so a Closure is invoked lazily.

Return value

mixedThe value that was stored at the key, or the default when the key does not exist.

Errors

Raises an error if the first argument is not a variable, since it is taken by reference.

Arr::pull is Arr::get followed by Arr::forget. It answers the very common pattern of taking one field out of a payload so the rest can be handled generically.

When to reach for it

  • Splitting a validated payload: pull the relationship or upload field out, then mass-assign what remains.
  • Consuming an options array where each handler removes the option it understands and the leftovers signal unknown options.
  • Extracting a token or nonce from a data array so it is not persisted along with everything else.

What trips people up

The array is taken by reference, so it must be a variable. Arr::pull($this->config(), 'key') or pulling straight from a function's return value is a fatal error, not a silent no-op.

It mutates. If the array is used elsewhere after the call, that caller now sees a different array. When you only want to read, use Arr::get; when you only want to remove, use Arr::forget.

Dot notation removes the leaf, not the branch. Pulling 'meta.sku' takes the sku value and leaves meta behind as an empty array. Pull 'meta' if you want the whole level gone.

Pulling a key that never existed does not create it — the default is returned and the array is untouched.

Example

Try it yourself
Loading editor…
Press Run to execute the code.

When to use it

  • Take a relationship field out of a validated payload before mass-assigning the rest.
  • Strip a one-time token from a data array so it never reaches storage.
  • Consume known options from a settings array and treat whatever remains as unrecognised.

Frequently asked questions

Does Arr::pull support dot notation?

Yes, because it delegates to Arr::get and Arr::forget internally. Note that pulling 'meta.sku' removes only the sku leaf and leaves an empty meta array behind.

Why do I get an error passing a method call to Arr::pull?

The first parameter is declared by reference, so PHP requires a variable. Assign the result to a local variable first, then pull from that.

What is the difference between Arr::pull and Arr::get?

Arr::pull removes the key after reading it and mutates the array you pass; Arr::get only reads and leaves the array unchanged.

More examples

Splitting a payload before mass assignment

After the pull, $data holds only title and body — the columns that actually exist on the table — while $tags is handled separately. Using Arr::get here would leave 'tags' in $data and break the create() call.

Example · php
<?php

namespace App\Http\Controllers;

use App\Models\Post;
use Illuminate\Http\Request;
use Illuminate\Support\Arr;

class PostController extends Controller
{
    public function store(Request $request)
    {
        $data = $request->validate([
            'title' => ['required', 'string'],
            'body' => ['required', 'string'],
            'tags' => ['array'],
        ]);

        // Take the relationship data out so $data is safe to mass assign.
        $tags = Arr::pull($data, 'tags', []);

        $post = Post::create($data);

        $post->tags()->sync($tags);

        return redirect()->route('posts.show', $post);
    }
}

Pull versus get and forget

The counts show the difference plainly: Arr::get leaves the array at three keys, Arr::pull drops it to two. The leftover-keys pattern in the last line is how option parsers detect arguments they did not recognise.

Example · php
<?php

use Illuminate\Support\Arr;

$options = ['driver' => 'redis', 'ttl' => 60, 'tags' => ['a', 'b']];

// Read without mutating.
$driver = Arr::get($options, 'driver');
echo count($options), PHP_EOL;

// Read and remove.
$ttl = Arr::pull($options, 'ttl');
echo count($options), PHP_EOL;

// Whatever is left is what nobody consumed.
print_r(array_keys($options));

/*
3
2
Array
(
    [0] => driver
    [1] => tags
)
*/

Discussion

  • Be the first to comment on this lesson.