Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Only User Model is saving with empty Values to database

In Laravel 5.4 when I try to save User model to the database the values are not saved. I've set the fillable property as well.

It was working in Laravel 5.3. This issue is coming after upgrading the application into Laravel 5.4.

Below is a User model.

class User extends BaseModel implements AuthenticatableContract, CanResetPasswordContract, JWTSubject
{
    use SoftDeletes,
        UserAccess,
        UserAttribute,
        UserRelationship,
        Authenticatable,
        CanResetPassword,
        Notifiable;

    /**
     * Database Table
     *
     * @var string
     */
    protected $table = "users";

    /**
     * The attributes that are not mass assignable.
     *
     * @var array
     */
    protected $guarded = ['id'];

    /**
     * Fillable Form Fields
     *
     * @var array
     */
    protected $fillable = [
        'name',
        'first_name',
        'last_name',
        'email',
        'password',
        'status',
        'confirmed',
        'api_user',
        'confirmation_code',
        'account_id',
        'role_id',
        'cw_contact_id',
        'all',
        'all_locations',
        'username',
    ];

    /**
     * The attributes that should be hidden for arrays.
     *
     * @var array
     */
    protected $hidden = ['password', 'remember_token'];

    /**
     * Select HTML Preference
     *
     * @var string
     */
    protected static $selectHTMLFormat = "[email]";

    /**
     * @var array
     */
    protected $dates = ['deleted_at', 'last_login'];
}

Please note the issue is with User Model only.

I'm saving User as below.

// Create User
        $user = $this->model->create([
            'first_name'        => $input['first_name'],
            'last_name'         => $input['last_name'],
            'username'          => $input['username'],
            'email'             => $input['email'],
            'password'          => bcrypt($input['password']),
            'confirmation_code' => md5(uniqid(mt_rand(), true)),
            'confirmed'         => 1,
            'api_user'          => (isset($input['api_user']) ? $input['api_user'] : 0),
            'account_id'        => $input['account_id'],
            'role_id'           => (isset($input['role_id']) ? $input['role_id'] : 0),
            'all'               => (!isset($input['associated-permissions']) || $input['associated-permissions'] == 'all') ? 1 : 0,
            'status'            => (!isset($input['status']) || $input['status'] ? 1 : 0),
            'all_locations'     => $input['all_locations']
        ]);

Then the create method of BaseModel will be called and below is the code of it.

public static function create(array $attributes = Array())
{
    $user = access()->user();

    if($user)
    {
        $attributes['account_id'] = (!isset($attributes['account_id']) ? $user->account->id : $attributes['account_id'] );
    }

    $childClass     = get_called_class();
    $model          = new $childClass;
    $model->runActionLogger(false, 'create');

    return parent::query()->create($attributes);
}
like image 650
Viral Solani Avatar asked Apr 06 '17 07:04

Viral Solani


2 Answers

The reason is most probably the new middleware in Laravel 5.4 called "Request Sanitization Middleware" as explained in https://laravel.com/docs/5.4/releases.

Disable \Illuminate\Foundation\Http\Middleware\ConvertEmptyStringsToNull::class, in app/Http/kernel.php and see what you get.

You can also check in /config/database.php and your mysql connection settings: 'strict' => true, if so, set to false.

A good practice is using the model for user input. In this case, instead of $user = $this->model->create(...) populate you model with $user = new \App\User($input) and update your values from there, f.ex. $user->confirmation_code = md5(uniqid(mt_rand(), true)); and $user->password = bcrypt($user->password);

If fields are nullable, indicate as such in your migration file, f.ex. $table->string('all')->nullable();

If done just run $user->save();

like image 63
Dimitri Mostrey Avatar answered Oct 15 '22 23:10

Dimitri Mostrey


From 5.4 the create() function is not more defined in Illuminate\Database\Eloquent\Model:

Is handled as dinamic method call, that is by calling one of these functions (dependig on if it's called statically or not):

public static function __callStatic($method, $parameters)
// or
public function __call($method, $parameters)

In the Illuminate\Database\Eloquent\Model class.

Now I dont have all your code but, IMHO, I will try to change this line in your BaseModel class:

return parent::query()->create($attributes);

to this:

return $model->create($attributes);

or, even better for me, to this:

return (new static)->newQuery()->create($attributes);
like image 26
dparoli Avatar answered Oct 15 '22 22:10

dparoli