最近工作电脑装完win10后,之前使用的codeSmith安装不了,索性自己写一个。
界面比较简单,如下图:
第一行为Oracle数据库的连接字符串。连接成功后,填充表到第4行的下拉列表中。
第二行为实体类命名空间。
第三行为保存生成类、xml文件选择文件夹。
1 private void btnConnect_Click(object sender, RoutedEventArgs e) 2 { 3 try 4 { 5 using (OracleConnection conn = new OracleConnection()) 6 { 7 conn.ConnectionString = txtConnStr.Text; 8 9 using (OracleCommand cmd = conn.CreateCommand())10 {11 cmd.CommandText = "select distinct table_name from user_tables order by table_name";12 13 DataTable dt = new DataTable();14 15 OracleDataAdapter adapter = new OracleDataAdapter();16 adapter.SelectCommand = cmd;17 18 adapter.Fill(dt);19 20 cbTables.DisplayMemberPath = "TABLE_NAME";21 cbTables.SelectedValuePath = "TABLE_NAME";22 cbTables.ItemsSource = dt.DefaultView;23 24 }25 26 MessageBoxShow("连接成功!");27 28 }29 }30 catch31 {32 MessageBoxShow("连接失败!");33 }34 }
1 private void btnChoseDirectory_Click(object sender, RoutedEventArgs e) 2 { 3 FolderBrowserDialog folderDialog = new FolderBrowserDialog(); 4 DialogResult dialogResult = folderDialog.ShowDialog(); 5 6 if (dialogResult == System.Windows.Forms.DialogResult.OK) 7 { 8 labDirectoryPath.Content = folderDialog.SelectedPath.Trim(); 9 }10 }
1 private void btnSave_Click(object sender, RoutedEventArgs e) 2 { 3 if (string.IsNullOrEmpty(txtEntityClassNamespace.Text.Trim())) 4 { 5 MessageBoxShow("请输入实体命名空间名称!"); 6 txtEntityClassNamespace.Focus(); 7 return; 8 } 9 if (labDirectoryPath.Content == null) 10 { 11 MessageBoxShow("请选择文件夹保存生成文件!"); 12 btnChoseDirectory.Focus(); 13 return; 14 } 15 if (cbTables.SelectedValue == null) 16 { 17 MessageBoxShow("请选择表名!"); 18 return; 19 } 20 21 DataTable dt = GetTableSchemaByTableName(); 22 23 GenerateClass(dt); 24 25 GenerateMappingXml(dt); 26 27 MessageBoxShow("生成成功!"); 28 } 29 30 private string OracleTypeToCSType(string oracleType) 31 { 32 string csType = string.Empty; 33 34 switch (oracleType.ToUpper()) 35 { 36 case "NVARCHAR2": 37 case "VARCHAR2": 38 case "CHAR": 39 csType = "string"; 40 break; 41 case "LONG": 42 csType = "long"; 43 break; 44 case "NUMBER": 45 csType = "int"; 46 break; 47 case "DATE": 48 csType = "datetime"; 49 break; 50 } 51 52 return csType; 53 } 54 55 private DataTable GetTableSchemaByTableName() 56 { 57 string selectSQL = @"select t1.COLUMN_NAME,t1.data_type,t1.data_length,t1.nullable,t2.comments, 58 replace(initcap(t1.TABLE_NAME),'_','') className 59 from user_tab_columns t1 left 60 join user_col_comments t2 61 on t1.TABLE_NAME = t2.table_name and t1.COLUMN_NAME = t2.column_name 62 where t1.table_name = :table_name 63 order by to_number(t1.column_id)"; 64 65 DataTable dt = new DataTable(); 66 using (OracleConnection conn = new OracleConnection()) 67 { 68 conn.ConnectionString = txtConnStr.Text; 69 70 using (OracleCommand cmd = conn.CreateCommand()) 71 { 72 cmd.CommandText = selectSQL; 73 cmd.Parameters.Add(new OracleParameter(":table_name", cbTables.SelectedValue)); 74 75 OracleDataAdapter adapter = new OracleDataAdapter(); 76 adapter.SelectCommand = cmd; 77 78 adapter.Fill(dt); 79 } 80 } 81 82 return dt; 83 } 84 85 private void GenerateClass(DataTable dt) 86 { 87 string entityClassNamespace = txtEntityClassNamespace.Text; 88 if (dt.Rows.Count > 0) 89 { 90 string className = dt.Rows[0]["className"].ToString(); 91 92 using (FileStream csStream = new FileStream(System.IO.Path.Combine(labDirectoryPath.Content.ToString(), className + ".cs"), FileMode.Create, FileAccess.Write)) 93 { 94 using (StreamWriter writer = new StreamWriter(csStream, Encoding.Default)) 95 { 96 writer.WriteLine(string.Format("namespace {0}", entityClassNamespace)); 97 98 writer.WriteLine("{ "); 99 writer.WriteLine(string.Format(@" public class {0} : BaseModel100 { { ", className));101 for (int i = 0; i < dt.Rows.Count; i++)102 {103 writer.WriteLine(string.Format(@" ///104 /// {0}105 /// ", dt.Rows[i]["comments"].ToString()));106 writer.WriteLine(string.Format(" public virtual {0} {1} { { set; get; }}",107 OracleTypeToCSType(dt.Rows[i]["data_type"].ToString()),108 dt.Rows[i]["COLUMN_NAME"].ToString()));109 writer.WriteLine();110 }111 writer.WriteLine(" }");112 writer.WriteLine("}");113 }114 }115 116 }117 }118 119 private void GenerateMappingXml(DataTable dt)120 {121 string entityClassNamespace = txtEntityClassNamespace.Text;122 if (dt.Rows.Count > 0)123 {124 string className = dt.Rows[0]["className"].ToString();125 126 XNamespace xmlns = "urn:nhibernate-mapping-2.2";127 128 var xDoc = new XDocument(new XElement(xmlns + "hibernate-mapping",129 new XElement(xmlns + "class",130 new XAttribute("name", string.Format("{0}.{1},{0}", entityClassNamespace, className)),131 new XAttribute("table", cbTables.SelectedValue),132 new XAttribute("lazy", "true"),133 new XElement(xmlns + "id",134 new XAttribute("column", "ID"),135 new XAttribute("name", "ID"),136 new XElement(xmlns + "generator",137 new XAttribute("class", "sequence"),138 new XElement(xmlns + "param",139 new XAttribute("name", "sequence"),140 new XText(string.Format("SEQ_{0}", cbTables.SelectedValue))141 ))))));142 143 XElement _class = xDoc.Root.Element(xmlns + "class");144 145 for (int i = 0; i < dt.Rows.Count; i++)146 {147 string columnName = dt.Rows[i]["COLUMN_NAME"].ToString();148 149 XElement property = new XElement(xmlns + "property");150 property.SetAttributeValue("name", columnName);151 property.SetAttributeValue("column", columnName);152 153 _class.Add(property);154 }155 156 xDoc.Save(System.IO.Path.Combine(labDirectoryPath.Content.ToString(), className + ".hbm.xml"));157 }158 }
总结:
- 使用user_tables系统表查询用户所有表
- 使用user_tab_columns查询表的所有列
- 使用user_col_comments查询表的备注信息
- 使用文件流生成实体类,使用Linq to xml生成*.hbm.xml文件