原文:https://www.cnblogs.com/FGang/p/11262232.html
一、創建表映射實體類
using System; using System.Collections.Generic; using System.ComponentModel.DataAnnotations; using System.ComponentModel.DataAnnotations.Schema; using System.Data.Common; using System.Data.Entity; using System.Linq; using System.Web; namespace DBClientEntity { [Table("User")]//表名 public class User { [Key] //主鍵 [DatabaseGeneratedAttribute(DatabaseGeneratedOption.None)]//非自增長,自增長為Identity [MaxLength(20)] [Column(TypeName= "varchar")] public string ID { get; set; } [Required]//必填 [MaxLength(50)]//字段長度 ,若不指定長度則生成 的表默認為nvarchar(max) [Column(TypeName = "varchar")] //指定字段類型為varchar,而非默認的nvarchar public string Password { get; set; } [Required] public byte Type { get; set; } [Required] public System.DateTime CreateTime { get; set; } } }
備注:
- byte生成的字段類型對應tinyint
- byte[]數組生成的字段類型對應varbinary(MAX)
創建好表實體類后,接着就是創建數據庫上下文(繼承DbContext)並將實體類添加進來。
代碼示例如下:
using DBClientEntity; using System; using System.Collections.Generic; using System.Data.Entity; using System.Data.Entity.Core.Objects; using System.Data.Entity.Infrastructure; using System.Data.Entity.ModelConfiguration; using System.Linq; using System.Reflection; using System.Web; namespace DBClientEntity { /// <summary> /// EF數據庫上下文 /// </summary> public class DbClientContext : DbContext { //connStr為數據庫連接串或app.config中的數據庫連接名稱 public DbClientContext(string connStr) : base(connStr) { } /// <summary> /// 實體類表 /// </summary> public DbSet<User> User { get; set; } } }
EF自動創建數據庫需要我們告訴數據庫如何進行初始化;如創建表后是否需要插入一些基礎數據,是否 需要創建存儲過程、觸發器等。還有就是EF有三種初始化方式(參見下面三個類):
- DropCreateDatabaseIfModelChanges 模型一變重建數據庫(開發階段)
- CreateDatabaseIfNotExists 數據庫不存在時創建數據庫(適合項目正式上線)
- DropCreateDatabaseAlways 每次啟動程序時都重新創建數據庫(提前是數據庫不能被任何程序占用,包含sqlserver管理工具打開運行也會報錯被使用,此方式不太可取,建議不要使用)
下面示例如何創建初始化器並插入一些數據、創建觸發器(首次創建數據庫才會執行Seed方法)
using System; using System.Collections.Generic; using System.Data.Entity; using System.IO; using System.Linq; using System.Reflection; using System.Text; namespace DBClientEntity { /// <summary> /// 數據庫初始化器 /// </summary> public class DBIfNotExistsInitializer : CreateDatabaseIfNotExists<DbClientContext> public override void InitializeDatabase(DbClientContext context) { base.InitializeDatabase(context); } /// <summary> /// 初始化一些數據,模型有變化或首次運行才會執行 /// </summary> /// <param name="context"></param> protected override void Seed(DbClientContext context) { #region 創建觸發器(不處理異常) //[UserInfo]表觸發器 string fileName = "trUserInfo.Trigger.sql"; string sql = GetSqlFile(fileName); if (!string.IsNullOrEmpty(sql)) { try { context.Database.ExecuteSqlCommand(sql); } catch (Exception ex) { throw new Exception(string.Format("執行腳本{0}出錯! {1}", fileName, ex.Message)); } } #endregion //創建內置帳號 User item = new User(); item.ID = "admin"; item.Password = "111111"; item.Type = 2; item.CreateTime = DateTime.Now; if (context.User.Count(x => x.ID == item.ID) < 1) { context.User.Add(item); context.SaveChanges(); } base.Seed(context); } /// <summary> /// 讀取資源文件中的腳本文件 /// </summary> /// <param name="fileName">如UserInfo.Trigger.sql</param> /// <returns></returns> private string GetSqlFile(string fileName) { string sql = ""; string nameSpace = this.GetType().Namespace; Assembly assembly = Assembly.GetExecutingAssembly(); Stream stream = assembly.GetManifestResourceStream(nameSpace + "." + fileName); if (stream != null) { try { //默認編碼加載腳本文件 using (StreamReader reader = new StreamReader(stream, Encoding.Default)) { sql = reader.ReadToEnd(); } } catch { } finally { stream.Close(); } // 返回讀取結果 } return sql; } } }
在創建完DBIfNotExistsInitializer數據庫初始化器類后,需要在程序每一次訪問數據庫前,告訴EF使用該初始化器進行初始化。
代碼如下 :
Database.SetInitializer<DbClientContext>(new DBIfNotExistsInitializer());
說明:
DbClientContext 是之前創建的數據庫上下文,訪問數據庫時必須使用該類,否則會造成EF在數據庫首次創建時不會執行Seed方法