在 CakePHP 中共享应用程序逻辑的正确位置是什么?

发布于 2024-09-05 18:21:28 字数 810 浏览 4 评论 0原文

我想这个问题的简单答案就是一个组件

虽然我同意,但我觉得为如此具体的东西编写一个组件很奇怪。

例如,假设我有一个用户表。当创建用户时,它应该形成事件的连锁反应,在数据库中启动与用户相关的不同类型的数据。我认为最好避免从不同的控制器直接操作数据库,而是将所有这些整齐地打包在一个方法中。然而,由于某些逻辑需要单独访问,我真的不能在一个方法中拥有整个包。相反,我认为将其分解为更小的部分是合乎逻辑的(例如 $userModelOrController->createNew()$candyStorageModelOrController->createNew())与各自的数据库表进行交互。

现在,如果将逻辑放入模型中,它会很好地工作,直到我需要使用其他模型。当然这是可能的,但是与在控制器中加载模型相比,它并不是那么简单。这就像蛋糕开发人员告诉我“当然,如果你想这样做是可以的,但我不会这样做”。

然后,如果将逻辑放入控制器,我可以通过 $this->loadModel() 轻松访问其他模型,但这让我回到了之前解释的情况,因为我需要链式反应可以无限地进行下去。从控制器访问其他控制器是可能的,但似乎没有任何直接的方法可以做到这一点,所以我猜我仍然没有做得正确。

通过使用组件,这个问题可以轻松解决,因为组件可供我想要的每个控制器使用。但就像我在一开始写的那样,专门为这个任务创建一个组件感觉很尴尬。对我来说,组件看起来更像是额外功能的包(如核心组件),而不是共享控制器特定逻辑的东西。

由于我对整个 MVC 事物很陌生,所以我可能完全误解了这个概念。再次,如果有人指出我正确的方向,我将不胜感激:)

I guess simple answer to the question would be a component.

Although I agree, I feel weird having to write a component for something so specific.

For example, let's say I have a table of users. When a user is created, it should form a chain reaction of events, initiating different kinds of data related to the user all around the database. I figured it would be best to avoid directly manipulating the database from different controllers and instead pack all that neatly in a method. However since some logic needs to be accesed separately, I really can't have the whole package in a single method. Instead I thought it would be logical to break it up to smaller pieces(like $userModelOrController->createNew() and $candyStorageModelOrController->createNew()) that only interact with their respective database table.

Now, if the logic is put to the model, it works great until I need to use other models. Of course it's possible, but when compared to loading models in a controller, it's not that simple. It's like a Cake developer telling me "Sure, it's possible if you want to do it that way but that's not how I would do it".

Then, if the logic is put to the controller, I can access other models really easy through $this->loadModel(), but that brings me back to the previously explained situation since I need to be able to continue the chain reaction indefinitely. Accessing other controllers from a controller is possible, but again there doesn't seem to be any direct way of doing so, so I'm guessing I'm still not doing it right.

By using a component this problem could be solved easily, since components are available to every controller I want. But like I wrote at the beginning, it feels awkward to create a component specifically for this one task. To me, components seem more like packages of extra functionality(like the core components) and not something to share controller-specific logic.

Since I'm new to this whole MVC thing, I could've completely misunderstood the concept. Once again, I would be thankful if someone pointed me to the right direction :)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

倾其所爱 2024-09-12 18:21:28

每当我面临如此困难的场景时,我都会盯着 CakePHP Events系统无限小时。

到目前为止,我已经设法以某种方式避免它(主要是由于缺乏勇气),但我认为它值得研究,因为它显然是为了在某种程度上跨越 MVC“墙”而设计的。

另一种可能的解决方案是 有限状态机行为,它允许您将逻辑更清晰地推向模型,并围绕它构建控制器+组件。此行为的唯一后备(恕我直言)是它不允许单个模型上有多个 state 字段。

对此类问题进行更真实的表述可能会产生更好的解决方案,因为我们中的许多人都走了这条路,这可能是一个有价值的例子。

Whenever I am faced with such difficult scenarios, I stare at CakePHP Events System for an infinite number of hours.

I've so far managed to avoid it somehow (mostly due to lack of courage), but I think it's worth looking into, since it is obviously designed to jump the MVC "walls" to some extent.

Another possible solution is the Finite State Machine behavior, which allows you to push the logic towards the Model more cleanly and build your Controller+Component around it. The only fallback (IMHO) of this Behavior is that it doesn't allow for multiple state fields on a single Model.

A more factual representation of such a problem might yield better solutions, since many of us went down this road and it could be a valuable example.

美人如玉 2024-09-12 18:21:28

cookbook 中明确指出:“组件是逻辑包,在控制器之间共享。如果您发现自己想要在控制器之间复制和粘贴内容,您可以考虑将某些功能包装在组件中。”

It is clearly stated in the cookbook: "Components are packages of logic that are shared between controllers. If you find yourself wanting to copy and paste things between controllers, you might consider wrapping some functionality in a component."

つ低調成傷 2024-09-12 18:21:28

这是一个明确的错误,CakePHP 不支持轻松地

  • 从模型访问另一个模型,
  • 从模型访问组件,
  • 任何模型
  • 从具有可从控制器和视图(组件和助手之间的东西)访问的功能的组件访问 ,或者从助手(或反之亦然)

我最终主要是向超类 AppController 添加功能。

It is deifinitley bugging that CakePHP does not support easly

  • accessing another Model from a Model
  • accessing a Component from a Model
  • accessing any Model from a Component
  • having a function accessible both from Controllers and Views (something between Components and Helpers), or accessing a Component from a Helper (or vica-versa)

I mostly ended up adding function to the superclass AppController.

晒暮凉 2024-09-12 18:21:28

如果您希望模型共享一些逻辑,您可以使用 AppModel。如果需要访问模型中的不同模型,可以使用App::import()ClassRegistry::init。现在,如果您希望逻辑仅适用于您选择的某些模型,您可以使用Behavior 或创建一个不同的 AppModel,其中只有您选择的模型才会继承。

You can use the AppModel if you want your models to share some logic. If you need to access different models in your model, you can use App::import() or ClassRegistry::init. Now if you want the logic to be available only to some models of your choice, you can use a Behavior or create a different AppModel where only your selected models will inherit.

慵挽 2024-09-12 18:21:28

也许更好的方法是在插件中实现这一点。插件允许您将 MVC 所有部分的全部功能封装到一个包中,可以通过插件的帮助程序、组件、行为将其拉入代码中的任何位置。这样,

  • 您可以将功能放在最合适的位置,
  • 逻辑与应用程序逻辑的其余部分分开,并且
  • 您可以根据需要启用/禁用此功能。

Probably a better way to implement this is within a plugin. Plugins allow you to encapsulate entire functionality across all parts of MVC into a package which can be pulled in anywhere in your code via the plugin's Helpers, Components, Behaviors. This way,

  • you can put the functionality where its most appropriate,
  • the logic is kept separate from the rest of your app logic and
  • you can enable/disable this functionality as needed.
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文