Laravel 5.2 $fillable

2019-08-13 00:41发布

问题:

Let's say, my model has the following DB structure:

name:string
last_name:string

And I wish to update the model, with this $request->input() array given:

name => 'Quinn',
last_name => 'Daley',
middle_name => 'Phill'

I would get an error message, because it would try to update the middle_name field, which does not exist in the DB.

So here is my question: How can I make it so only existing fields are updated? Without using the protected $fillable property.

Edit: the reason I don't want to use $fillable is that I don't want to list all the existing fields from the database. What if I have a large model with 50 fields in it? Isn't there a possibility to only accept parameters that exist in the model DB from the $request->input()?

UPDATE

There is a cleaner solution using $model->getAttributes():

$user->update($request->only(array_keys($user->getAttributes()))

This solution is also better if you are using a different $connection for the model, which was my case.

回答1:

Instead of using input() or all(), you can use the only() or except() methods on the request to limit the fields. For example:

$user = User::find(1);

$user->update($request->only(['name', 'last_name']));
// or
$user->update($request->except(['middle_name']));

Edit

If you want to get the column names of the table, you can do this using Schema::getColumnListing($tableName);. So, in this case, your code would look something like:

$user = User::find(1);

$user->update($request->only(Schema::getColumnListing($user->getTable())));


回答2:

protected $fillable will be required, if you are using create or update function. however, I think you solve it in this way without using the protected $fillable property.

$yourmodel = YourModel::find($id);
$yourmodel->name = $request->input("name");
$yourmodel->last_name = $request->input("last_name");
$yourmodel->save();


回答3:

You can use fillable array in this way:

// in your model

/**
 * Get only available fields
 *
 * @param  array  $input
 * @return array
 */
public function filterFields(array $input)
{
    $fields = $this->fillable;

    return array_filter($input, function ($v, $k) use ($fields) {
        return in_array($k, $fields);
    }, ARRAY_FILTER_USE_BOTH);
}

And filter data from $request->input(); Also you can make middleware for this perpose.