php Symfony:在控制器中示例化一个实体可以吗?

q35jwt9p  于 2023-02-28  发布在  PHP
关注(0)|答案(1)|浏览(151)

SOLID的原则之一是依赖反转。据我所知,这意味着我不应该示例化代码中的其他类并将它们传递给构造函数。我写这个的时候是否违反了这个原则?

UserController extends AbstractController
{
    public function create(Request $request): Response
    {
        $user = new User();
        $form = $this->createForm(RegistrationType::class, $user);

        $form->handleRequest($request);
        if ($form->isSubmitted() && $form->isValid()) {
            $this->entityManager->persist($user);
            $this->entityManager->flush();

            return $this->redirectToRoute('home');
        }

        return $this->render('user/register.html.twig');
    }
}

在上面的例子中,我使用了“new User()"。

rekjcdws

rekjcdws1#

在我看来,你并没有因为new User()而违反SOLID原则,而是因为你在调用实体管理器。我宁愿使用模型层。在你的情况下,我的模型是UserService。你的控制器现在依赖于它,如果你在这个用例中添加新任务,你(或你的团队)将在你的控制器中编写它,你不应该这样做,我也不喜欢这样。
所以我更愿意使用以下代码:

#[Route('/register', name: 'app_register')]
    public function register(Request $request, UserService $userService): Response 
    {        
        $user = new User();
        $form = $this->createForm(RegistrationFormType::class, $user);
        $form->handleRequest($request);

        if ($form->isSubmitted() && $form->isValid()) {
            try {
                $message = $userService->createUser($user);
                $this->addFlash('success', $message);
            } catch (UserServiceException $e) {
                $this->addFlash($e->getLevel(), $e->getReason());
            }

            return $this->redirectToRoute('home');
        }

        return $this->render('registration/register.html.twig', [
            'registrationForm' => $form->createView(),
        ]);

用户创建过程中的所有逻辑步骤都在UserService中编码(持久化、激活电子邮件、管理员日志等)
我的控制器只需要知道它是否工作。然后它完成flash消息。如果它是一个异常,它捕捉一个人的消息(原因),并转发给flash消息。
如果你的实体有点复杂(让我们使用一辆有发动机和轮子的汽车),你可以使用一个CarModel,它只包含带有Assert#[Assert\NotBlank()的私有属性(像任何简单实体一样)和公共getter和setter。
您在控制器new CarModel()中创建模型,一旦表单提交并生效,控制器就会将模型转发到CarServiceCarService将从模型中创建复杂的Car实体、Motor实体和四个Wheels实体,并将它们持久化。
总结一下,我的控制器:

  • 直接创建简单实体,或者用new MyEntity()或'new MyModel()为复杂用例创建模型;
  • 使用所述请求来创建表单和完成实体;
  • 使用该请求来了解已提交的表单是否有效;
  • 调用模型层(UserService)执行用例;
  • 基于结果完成所述短讯,
  • 完成并呈现视图或重定向用户。

相关问题