laravel 如何使用多态性返回多个结果并同时使用多个行为

ulydmbyx  于 2022-12-30  发布在  其他
关注(0)|答案(1)|浏览(266)

我正在使用Laravel 9,我的请求可以包含:

  • 参数名为SEASON,值可以是array或空,因此SEASON参数可以是array,也可以是null
  • 名为EXPIRY的参数可以是array,也可以是null

我有两个类,一个用于SEASON特性,另一个用于EXPIRY,它们都是从Repository扩展而来的,并且都有一个名为execute的方法,该方法返回一个数组

abstract class Repository 
{
     abstract public function execute(): array;
}

class Expiry extends Repository
{
   public function execute()
   {
       return ['The Request contain Expiry Parameter, and seasonal behaviours is done'];
   }
}

class Season extends Repository
{
   public function execute()
   {
       return ['The Request contain Season Parameter, and expiry behaviours is done'];
   }
}

如果我的请求包含SEASON,我想调用Season类的execute方法,或者如果我的请求包含Expiry,我想调用expiry的execute方法。或者调用两者,并将execute的execute返回合并到一个数组中,这样我就可以将其作为结果。

['The Request contain Expiry Parameter, and seasonal behaviours is done', 'The Request contain Expiry Parameter, and expiry behaviours is done']

这就是我在控制器中尝试的:

public function bootstrap($data)
{
    $parseTopics = Helper::parseTopicsRequest();

    $basicProgram = new BasicProgramRepository();
    $seasonalProgram = new SeasonalProgramRepository($parseTopics['SEASONAL']);

    $object = count($parseTopics['SEASONAL']) ? $seasonalProgram : $basicProgram;
    // Polymorphism
    return $object->execute();
}

问题一:我不确定我是否应该用这种方式或类似的东西来解决我的需求:

$employe = new Program(new BasicProgramRepository());

预期结果:预期的结果取决于我是否有季节参数和有效期。我想实现的是使用不同的行为(执行方法)

1mrurvl1

1mrurvl11#

如果您想实现多态性方法,最好创建存储库或仅用于管理逻辑东西。
这是样品。

class SampleRepository
{
    /**
     * repository instance value
     *
     * @var string[] | null
     */
    private $sampleArray; // maybe here is SEASON or EXPIRY or null

    /**
     * constructor
     *
     * @param string[] | null $sampleArray
     */
    public function __construct($sampleArray)
    {
        $this->sampleArray = $sampleArray;
    }

    /**
     * execute like class interface role
     *
     * @return array
     */
    public function execute()
    {
        return (!$this->sampleArray) ? [] : $this->getResult();
    }

    /**
     * get result
     *
     * @return array
     */
    private function getResult()
    {
        // maybe pattern will be better to manage another class or trait.
        $pattern = [
            "SEASON" => new Season(),
            "EXPIRY" => new Expiry()
        ];
        return collect($this->sampleArray)->map(function($itemKey){
            $requestClass = data_get($pattern,$itemKey);
            if (!$requestClass){ // here is space you don't expect class or canIt find correct class
                return ["something wrong"];
            }
            return $requestClass->execute();
        })->flatten();
    }
}

你可以这样打电话。

$sampleRepository  = new SampleRepository($sampleValue); // expect string[] or null like ["SEASON"],["SEASON","EXPIRY"],null
    $result = $sampleRepository->execute(); // [string] or [string,string] or []

这种方法只是你的参数是安全值。2如果你的返回结果是几乎相同的季节类和到期类,这将是更好的管理特点。3(即$模式的样本代码)
尝尝。
我看了评论,所以下面..
例如,它更喜欢只获取getResult()的结果,因此,一些模式和那么多逻辑不应该写在getResult()上;
如果您使用trait,这是sample。首先,您需要创建管理行为类。
Behavior.php

<?php 
namespace App\Repositories;

class Behavior
{
    use Behavior\BehaviorTrait;
    // if you need to add another pattern, you can add trait here.
}

然后,你需要在同一层创建行为目录。2你移动那个目录,你就创建了这样的trait文件。

<?php

namespace App\Repositories\Behavior;

trait BehaviorTrait
{
    public static function findAccessibleClass(string $itemKey)
    {
      return data_get([
        "SEASON" => new Season(),
        "EXPIRY" => new Expiry()
      ],$itemKey);
    }
}

findAccessibleClass()方法负责查找正确的类。
然后,你像这样调用这个方法

private function getResult()
    {
        return collect($this->sampleArray)->map(function($itemKey){
            $requestClass = Behavior::findAccessibleClass($itemKey); // fix here.
            if (!$requestClass){ // here is space you don't expect class or canIt find correct class
                return ["something wrong"];
            }
            return $requestClass->execute();
        })->flatten();
    }

如果getResult()中代码太多,最好将负责的代码分开。
要创建行为特征,getResult不需要负责行为逻辑。它将很容易测试或修复简而言之。
希望一切顺利。

相关问题