Skip to content

Commit

Permalink
update: detect implicit and explicit default formats for a given object
Browse files Browse the repository at this point in the history
  • Loading branch information
Jasonej committed Nov 4, 2021
1 parent b987074 commit 61dfc62
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 2 deletions.
17 changes: 15 additions & 2 deletions src/Formatting/FormatManager.php
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

class FormatManager
{
protected ?FormatDefinition $default;
protected Collection $formats;
protected ReflectionObject $reflection;
protected object $subject;
Expand All @@ -21,12 +22,24 @@ public function __construct(object $subject)
{
$this->reflection = new ReflectionObject($subject);
$this->subject = $subject;
$this->formats = (new Collection($this->reflection->getMethods()))

$definitions = (new Collection($this->reflection->getMethods()))
->filter(fn(ReflectionMethod $method) => !empty($method->getAttributes(Format::class)))
->mapInto(FormatDefinition::class)
->mapInto(FormatDefinition::class);

$this->formats = $definitions
->tap(Closure::fromCallable([$this, 'preventFormatNameCollisions']))
->flatMap(fn(FormatDefinition $definition) => $definition->names()
->mapWithKeys(fn(string $name) => [$name => $definition]));

$this->default = $definitions->filter(fn(FormatDefinition $definition) => $definition->isExplicitlyDefault())
->when($definitions->containsOneItem(), fn(Collection $defaults) => $defaults->push($definitions->first()))
->first();
}

public function default(): FormatDefinition
{
return $this->default;
}

public function formats(): Collection
Expand Down
33 changes: 33 additions & 0 deletions tests/Unit/Formatting/FormatManagerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,41 @@ public function test_format_name_collisions_are_prevented(object $subject): void
new FormatManager($subject);
}

/** @dataProvider defaultFormatProvider */
public function test_default_format_is_detected_properly(object $subject, string $expectedFormat): void
{
# Act
$manager = new FormatManager($subject);

# Assert
$this->assertSame($expectedFormat, $manager->default()->name());
}

# region Data Providers

public function defaultFormatProvider(): array
{
return [
'implicit default' => [
'object' => new class {
#[Format]
public function foo() {}
},
'foo',
],
'explicit default' => [
'object' => new class {
#[Format]
public function bar() {}

#[IsDefault, Format]
public function foo() {}
},
'foo',
],
];
}

public function formatNameCollisionProvider(): array
{
return [
Expand Down

0 comments on commit 61dfc62

Please sign in to comment.