如何使用 Oracle 的实体框架支持强制使用 pascal 大小写? [英] How to force pascal case with Oracle's Entity Framework support?

查看:28
本文介绍了如何使用 Oracle 的实体框架支持强制使用 pascal 大小写?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

Oracle 的实体框架支持使所有类名都大写并保留下划线.所以 ORDER_ITEMS 表变成了类名中的 ORDER_ITEMS.但我想对类名使用 Pascal 大小写.

ORDER_ITEMS ==> 需要 OrderItems.

如何更改默认命名规则?

解决方案

大约 2 周前,我的任务是摆脱 Linq Connect 作为我们的数据提供者,转而使用 EF 进行 ORM 操作.嗯,众所周知,当微软和甲骨文参与进来时,事情绝非易事,因为他们不能很好地合作.由精明的开发人员来寻找 Pascal Casing 和 Pluralization 的解决方案,以便从 Oracle 数据库生成的实体符合我们的标准.我们不希望带下划线的表名出现在我们的模型上.经过一番思考和发展,终于找到了一个好的解决方案.最终结果是操作 EDMX 文件,然后运行 ​​T4 模板以实现奇迹.我们的最终结果将所有实体及其属性转换为 Pascal 大小写.它还将所有存储函数转换为 Pascal 大小写.集合的导航属性也都复数了.以下是要遵循的步骤和代码片段.希望这对编码社区中的某些人有所帮助,您可以随时通过 twitter 上的 seafarer_007 与我联系,提出有用的意见或建议.它是: 1. 使用 EF 数据模型项生成 EDMX.我在 Visual Studio 2012 中使用了 EF 5.0. 2. 编写一个控制台应用程序来操作 EDMX 和设计器文件.我在 App Config 中添加了对两者的引用.3. 应该就是这样,您将拥有 Pascal 外壳和复数实体.您可以随时根据需要调整 Pascal case 方法.4. 我在 Visual Studio 2012 和 EF 5.0 上测试了代码.5. 警告:仅适用于没有点的单字命名空间,基本上你不能为模型使用 OrgName.DeptName.Namespace,它只会处理 OrgName,但是,你可以调整 Pascal Casing Method 来解决这个问题.

