【问题标题】:Generate POCO classes in different project to the project with Entity Framework model使用实体框架模型在与项目不同的项目中生成 POCO 类
【发布时间】:2011-01-28 17:24:04
【问题描述】:

我正在尝试使用 VS2010 将存储库模式与 EF4 一起使用。

为此,我通过右键单击实体模型设计器并单击添加代码生成项来使用 POCO 代码生成。然后我选择 POCO 模板并获取我的课程。

我希望能够将我的解决方案结构化为实体 (POCO) 类的单独项目和实体模型和存储库代码的另一个项目。

这意味着我的 MVC 项目可以将 POCO 类用于强类型视图等,而不必了解存储库或必须引用它。

为了将它们整合在一起,我将创建另一个带有接口并使用 IoC 的单独项目。

听起来不错,我只是不知道如何将类生成到他们自己的项目中!我可以复制它们,然后更改它们的命名空间,但我想在更改数据库中的架构并想要更新我的模型时避免手动工作。

谢谢

【问题讨论】:

    标签: .net entity-framework code-generation repository-pattern poco


    【解决方案1】:

    实际上 EF 4.0 中的 T4 模板在设计时就考虑到了这种情况 :)

    有2个模板:

    • 一个用于实体本身(即 ModelName.tt)
    • 一个用于 ObjectContext(即 ModelName.Context.tt)

    您应该将 ModelName.tt 文件放在您的 POCO 项目中,只需将模板更改为指向持久感知项目中的 EDMX 文件。

    我知道听起来很奇怪:现在有一个依赖项,但它是在 T4 生成时,而不是在编译时!那应该没问题吧?因为生成的 POCO 程序集仍然完全不了解持久性。

    请参阅此处的第 5 步和第 6 步:http://blogs.msdn.com/adonet/pages/walkthrough-poco-template-for-the-entity-framework.aspx 了解更多信息。

    希望对你有帮助

    亚历克斯

    【讨论】:

    【解决方案2】:

    @尼克,

    1. 要强制重新生成 POCO 实体,您只需右键单击主 .tt 文件并选择“运行自定义工具”。这将强制它使用您对 .edmx 模型的更新更改重新生成您的 POCO 类。
    2. 尽管您不一定要生成数据库,但您继续右键单击模型并选择“从模型生成数据库...”是否有任何问题?这很可能会消除您的“错误 11007...”。
    3. 我认为它相当于“代码隐藏”。我不知道更多。

    关于亚历克斯提供的链接还有一点需要注意。一旦我将主 .tt 文件移动到另一个项目,从“.Context.tt”文件生成的文件将无法编译,因为它缺少对位于不同命名空间中的 POCO 文件的引用(因为我想要我的 ObjectContext 与我的 POCO 文件位于不同的域中)。我不得不将“.Context.tt”文件修改为using Poco.Namespace(其中Poco.Namespace 是生成POCO 文件的命名空间的名称)。这然后允许我的项目编译。

    乔尔

    【讨论】:

    • re: 2. 编译时,我现在收到每个实体的警告:“错误 11007:实体类型 XXXX 未映射。”。这可能与没有生成数据库(?)有关,但在我编辑 edmx(使用 xml 编辑器)以删除那里的映射(即使它对我来说看起来很完美)之前,这并没有发生,然后去了回到设计师并使用工具添加映射。
    • 我在“.Context.tt”文件中遇到了这个exact相同的问题,并想添加一个确实有效的using 语句。问题是文件是自动生成的。如果必须更新模型,则必须删除并重新添加 using 语句。有没有更好的方法来解决这个问题?
    • 没关系,在查看 Alex 的链接后才知道这一点。滚动到名为 7 的部分。更改“Blogging.Context.tt”命名空间以匹配“实体” Context.tt 属性上的自定义工具命名空间可以更新为MyProject.Model,并且引用将解析。
    【解决方案3】:

    对于 EF5 + DbContext 生成器:将您的 Name.Context.tt 移动到不同的项目很容易。但是,您将需要引用模型类。您可以手动执行此操作,但这需要您在每次生成代码时更改它。您还可以对两个项目使用相同的命名空间。这是有效的并且会起作用,但我认为这是糟糕的设计。另一种方法是更改​​ T4 模板 (Name.Context.tt)。

    改变这个(第 43 行):

    using System;
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    <#
    if (container.FunctionImports.Any())
    {
    #>
    

    到这里:

    using System;
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    <#
    if (modelNamespace != codeNamespace)
    #>
    using <#=code.EscapeNamespace(modelNamespace)#>;
    <#
    if (container.FunctionImports.Any())
    {
    #>
    

    这将检查您的模型命名空间是否与您的代码命名空间不同,如果是,它将插入所需的 using 以引用您的模型类。

    【讨论】:

    • "...但这需要您在每次生成代码时更改它..." - 如果您的意思是 当 TT 文件由EDMX 之类的 然后我通常会提前将 TT 放在源代码控制中,然后简单地还原更改
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2011-06-04
    • 1970-01-01
    • 1970-01-01
    • 2016-01-28
    • 1970-01-01
    • 1970-01-01
    • 2020-01-31
    相关资源
    最近更新 更多