If you've been using PHP 8.1, chances are you already know about this new feature called [Enumerations or "Enums"](https://www.php.net/manual/en/language.enumerations.php). If not, then I suggest that you check it out as it is, in my opinion, one of the most powerful new feature PHP has added to the language. It might solve a lot of your use-cases as it did for me.
As an example, let's say that we have a backed enum class that holds the cases for the status of the ticket in our app:
```
enum TicketStatus : string
{
case Draft = 'draft';
case Open = 'open';
case Ongoing = 'ongoing';
case Closed = 'closed';
}
```
One cool thing about enumerations is that you can call a `cases()` method on it to list all the cases like so:
```
$result = TicketStatus::cases();
dd($result);
[
TicketStatus {
+name: "Draft",
+value: "draft",
},
TicketStatus {
+name: "Open",
+value: "open",
},
TicketStatus {
+name: "Ongoing",
+value: "ongoing",
},
TicketStatus {
+name: "Closed",
+value: "closed",
},
]
```
As you can see, each element in the result is an instance of `TicketStatus` class with properties `name` and `value`. So it begs the question, what if I just want to get just the names or just the values? Unfortunately, this isn't something that comes out of the box and calling `TicketStatus::names()` or `TicketStatus::values()` would cause an error.
One solution is to use `Illuminate\Support\Collection` class.
```
$names = collect(TicketStatus::cases())->pluck('name');
dd($names);
Illuminate\Support\Collection {
all: [
"Draft",
"Open",
"Ongoing",
"Closed",
],
}
$values = collect(TicketStatus::cases())->pluck('values');
dd($values);
Illuminate\Support\Collection {
all: [
"draft",
"open",
"ongoing",
"closed",
],
}
```
Okay, now we're talking! Let's refactor that as methods in our enum class, like so:
```
enum TicketStatus : string
{
case Draft = 'draft';
case Open = 'open';
case Ongoing = 'ongoing';
case Closed = 'closed';
public static function names()
{
return collect(self::cases())->pluck('name');
}
public static function values()
{
return collect(self::cases())->pluck('value');
}
}
```
Now, calling `TicketStatus::names()` or `TicketStatus::values()` would definitely work!
But wait, there's more! Since we are already using `Collection` class here, we might as well see to it that we are able to take advantage of the full features it can offer. How about refactoring to have something like `TicketStatus::collection()` ? Let's do it!
```
enum TicketStatus : string
{
case Draft = 'draft';
case Open = 'open';
case Ongoing = 'ongoing';
case Closed = 'closed';
public static function names()
{
return self::collection()->pluck('name');
}
public static function values()
{
return self::collection()->pluck('value');
}
public static function collection()
{
return collect(self::cases());
}
}
```
Cool! Now we can take full advantage of collection features within our enum. In the future we can do something like `TicketStatus::collection()->map(...)` or `TicketStatus::collection()->each(...)` should we need to. It is now up to you if you want to add more convenience methods or just chain from the `collection()` method.
Last thing that we would want to do is to be able to share these convenient functions with other enum classes. So let's wrap it within a trait...
```
trait Collectible
{
public static function names()
{
return self::collection()->pluck('name');
}
public static function values()
{
return self::collection()->pluck('value');
}
public static function collection()
{
return collect(self::cases());
}
}
```
And just use the trait within your enum classes like so
```
enum TicketStatus : string
{
use Collectible;
case Draft = 'draft';
case Open = 'open';
case Ongoing = 'ongoing';
case Closed = 'closed';
}
```
And there you have it! You have supercharged your backed enum classes using collection. Hope you enjoy!