苏莱曼诺夫/laravel-enum-helper

简单的、有偏见的、框架无关的 PHP 8.1 枚举辅助器,适用于 Laravel

v2.0.0 2024-04-14 02:49 UTC

This package is auto-updated.

Last update: 2024-09-14 03:35:58 UTC


README

Latest Version on Packagist Pest Tests number GitHub Tests Action Status GitHub Code Style Action Status Total Downloads

这是基于 Laravel 框架的 suleymanozev/enum-helper 包的扩展。该包包含一个 LaravelEnumHelper 特性,它扩展了 EnumInvokableEnumFromsEnumNamesEnumValuesEnumEqualityEnumDescription,并添加了动态方法来返回翻译或“属性”方法和相关辅助方法。

您可以将它视为一个 EnumDescription 特性,但它是完全动态的。

因此,您可以定义一个自定义的 method() 并获得以下函数:[method]s()[method]sByName()[method]sByValue()。例如,使用 color() 您可以获得 colors()colorsByName()colorsByValue() 方法。

酷的地方在于您还可以避免编写方法,只编写翻译。例如,您可以通过仅在 enums.php 中写入翻译来定义属性 excerpt,并获取 excerpt()excerpts()excerptsByName()excerptsByValue() 方法。

该包使用 Laravel Pluralizer 组件 来获取要调用的单数方法或进行翻译。

enum-helper 基础包摘要

您可以在他的 仓库 中看到 suleymanozev/enum-helper 的详细信息,这是一个摘要

  • 可调用案例:通过静态调用枚举来获取枚举的值
  • 通过名称或值构建枚举:对所有枚举使用 from()tryFrom()fromName()tryFromName()
  • 枚举检查isPure()isBacked()has()hasName()hasValue() 方法
  • 枚举等价性is()isNot()in()notIn() 方法
  • 名称:列出案例名称的方法(names()namesByValue()
  • :列出案例值的方法(values()valuesByName()
  • 唯一 ID:从实例或标识符获取唯一标识符(uniqueId()fromUniqueId()
  • 描述 & 翻译:向枚举添加描述(可选翻译)(description()descriptions()descriptionsByName()descriptionsByValue()

安装

需要 Laravel 8 或更高版本和 PHP 8.1+。

composer require suleymanozev/laravel-enum-helper

使用方法

您可以通过使用 LaravelEnumHelper 特性简单地使用此功能。

use Suleymanozev\LaravelEnumHelper\LaravelEnumHelper;

// Pure enum 
enum Status
{
    use LaravelEnumHelper;

    case PENDING;
    case ACCEPTED;
    case DISCARDED;
    case NO_RESPONSE;

    public function color(): string
    {
        return match ($this) {
            self::PENDING => '#000000',
            self::ACCEPTED => '#0000FF',
            self::DISCARDED => '#FF0000',
            self::NO_RESPONSE => '#FFFFFF',
        };
    }
}

// BackedEnum
enum StatusString
{   
    use LaravelEnumHelper;

    case PENDING = 'P';
    case ACCEPTED = 'A';
    case DISCARDED = 'D';
    case NO_RESPONSE = 'N';
    
    // or public function color(?string $lang = null): string
    public function color(): string
    {
        ...
    }

之后,您可以定义一个自定义的“属性”方法,例如 color()color(?string $lang = null),或者定义翻译。

翻译

使用此特性有两种管理翻译字符串的方法。

使用短键

语言字符串可以存储在 lang 目录中的 enums.php 文件中。在此目录中,可能存在每个应用程序支持的每种语言的子目录。

/lang
    /en
        enums.php
    /it
        enums.php

所有语言文件都返回一个键控字符串数组。该数组有 3 个级别

  • 第一级键:枚举的完整类名
  • 第二级键:要翻译的属性名称
  • 第三级键:枚举情况的名字/值。

默认属性是 description,所以如果您只使用该属性,则可以使用2级数组。

// /lang/it/enums.php

return [
    // If you need to translate just the description property
    Status::class => [
        Status::PENDING() => 'In attesa', // using invokable trait functionality
        'ACCEPTED' => 'Accettato', // using the name of pure enum case
        'DISCARDED' => 'Rifiutato',
        'NO_RESPONSE' => 'Nessuna Risposta',
    ],
     // If you need to translate multiple properties (e.g. description, excerpt)
    StatusString::class => [
        'description' => [ // using invokable trait functionality
            StatusString::PENDING() => 'In attesa',
            StatusString::ACCEPTED() => 'Accettato',
            ...
        ],
        'excerpt' => [ // using the value of BackedEnum case
            "P" => 'In attesa',
            "A" => 'Accettato',
    ...

使用翻译字符串作为键

语言字符串存储在lang目录下的JSON文件中(例如 lang/it.json)。在这个例子中,description 属性被翻译了。

{
  "enums.Namespace\\StatusString.description.P": "In attesa",
  "...":"..."
}

但如果你想使用这种方式,你可以在枚举类上简单地定义一个方法,如这个 description 方法。

public function description(?string $lang = null): string
{
    return match ($this) {
        self::PENDING => __('Await decision', $lang),
        self::ACCEPTED => __('Recognized valid', $lang),
        self::DISCARDED => __('No longer useful', $lang),
        self::NO_RESPONSE => __('No response', $lang),
    };

[property]() 方法

这个动态方法尝试在枚举上解析 property() 方法。
如果该方法不存在,尝试使用框架的翻译函数 __("enums.Namespace\EnumClass.property.CASE_NAME") 翻译实例值。
因为默认属性是 description,如果该属性没有翻译,将回退到将情况名称人性化。对于其他属性,如果翻译不存在,包会抛出 TranslationMissing 异常。

静态 [property]s() 方法

这个动态方法获取枚举 property() 返回的案例列表。该方法的名称是属性的复数形式,所以如果你使用 property,它将是 properties()

StatusString::descriptions(); // ['Await decision','Recognized valid','No longer useful','No response']
StatusString::colors(); // ['#000000','#0000FF','#FF0000','#FFFFFF']
// Subset
StatusString::descriptions([StatusString::ACCEPTED, StatusString::NO_RESPONSE]); // ['Recognized valid','No response']
StatusString::colors([StatusString::ACCEPTED, StatusString::NO_RESPONSE]); // ['#0000FF','#FFFFFF']
// Forcing language
Status::descriptions(null, 'it'); // 🇮🇹 ['In attesa','Accettato','Rifiutato','Nessuna Risposta']
StatusString::colors(null, 'it'); // ['#000000','#0000FF','#FF0000','#FFFFFF']
// Subset and language 
Status::descriptions([Status::NO_RESPONSE, Status::DISCARDED], 'it'); // 🇮🇹 ['Nessuna Risposta', 'Rifiutato']
StatusString::colors([StatusString::ACCEPTED, StatusString::NO_RESPONSE], 'it'); // ['#0000FF','#FFFFFF']

静态 [property]sByName() 方法

这个动态方法返回一个关联数组 [case name => property() result]。该方法的名称是属性的复数形式,所以如果你使用 property,它将是 propertiesByName()

StatusString::descriptionsByName(); // ['PENDING' => 'Await decision', 'ACCEPTED' => 'Recognized valid',...
StatusString::colorsByName(); // ['PENDING' => '#000000','ACCEPTED' => '#0000FF',...
Status::descriptionsByName(); // ['PENDING' => 'Await decision', 'ACCEPTED' => 'Recognized valid',...
// Subset
StatusString::descriptionsByName([StatusString::DISCARDED, StatusString::ACCEPTED]); // ['DISCARDED' => 'No longer useful', 'ACCEPTED' => 'Recognized valid']
Status::descriptionsByName([[Status::PENDING, Status::DISCARDED]); // ['PENDING' => 'Await decision', 'DISCARDED' => 'No longer useful']
// Forcing language
StatusString::descriptionsByName(null, 'it'); // 🇮🇹 ['P' => 'In attesa','A' => 'Accettato',...
// Subset and language 
Status::descriptionsByName([Status::DISCARDED, Status::NO_RESPONSE], 'it'); // 🇮🇹 ['DISCARDED' => 'Rifiutato','NO_RESPONSE' => 'Nessuna Risposta',...

静态 [property]sByValue() 方法

这个动态方法返回一个关联数组 [case value => property() result],在 BackedEnum 上,[case name => property() result] 否则。该方法的名称是属性的复数形式,所以如果你使用 property,它将是 propertiesByValue()

Status::descriptionsByValue(); // ['PENDING' => 'Await decision', 'ACCEPTED' => 'Recognized valid',...
StatusString::descriptionsByValue(); // ['P' => 'Await decision', 'A' => 'Recognized valid',...
StatusString::colorsByValue(); // ['P' => '#000000','A' => '#0000FF',...
// Subset
Status::descriptionsByValue([Status::PENDING, Status::DISCARDED]); // ['PENDING' => 'Await decision', 'DISCARDED' => 'No longer useful']
StatusString::descriptionsByValue([StatusString::DISCARDED, StatusString::ACCEPTED]); // ['D' => 'No longer useful', 'A' => 'Recognized valid']
StatusString::colorsByValue([[Status::PENDING, Status::DISCARDED]); // ['P' => '#000000', 'D' => '#FF0000']
// Forcing language
StatusString::descriptionsByValue(null, 'it'); // 🇮🇹 ['P' => 'In attesa','A' => 'Accettato',...
// Subset and language 
Status::descriptionsByValue([StatusString::DISCARDED, StatusString::NO_RESPONSE], 'it'); // 🇮🇹 ['DISCARDED' => 'Rifiutato','NO_RESPONSE' => 'Nessuna Risposta',...

特别感谢

  • Datomatic 团队