控制台应用程序代码如下:

 static void Main(string[] args){string pathFile = string.Empty;string designFile = string.Empty;//EDMX文件位置if (ConfigurationManager.AppSettings["EDMX"] != null){pathFile = ConfigurationManager.AppSettings["EDMX"].ToString();}//EF 5.0的设计器位置if (ConfigurationManager.AppSettings["EDMXDiagram"] != null){designFile = ConfigurationManager.AppSettings["EDMXDiagram"].ToString();}XDocument xdoc = XDocument.Load(pathFile);const string CSDLNamespace = "http://schemas.microsoft.com/ado/2009/11/edm";const string MSLNamespace = "http://schemas.microsoft.com/ado/2009/11/mapping/cs";XElement csdl = xdoc.Descendants(XName.Get("Schema", CSDLNamespace)).First();XElement msl = xdoc.Descendants(XName.Get("Mapping", MSLNamespace)).First();#region CSDLforeach (var entitySet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("EntitySet", CSDLNamespace))){entitySet.Attribute("Name").Value = PascalCase(entitySet.Attribute("Name").Value);entitySet.Attribute("EntityType").Value = PascalCase(entitySet.Attribute("EntityType").Value);}foreach (var associationSet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("AssociationSet", CSDLNamespace))){foreach (var end in associationSet.Elements(XName.Get("End", CSDLNamespace))){end.Attribute("EntitySet").Value = PascalCase(end.Attribute("EntitySet").Value);}}foreach (var funtionSet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("FunctionImport", CSDLNamespace))){funtionSet.Attribute("Name").Value = PascalCase(funtionSet.Attribute("Name").Value);}foreach (csdl.Elements(XName.Get("EntityType", CSDLNamespace)) 中的 var entityType){entityType.Attribute("Name").Value = PascalCase(entityType.Attribute("Name").Value);foreach (entityType.Elements(XName.Get("Key", CSDLNamespace)) 中的变量键){foreach (var propertyRef in key.Elements(XName.Get("PropertyRef", CSDLNamespace))){propertyRef.Attribute("Name").Value = PascalCase(propertyRef.Attribute("Name").Value);}}foreach (entityType.Elements(XName.Get("Property", CSDLNamespace)) 中的 var 属性){property.Attribute("Name").Value = PascalCase(property.Attribute("Name").Value);}foreach (var navigationProperty in entityType.Elements(XName.Get("NavigationProperty", CSDLNamespace))){navigationProperty.Attribute("Name").Value = PascalCase(navigationProperty.Attribute("Name").Value, true, true);}}foreach (csdl.Elements(XName.Get("Association", CSDLNamespace)) 中的变量关联){foreach (var end in association.Elements(XName.Get("End", CSDLNamespace))){end.Attribute("Type").Value = PascalCase(end.Attribute("Type").Value);}foreach(var refs in association.Elements(XName.Get("ReferentialConstraint", CSDLNamespace))){foreach (var pri in refs.Elements(XName.Get("Principal", CSDLNamespace))){foreach(pri.Elements(XName.Get(PropertyRef",CSDLNamespace))中的var proref){proref.Attribute("Name").Value = PascalCase(proref.Attribute("Name").Value);}}foreach (var pri in refs.Elements(XName.Get("Dependent", CSDLNamespace))){foreach(pri.Elements(XName.Get(PropertyRef",CSDLNamespace))中的var proref){proref.Attribute("Name").Value = PascalCase(proref.Attribute("Name").Value);}}}}#endregion#region MSLforeach (var entitySetMapping in msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)).Elements(XName.Get("EntitySetMapping", MSLNamespace))){entitySetMapping.Attribute("Name").Value = PascalCase(entitySetMapping.Attribute("Name").Value);foreach (var entityTypeMapping in entitySetMapping.Elements(XName.Get("EntityTypeMapping", MSLNamespace))){entityTypeMapping.Attribute("TypeName").Value = PascalCase(entityTypeMapping.Attribute("TypeName").Value);foreach(var scalarProperty in(entityTypeMapping.Element(XName.Get("MappingFragment", MSLNamespace))).Elements(XName.Get("ScalarProperty", MSLNamespace))){scalarProperty.Attribute("Name").Value = PascalCase(scalarProperty.Attribute("Name").Value);}}}foreach (在 msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)) 中的 var associationSetMapping).Elements(XName.Get("AssociationSetMapping", MSLNamespace))){foreach (var endProperty in associationSetMapping.Elements(XName.Get("EndProperty", MSLNamespace))){foreach (var scalarProperty in endProperty.Elements(XName.Get("ScalarProperty", MSLNamespace))){scalarProperty.Attribute("Name").Value = PascalCase(scalarProperty.Attribute("Name").Value);}}}foreach (var functionSetMapping in msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)).Elements(XName.Get("FunctionImportMapping", MSLNamespace))){functionSetMapping.Attribute("FunctionImportName").Value = PascalCase(functionSetMapping.Attribute("FunctionImportName").Value);}#endregionxdoc.Save(pathFile);XmlDocument designXml = new XmlDocument();designXml.Load(designFile);XmlNamespaceManager dsMan = new XmlNamespaceManager(designXml.NameTable);dsMan.AddNamespace("edmx", "http://schemas.microsoft.com/ado/2009/11/edmx");dsMan.AddNamespace("d", "http://schemas.microsoft.com/ado/2009/11/edmx");#region 设计师XmlNodeList entitySet1 = designXml.DocumentElement.SelectNodes("//d:Diagrams", dsMan);foreach(entitySet1 中的 XmlNode xn){foreach(xn.ChildNodes 中的 XmlElement xp){foreach(xp.ChildNodes 中的 XmlElement z){if (z.Attributes[0].Name == "EntityType"){z.Attributes[0].Value = PascalCase(z.Attributes[0].Value.ToString(), true);}}}}designXml.Save(designFile);#endregion}#region 复数公共静态字符串复数(字符串名称){return System.Data.Entity.Design.PluralizationServices.PluralizationService.CreateService(new CultureInfo("en-US")).Pluralize(name);}#endregion#region 帕斯卡套管公共静态字符串 PascalCase(StructuralType 类型,bool sanitizeName = true){如果(类型==空){返回空;}返回 PascalCase(type.Name, sanitizeName);}公共静态字符串 PascalCase(EdmMember 成员,bool sanitizeName = true){如果(成员==空){返回空;}返回 PascalCase(member.Name, sanitizeName);}公共静态字符串 PascalCase(字符串名称,bool sanitizeName = true,bool 复数 = false){//如果帕斯卡大小写存在//退出函数正则表达式 rgx = 新正则表达式(@"^[A-Z][a-z]+(?:[A-Z][a-z]+)*$");字符串 pascalTest = 名称;如果(名称.包含(.")){字符串[] 测试 = 新字符串[]{};test = name.Split('.');if(rgx.IsMatch(test[1].ToString())){返回名称;}}别的{如果(rgx.IsMatch(名称)){返回名称;}}//检查命名空间中的点符号布尔包含 = 假;string[] temp = new string[] { };var namespc = string.Empty;如果(名称.包含(.")){包含 = 真;temp = name.Split('.');namepc = temp[0];}如果(包含){名称 = 温度 [1];}name = name.ToLowerInvariant();字符串结果 = 名称;bool upperCase = false;结果 = string.Empty;for (int i = 0; i < name.Length; i++){if (name[i] == ' ' || name[i] == '_'){大写 = 真;}别的{if (i == 0 || 大写){结果 += name[i].ToString().ToUpperInvariant();大写 = 假;}别的{结果 += 名称[i];}}}如果(包含){结果 = namespc.ToString() + "."+ 结果;}如果(复数){结果 = 复数(结果);}返回结果;}#endregion

Oracle's entity framework support is making all class names upper case and carrying over underscore. So ORDER_ITEMS table becomes ORDER_ITEMS in class name. but I want to use Pascal case for class names.

ORDER_ITEMS ==> OrderItems is wanted.

How can I change the default naming rule?

解决方案

Around 2 weeks ago, I was tasked with getting rid of Linq Connect as our Data provider to using EF for our ORM operations. Well, as well all know it, things are never easy when Microsoft and Oracle are involved, as they don’t play well together. It was up to the savvy developer to find a solution for Pascal Casing and Pluralization, so that the Entities generated from the Oracle database matched our standards. We didn't want table names with underscores to show up on our Models. It took a little bit of thought and development to finally come to a good solution. The end result was manipulating the EDMX file and then running the T4 templates to make the magic happen. Our end result converted all the entities and their properties to Pascal casing. It also converted all the Stored functions to Pascal casing. Navigation properties to collection were all also pluralized. Here are the steps and the code snippet to follow. Hope this helps some one in the coding community and you can always reach out to me at seafarer_007 on twitter with helpful comments or suggestions. Here it is: 1. Generate the EDMX using the EF Data Model item. I used EF 5.0 in Visual Studio 2012. 2. Write a console app that manipulates the EDMX and the designer files. I have added references to both in the App Config. 3. That should be it, and you will have Pascal cased and Pluralized entities. You can always tweak the Pascal case method to your desires. 4. I tested the code on Visual Studio 2012 and EF 5.0. 5. Caveat : Works with only a single worded namespace without dots, basically you can’t have OrgName.DeptName.Namespace for the Model, it will only handle OrgName, however, you can tweak the Pascal Casing Method to resolve that.

Console Application code below:

    static void Main(string[] args)
    {

        string pathFile = string.Empty;
        string designFile = string.Empty;


        //EDMX File location
        if (ConfigurationManager.AppSettings["EDMX"] != null)
        {
            pathFile = ConfigurationManager.AppSettings["EDMX"].ToString();
        }

        //Designer location for EF 5.0
        if (ConfigurationManager.AppSettings["EDMXDiagram"] != null)
        {
            designFile = ConfigurationManager.AppSettings["EDMXDiagram"].ToString();
        }





        XDocument xdoc = XDocument.Load(pathFile);


        const string CSDLNamespace = "http://schemas.microsoft.com/ado/2009/11/edm";
        const string MSLNamespace = "http://schemas.microsoft.com/ado/2009/11/mapping/cs";

        XElement csdl = xdoc.Descendants(XName.Get("Schema", CSDLNamespace)).First();
        XElement msl = xdoc.Descendants(XName.Get("Mapping", MSLNamespace)).First();



        #region CSDL
        foreach (var entitySet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("EntitySet", CSDLNamespace)))
        {
            entitySet.Attribute("Name").Value = PascalCase(entitySet.Attribute("Name").Value);
            entitySet.Attribute("EntityType").Value = PascalCase(entitySet.Attribute("EntityType").Value);
        }
        foreach (var associationSet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("AssociationSet", CSDLNamespace)))
        {
            foreach (var end in associationSet.Elements(XName.Get("End", CSDLNamespace)))
            {
                end.Attribute("EntitySet").Value = PascalCase(end.Attribute("EntitySet").Value);
            }
        }

        foreach (var funtionSet in csdl.Element(XName.Get("EntityContainer", CSDLNamespace)).Elements(XName.Get("FunctionImport", CSDLNamespace)))
        {

            funtionSet.Attribute("Name").Value = PascalCase(funtionSet.Attribute("Name").Value);

        }

        foreach (var entityType in csdl.Elements(XName.Get("EntityType", CSDLNamespace)))
        {
            entityType.Attribute("Name").Value = PascalCase(entityType.Attribute("Name").Value);

            foreach (var key in entityType.Elements(XName.Get("Key", CSDLNamespace)))
            {
                foreach (var propertyRef in key.Elements(XName.Get("PropertyRef", CSDLNamespace)))
                {
                    propertyRef.Attribute("Name").Value = PascalCase(propertyRef.Attribute("Name").Value);
                }
            }

            foreach (var property in entityType.Elements(XName.Get("Property", CSDLNamespace)))
            {
                property.Attribute("Name").Value = PascalCase(property.Attribute("Name").Value);
            }

            foreach (var navigationProperty in entityType.Elements(XName.Get("NavigationProperty", CSDLNamespace)))
            {
                navigationProperty.Attribute("Name").Value = PascalCase(navigationProperty.Attribute("Name").Value, true, true); 
            }

        }
        foreach (var association in csdl.Elements(XName.Get("Association", CSDLNamespace)))
        {
            foreach (var end in association.Elements(XName.Get("End", CSDLNamespace)))
            {
                end.Attribute("Type").Value = PascalCase(end.Attribute("Type").Value);
            }               

            foreach(var refs in association.Elements(XName.Get("ReferentialConstraint", CSDLNamespace)))
            {

                foreach (var pri in refs.Elements(XName.Get("Principal", CSDLNamespace)))
                {

                    foreach (var proref in pri.Elements(XName.Get("PropertyRef", CSDLNamespace)))
                    {

                        proref.Attribute("Name").Value = PascalCase(proref.Attribute("Name").Value);
                    }

                }

                foreach (var pri in refs.Elements(XName.Get("Dependent", CSDLNamespace)))
                {

                    foreach (var proref in pri.Elements(XName.Get("PropertyRef", CSDLNamespace)))
                    {

                        proref.Attribute("Name").Value = PascalCase(proref.Attribute("Name").Value);
                    }

                }


            }



        }
        #endregion

        #region MSL

        foreach (var entitySetMapping in msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)).Elements(XName.Get("EntitySetMapping", MSLNamespace)))
        {
            entitySetMapping.Attribute("Name").Value = PascalCase(entitySetMapping.Attribute("Name").Value);

            foreach (var entityTypeMapping in entitySetMapping.Elements(XName.Get("EntityTypeMapping", MSLNamespace)))
            {
                entityTypeMapping.Attribute("TypeName").Value = PascalCase(entityTypeMapping.Attribute("TypeName").Value);
                foreach
                (var scalarProperty in
                (entityTypeMapping.Element(XName.Get("MappingFragment", MSLNamespace))).Elements(XName.Get("ScalarProperty", MSLNamespace))
                )
                {
                    scalarProperty.Attribute("Name").Value = PascalCase(scalarProperty.Attribute("Name").Value);
                }

            }
        }
        foreach (var associationSetMapping in msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)).Elements(XName.Get("AssociationSetMapping", MSLNamespace)))
        {
            foreach (var endProperty in associationSetMapping.Elements(XName.Get("EndProperty", MSLNamespace)))
            {
                foreach (var scalarProperty in endProperty.Elements(XName.Get("ScalarProperty", MSLNamespace)))
                {
                    scalarProperty.Attribute("Name").Value = PascalCase(scalarProperty.Attribute("Name").Value);
                }
            }
        }

        foreach (var functionSetMapping in msl.Element(XName.Get("EntityContainerMapping", MSLNamespace)).Elements(XName.Get("FunctionImportMapping", MSLNamespace)))
        {
            functionSetMapping.Attribute("FunctionImportName").Value = PascalCase(functionSetMapping.Attribute("FunctionImportName").Value);
        }
        #endregion

        xdoc.Save(pathFile);


        XmlDocument designXml = new XmlDocument();

        designXml.Load(designFile);      


        XmlNamespaceManager dsMan = new XmlNamespaceManager(designXml.NameTable);
        dsMan.AddNamespace("edmx", "http://schemas.microsoft.com/ado/2009/11/edmx");
        dsMan.AddNamespace("d", "http://schemas.microsoft.com/ado/2009/11/edmx");


        #region Designer

        XmlNodeList entitySet1 = designXml.DocumentElement.SelectNodes("//d:Diagrams", dsMan);

        foreach (XmlNode xn in entitySet1)
        {

            foreach (XmlElement xp in xn.ChildNodes)
            {

                foreach (XmlElement z in xp.ChildNodes)
                {

                    if (z.Attributes[0].Name == "EntityType")
                    {

                        z.Attributes[0].Value = PascalCase(z.Attributes[0].Value.ToString(), true);

                    }


                }

            }


        }

        designXml.Save(designFile);


        #endregion

    }

    #region Pluralization


    public static string Pluralize(string name)
    {

   return System.Data.Entity.Design.PluralizationServices.PluralizationService.CreateService(new CultureInfo("en-US")).Pluralize(name);
    }



    #endregion



    #region Pascal Casing

    public static string PascalCase(StructuralType type, bool sanitizeName = true)
    {
        if (type == null)
        {
            return null;
        }

        return PascalCase(type.Name, sanitizeName);
    }


    public static string PascalCase(EdmMember member, bool sanitizeName = true)
    {
        if (member == null)
        {
            return null;
        }

        return PascalCase(member.Name, sanitizeName);
    }

    public static string PascalCase(string name, bool sanitizeName = true, bool pluralize = false)
    {

       // if pascal case exists
       // exit function

        Regex rgx = new Regex(@"^[A-Z][a-z]+(?:[A-Z][a-z]+)*$");

        string pascalTest = name;

        if (name.Contains("."))
        {
            string[] test  = new string[]{};
            test = name.Split('.');

            if(rgx.IsMatch(test[1].ToString()))
            {
                return name;
            }

        }
        else
        {

            if (rgx.IsMatch(name))
            {
                return name;
            }

        }

        //Check for dot notations in namespace

        bool contains = false;
        string[] temp = new string[] { };
        var namespc = string.Empty;

        if (name.Contains("."))
        {
            contains = true;
            temp = name.Split('.');
            namespc = temp[0];

        }

        if (contains)
        {
            name = temp[1];
        }

        name = name.ToLowerInvariant();

        string result = name;
        bool upperCase = false;

        result = string.Empty;
        for (int i = 0; i < name.Length; i++)
        {
            if (name[i] == ' ' || name[i] == '_')
            {
                upperCase = true;
            }
            else
            {
                if (i == 0 || upperCase)
                {
                    result += name[i].ToString().ToUpperInvariant();
                    upperCase = false;
                }
                else
                {
                    result += name[i];
                }
            }
        }


        if (contains)
        {


            result = namespc.ToString() + "." + result;



        }

        if (pluralize)
        {
            result = Pluralize(result);
        }


        return result;
    }
    #endregion

这篇关于如何使用 Oracle 的实体框架支持强制使用 pascal 大小写?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