我正在研究使用Doctrine2和我的Zend Framework设置。我非常喜欢datamapper模式,主要是因为它将我的域模型与我的数据库分开。
我的问题是在控制器中使用Doctrine和DQL的最佳做法是什么?
控制器使用Doctrine DQL / EntityManager直接用于 保存/加载我的域模型?
在...中创建自己的类 datamapper模式 保存/加载我的域模型,以及 然后在内部使用Doctrine 我自己的课程?
专业人士。对于#1来说当然是我不需要创建自己的数据映射模型,但是再次使用#2我可以在以后替换Doctrine(理论上)
你会做什么?
答案 0 :(得分:3)
关于你的抽象问题,我会说这实际上取决于这个项目的生命周期以及你的代码需要多么可移植。如果它是一个需要最少维护的一次性网站,它可能会节省您一些时间来放弃额外的抽象层,只需在控制器中编写Doctrine代码。但是,如果您计划重用此代码,将其移动到不同的平台,或者将其维护很长一段时间,我会花时间添加该抽象,因为它会为您提供更大的灵活性。
如果您仍在研究框架,请查看Kohana。它基本上是为PHP5编写的CodeIgniter的轻量级重写。
答案 1 :(得分:2)
我接受pix0r的建议。如果它是一个具有潜在长寿命的大型项目并且可能有很多开发人员,那么额外的抽象是值得的。这几乎也是我遵循的准则,无论是在带有doctrine2的php中还是带有jpa的java中(因为doctrine2非常类似于jpa)。
如果你想要额外的抽象,doctrine2已经有了使用存储库的可能性(存储库非常相似甚至等于DAO,可能更关注业务术语和逻辑)。有一个基类Doctrine \ ORM \ EntityRepository。每当您调用EntityManager#getRepository($ entityName)时,Doctrine将查看您是否为该实体配置了自定义存储库类。如果没有,它将实例化Doctrine \ ORM \ EntityRepository。您可以为元数据中的实体配置自定义存储库类,例如在docblock注释中:@ Entity(...,repositoryClass =“My \ Project \ Domain \ UserRepository”)。这样的自定义类应该从EntityRepository继承并适当地调用父构造函数。基类已经包含一些基本的find *功能。
罗马
答案 2 :(得分:1)
在您的研究中也考虑Symfony。它会让你使用ORM(推进/学说),或者你可以编写自己的数据模型。您还可以绕过数据关系并在需要时使用直接SQL。
为了解决您对1或2的担忧,我个人会在项目中使用ORM并在需要时绕过它。更好的是,使用symfony,如果你需要,你可以在学说和推进或你自己的课程之间切换。
Pros:
1) faster development. easier to maintain. generally more secure and consistent. easy to switch databases should you ever need to.(from MySQL to Oracle, etc).
2) Faster runtime. Less dependency.
Cons:
1) Slower runtime and larger memory footprint. Dependency on other projects.
2) (reverse the pros for #1)
答案 3 :(得分:1)
我的想法类似于pix0r的回应。但是,如果您的项目足够小,您可以直接在控制器中使用EntityManager / DQL,那么Doctrine 2可能对您的项目来说太过分了,也许您应该考虑使用更小/更简单的系统。
答案 4 :(得分:0)
根据我的经验,在控制器中编写持久层逻辑总是让我以技术债务的形式困扰着我。这个看似很小的决定现在可能会导致未来即使在小型项目上也不可避免且可能进行大规模的重新分解。理想情况下,我们希望能够复制和粘贴使用适当模型重新配置的极薄控制器,以防止我们不得不一遍又一遍地重复创建CRUD控制器,但也允许自定义这些控制器。在我看来,这只能通过遵守纪律并尽可能地将持久层从应用程序中抽象出来来实现。由于特别是在洁净室控制器上这样做的开销很小,我看不出任何有理由建议你不要这样做。