generated from spatie/package-skeleton-laravel
-
-
Notifications
You must be signed in to change notification settings - Fork 223
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
First changes so that Laravel Data and livewire work better together
- Loading branch information
1 parent
4135f77
commit a3d6f75
Showing
4 changed files
with
151 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
<?php | ||
|
||
namespace Spatie\LaravelData\Support\Lazy; | ||
|
||
use Exception; | ||
use Spatie\LaravelData\Lazy; | ||
|
||
class LivewireLostLazy extends Lazy | ||
{ | ||
public function __construct( | ||
public string $dataClass, | ||
public string $propertyName | ||
) { | ||
} | ||
|
||
public function resolve(): mixed | ||
{ | ||
return throw new Exception("Lazy property `{$this->dataClass}::{$this->propertyName}` was lost when the data object was transformed to be used by Livewire. You can include the property and then the correct value will be set when creating the data object from Livewire again."); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,119 @@ | ||
<?php | ||
|
||
namespace Spatie\LaravelData\Support\Livewire; | ||
|
||
use Livewire\Mechanisms\HandleComponents\ComponentContext; | ||
use Livewire\Mechanisms\HandleComponents\Synthesizers\Synth; | ||
use Spatie\LaravelData\Contracts\BaseData; | ||
use Spatie\LaravelData\Contracts\TransformableData; | ||
use Spatie\LaravelData\Support\DataConfig; | ||
use Spatie\LaravelData\Support\Lazy\LivewireLostLazy; | ||
|
||
class LivewireDataSynth extends Synth | ||
{ | ||
// TODO: | ||
// | ||
// Think about Lazy, we can always send them down? | ||
// Or only conditional lazy which are true -> probably a better default | ||
// What if we want to create a new data object and don't have the lazyvalue | ||
// -> we could create a new LiveWireMissingLazy object, which we then use as the lazy value | ||
// -> when resolving it would throw an error saying the value was lost in LiveWire | ||
// | ||
// Problem with computed properties should be sorted out | ||
// | ||
// DataCollections synth from the PR | ||
// | ||
// Do we want livewire as an dependency? | ||
// | ||
// Update docs | ||
// | ||
// Can we test this? | ||
// | ||
// Mapping property names, should we do this? | ||
|
||
protected DataConfig $dataConfig; | ||
|
||
public static string $key = 'laravel-data-object'; | ||
|
||
public function __construct(ComponentContext $context, $path) | ||
{ | ||
$this->dataConfig = app(DataConfig::class); | ||
|
||
parent::__construct($context, $path); | ||
} | ||
|
||
public static function match($target) | ||
{ | ||
return $target instanceof BaseData && $target instanceof TransformableData; | ||
} | ||
|
||
public function get(&$target, $key): BaseData | ||
{ | ||
return $target->{$key}; | ||
} | ||
|
||
public function set(&$target, $key, $value): void | ||
{ | ||
$target->{$key} = $value; | ||
} | ||
|
||
/** | ||
* @param BaseData&TransformableData $target | ||
* @param callable(mixed):mixed $dehydrateChild | ||
* | ||
* @return array | ||
*/ | ||
public function dehydrate( | ||
BaseData&TransformableData $target, | ||
callable $dehydrateChild | ||
): array { | ||
$morph = $this->dataConfig->morphMap->getDataClassAlias($target::class) ?? $target::class; | ||
|
||
$payload = $target->all(); | ||
|
||
ray($payload); | ||
|
||
foreach ($payload as $key => $value) { | ||
$payload[$key] = $dehydrateChild($key, $value); | ||
Check failure on line 78 in src/Support/Livewire/LivewireDataSynth.php
|
||
} | ||
|
||
return [ | ||
$payload, | ||
['morph' => $morph], | ||
]; | ||
} | ||
|
||
/** | ||
* @param mixed $value | ||
* @param array $meta | ||
* @param callable(mixed):mixed $hydrateChild | ||
* | ||
* @return BaseData | ||
*/ | ||
public function hydrate( | ||
Check failure on line 94 in src/Support/Livewire/LivewireDataSynth.php
|
||
array $value, | ||
array $meta, | ||
callable $hydrateChild | ||
): BaseData { | ||
$morph = $meta['morph']; | ||
|
||
$dataClass = $this->dataConfig->morphMap->getMorphedDataClass($morph) ?? $morph; | ||
|
||
$payload = []; | ||
|
||
foreach ($this->dataConfig->getDataClass($dataClass)->properties as $name => $property) { | ||
if (array_key_exists($name, $value) === false && $property->type->lazyType) { | ||
$payload[$name] = new LivewireLostLazy($dataClass, $name); | ||
|
||
continue; | ||
} | ||
|
||
$payload[$name] = $hydrateChild($name, $value[$name]); | ||
Check failure on line 112 in src/Support/Livewire/LivewireDataSynth.php
|
||
} | ||
|
||
return $dataClass::factory() | ||
->ignoreMagicalMethod('fromLivewire') | ||
->from($payload); | ||
} | ||
} |