Skip to content

Eloquent Value Object are not casted back when converting models to json. #33257

@rela589n

Description

@rela589n
  • Laravel Version: 7.15.0
  • PHP Version: 7.3.7
  • Database Driver & Version: 10.3.16-MariaDB

Description:

The problem is that value objects are not casted back when call Client::toJson().
So, for example we have next model:

App\Models\Client {#4028
     id: 7,
     name: "asdf@asdf.com",
     email_verified_at: null,
   }

Accessing name property gives us Name value object:

App\ValueObjects\Name^ {#4027
  #name: "asdf@asdf.com"
}

When we call $client->toJson(), we get empty object instead of primitive value:
{"id":7,"name":{},"email_verified_at":null}

Steps To Reproduce:

Client Eloquent Model:

class Client extends Authenticatable
{
    use Notifiable;

    protected $table = 'users';

    protected $hidden = [
        'password', 'remember_token',
    ];

    protected $casts = [
        'name'     => NameCast::class,
        'password' => PasswordCast::class,
    ];
}

Name Cast:

class NameCast implements CastsAttributes
{
    public function get($model, string $key, $value, $attributes)
    {
        return Name::create($value);
    }

    public function set($model, string $key, $setName, $attributes)
    {
        if (!$setName instanceof Name) {
            throw new \InvalidArgumentException('Parameter $setName must be instance of ' . Name::class);
        }

        return [
            $key => $setName->value()
        ];
    }
}

Name Value Object:

class Name
{
    public const MIN_LENGTH = 2;

    protected $name;

    private function __construct(string $name)
    {
        if (mb_strlen($name) < self::MIN_LENGTH) {
            throw new \InvalidArgumentException('Name must has at least ' . self::MIN_LENGTH . ' characters');
        }

        $this->name = $name;
    }

    public static function create(string $name): Name
    {
        return new static($name);
    }

    public function value()
    {
        return $this->name;
    }
}

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions