You're correct: the issue is with how the cast is being applied to the colors property. By default, Spatie's DataCast is designed to cast a single value to a Data object, not an array of Data objects. When you define:
'colors' => DataCast::class . ':' . ColorData::class,
it tries to cast the entire array as a single ColorData instance, which fails if the array is empty or contains multiple items.
Solution: Use DataCollectionCast for Arrays of Data Objects
Spatie Laravel Settings provides a DataCollectionCast specifically for this use case. You should update your cast definition like this:
use Spatie\LaravelSettings\SettingsCasts\DataCollectionCast;
public static function casts(): array
{
return [
'colors' => DataCollectionCast::class . ':' . ColorData::class,
];
}
This tells Laravel Settings to cast the colors property as a collection of ColorData objects.
Full Example:
namespace App\Settings\Background;
use App\Data\Settings\Background\ColorData;
use Spatie\LaravelSettings\Settings;
use Spatie\LaravelSettings\SettingsCasts\DataCollectionCast;
class ColorSettings extends Settings
{
public bool $enabled = false;
/** @var ColorData[] */
public array $colors = [];
public static function group(): string
{
return 'background:color';
}
public static function casts(): array
{
return [
'colors' => DataCollectionCast::class . ':' . ColorData::class,
];
}
}
Summary:
- Use
DataCastfor a single Data object. - Use
DataCollectionCastfor an array of Data objects.
References:
Let me know if you need further clarification!