Laravel 11开启shouldBeStrict后自定义属性报Undefined array key错误
修复Laravel严格模式下自定义属性Undefined array key错误
问题出在开启Model::shouldBeStrict()后,模型的$attributes数组会严格校验键的存在——你的自定义属性select和mediaData并非数据库字段,首次加载模型时$attributes里没有这些键,直接通过$this->attributes['select']访问就会触发错误。
以下是几种可行的修复方案:
方案1:在Getter中使用安全访问
修改属性的获取方法,添加默认值兜底,避免直接访问不存在的数组键:
// Get select value. public function getSelectAttribute(): bool { return $this->attributes['select'] ?? false; } // Get mediaData value. public function getMediaDataAttribute(): array { return $this->attributes['mediaData'] ?? []; }
这种方式最简单,直接在Getter里处理不存在的情况,给属性设置合理的默认值(比如select默认false,mediaData默认空数组)。
方案2:模型加载时初始化属性
利用模型的retrieved事件,在每次模型从数据库取出后自动初始化自定义属性,确保$attributes里存在对应的键:
protected static function boot() { parent::boot(); if(App::isLocal()) { Model::shouldBeStrict(); } // 模型加载后初始化自定义属性 static::retrieved(function ($currency) { if (!array_key_exists('select', $currency->attributes)) { $currency->setSelectAttribute(false); } if (!array_key_exists('mediaData', $currency->attributes)) { $currency->setMediaDataAttribute([]); } }); }
这种方式能保证每次模型实例化后,$attributes里都有自定义属性的键,后续访问不会报错。
方案3:使用类属性存储临时值
既然这些是运行时的临时属性(非数据库字段),没必要存在$attributes数组里,直接用类的私有属性存储更规范:
class Currency extends Model implements HasMedia { protected $table = 'currencies'; protected $primaryKey = 'id'; public $timestamps = false; protected $appends = ['select', 'mediaData']; // 用类属性存储临时值 private ?bool $select = false; private array $mediaData = []; protected static function boot() { parent::boot(); if(App::isLocal()) { Model::shouldBeStrict(); } } // Set select value. public function setSelectAttribute(bool $value): void { $this->select = $value; } // Get select value. public function getSelectAttribute(): bool { return $this->select; } // Set mediaData value. public function setMediaDataAttribute(array $value): void { $this->mediaData = $value; } // Get mediaData value. public function getMediaDataAttribute(): array { return $this->mediaData; } }
这种方式彻底脱离$attributes数组,完全避开严格模式的限制,同时符合临时属性的设计逻辑,推荐用于非数据库字段的自定义属性。
内容的提问来源于stack exchange,提问作者mstdmstd
相关产品推荐
相关产品推荐

