You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel中为Ben Sampo Enum添加自定义属性及本地化方案

解决Ben Sampo Enum扩展包自定义属性读取问题

1. 修正自定义属性读取Trait

原GetEnumAttributes trait无法正确读取属性值,核心问题是未从枚举项的反射注解中提取对应值,重新实现如下:

namespace App\Enums\Traits;

use BenSampo\Enum\Enum;
use ReflectionClass;

trait GetEnumAttributes
{
    /**
     * 获取单个枚举实例的所有自定义属性
     * @return array
     */
    public function getAttributes(): array
    {
        $reflectionClass = new ReflectionClass($this);
        $property = $reflectionClass->getProperty($this->name);
        $attribute = $property->getAttributes(\App\Enums\Attributes\EnumAttribute::class)[0] ?? null;
        
        return $attribute ? $attribute->getArguments() : [];
    }

    /**
     * 通过枚举值获取指定属性
     * @param int|string $value
     * @param string $attributeName
     * @return mixed|null
     */
    public static function getAttribute(int|string $value, string $attributeName)
    {
        $enum = static::fromValue($value);
        return $enum->getAttributes()[$attributeName] ?? null;
    }

    /**
     * 获取color属性的快捷方法
     * @param int|string $value
     * @return string|null
     */
    public static function getColor(int|string $value): ?string
    {
        return static::getAttribute($value, 'color');
    }

    /**
     * 获取所有带自定义属性的枚举实例
     * @return array
     */
    public static function getCustomInstances(): array
    {
        $instances = [];
        foreach (static::cases() as $case) {
            $instances[] = array_merge([
                'value' => $case->value,
                'name' => $case->name,
                'description' => $case->description,
            ], $case->getAttributes());
        }
        return $instances;
    }

    // 单个枚举实例的属性快捷访问
    public function getColor(): ?string
    {
        return $this->getAttributes()['color'] ?? null;
    }

    public function isFinal(): ?bool
    {
        return $this->getAttributes()['isFinal'] ?? null;
    }
}

2. 定义自定义属性注解类

创建统一的注解类来标记枚举项的自定义属性,确保反射能正确识别:

namespace App\Enums\Attributes;

use Attribute;

#[Attribute(Attribute::TARGET_PROPERTY)]
class EnumAttribute
{
    public function __construct(
        public ?string $color = null,
        public ?bool $isFinal = false
    ) {}
}

3. 实现带自定义属性的Status枚举

继承Ben Sampo Enum并集成上述Trait和注解,同时保留本地化特性:

namespace App\Enums;

use BenSampo\Enum\Enum;
use App\Enums\Attributes\EnumAttribute;
use App\Enums\Traits\GetEnumAttributes;

final class Status extends Enum
{
    use GetEnumAttributes;

    #[EnumAttribute(color: '#4CAF50', isFinal: false)]
    const Initial = 1;

    #[EnumAttribute(color: '#FFC107', isFinal: false)]
    const Processing = 2;

    #[EnumAttribute(color: '#F44336', isFinal: true)]
    const Completed = 3;

    // 保留Ben Sampo Enum的本地化描述
    public static function descriptions(): array
    {
        return [
            self::Initial => __('初始状态'),
            self::Processing => __('处理中'),
            self::Completed => __('已完成'),
        ];
    }
}

4. 调用方式测试

现在可以按需求自由获取属性:

// 通过枚举值获取color
$initialColor = Status::getColor(1); // 返回 #4CAF50

// 通过枚举实例获取color
$processingColor = Status::Processing->getColor(); // 返回 #FFC107

// 判断是否为最终状态
$isCompletedFinal = Status::Completed->isFinal(); // 返回 true

// 获取所有带自定义属性的枚举实例
$allStatus = Status::getCustomInstances();
// 返回示例结构:
// [
//     ['value' => 1, 'name' => 'Initial', 'description' => '初始状态', 'color' => '#4CAF50', 'isFinal' => false],
//     ['value' => 2, 'name' => 'Processing', 'description' => '处理中', 'color' => '#FFC107', 'isFinal' => false],
//     ['value' => 3, 'name' => 'Completed', 'description' => '已完成', 'color' => '#F44336', 'isFinal' => true],
// ]

内容的提问来源于stack exchange,提问作者ERasekh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 19:17:26