Skip to content

Commit

Permalink
Add support for PHP 8 enums (#136)
Browse files Browse the repository at this point in the history
* Add support for PHP 8 enums

* Use `headline` for BC reasons
  • Loading branch information
inxilpro authored Sep 18, 2024
1 parent 299aa6c commit 49627f7
Show file tree
Hide file tree
Showing 5 changed files with 55 additions and 9 deletions.
9 changes: 9 additions & 0 deletions src/Elements/Concerns/HasValue.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@

namespace Galahad\Aire\Elements\Concerns;

use BackedEnum;
use UnitEnum;

trait HasValue
{
/**
Expand All @@ -12,6 +15,12 @@ trait HasValue
*/
public function defaultValue($value): self
{
if ($value instanceof BackedEnum) {
$value = $value->value;
} elseif ($value instanceof UnitEnum) {
$value = $value->name;
}

$this->attributes->setDefault('value', $value);

return $this;
Expand Down
27 changes: 22 additions & 5 deletions src/Support/OptionsCollection.php
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,11 @@

namespace Galahad\Aire\Support;

use BackedEnum;
use Galahad\Aire\Contracts\SelectableEntity;
use Illuminate\Support\Collection;
use Illuminate\Support\Str;
use UnitEnum;

class OptionsCollection extends Collection
{
Expand All @@ -21,11 +24,25 @@ public function getOptions(): array

protected function getArrayableItems($items)
{
if (is_string($items) && is_subclass_of($items, '\\BenSampo\\Enum\\Enum')) {
if (method_exists($items, 'asSelectArray')) {
$items = forward_static_call([$items, 'asSelectArray']);
} elseif (method_exists($items, 'toSelectArray')) {
$items = forward_static_call([$items, 'toSelectArray']);
if (is_string($items)) {
if (is_subclass_of($items, '\\BenSampo\\Enum\\Enum')) {
if (method_exists($items, 'asSelectArray')) {
$items = forward_static_call([$items, 'asSelectArray']);
} elseif (method_exists($items, 'toSelectArray')) {
$items = forward_static_call([$items, 'toSelectArray']);
}
} elseif (is_subclass_of($items, UnitEnum::class)) {
$items = collect($items::cases())->mapWithKeys(function(UnitEnum $case) {
$label = method_exists($case, 'description')
? $case->description()
: Str::headline($case->name);

if ($case instanceof BackedEnum) {
return [$case->value => $label];
}

return [$case->name => $label];
});
}
}

Expand Down
6 changes: 4 additions & 2 deletions tests/Unit/DataBindingTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -105,13 +105,15 @@ public function test_backed_enums_are_bound_propery(): void

require_once __DIR__.'/enum-stubs.php';

$model = new EnumModelStub(['name' => 'Chris']);
$model = new EnumModelStub(['name' => 'inxilpro']);

$this->assertEquals(Names::ChrisMorrell, $model->name);

$this->aire()->form()->bind($model);

$input = $this->aire()->input('name');

$this->assertSelectorAttribute($input, 'input', 'value', 'Chris');
$this->assertSelectorAttribute($input, 'input', 'value', 'inxilpro');
}

public function test_bound_data_with_square_brackets_is_supported(): void
Expand Down
18 changes: 18 additions & 0 deletions tests/Unit/SelectTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,24 @@ public function test_an_enum_class_name_will_be_converted_to_a_selectable_array(
$this->assertSelectorTextEquals($html, 'option[value="2"]', 'Ann Patchett');
$this->assertSelectorTextEquals($html, 'option[selected]', 'Ann Patchett');
}

public function test_a_native_enum_is_supported(): void
{
if (version_compare(PHP_VERSION, '8.1.0', '<')) {
$this->markTestSkipped('Only applies to PHP 8.1 and higher.');
}

require_once __DIR__.'/enum-stubs.php';

$html = $this->aire()
->select(Names::class)
->defaultValue(Names::BogdanKharchenko)
->render();

$this->assertSelectorTextEquals($html, 'option[value="inxilpro"]', 'Chris Morrell');
$this->assertSelectorTextEquals($html, 'option[value="boggybot"]', 'Bogdan Kharchenko');
$this->assertSelectorTextEquals($html, 'option[selected]', 'Bogdan Kharchenko');
}
}

if (class_exists('BenSampo\Enum\Enum')) {
Expand Down
4 changes: 2 additions & 2 deletions tests/Unit/enum-stubs.php
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ class EnumModelStub extends Model

enum Names: string
{
case CM = 'Chris';
case ChrisMorrell = 'inxilpro';

case TE = 'Tim';
case BogdanKharchenko = 'boggybot';
}

0 comments on commit 49627f7

Please sign in to comment.