爲了能夠解決您的問題,您應該瞭解EF如何處理連接字符串以及遷移如何工作。
如何EF涉及連接字符串:通常你DbContext
有一個參數的構造函數,調用其基類的構造函數有硬編碼的連接字符串名稱。您的項目app.config
或web.config
文件應包含一個connectionStrings
部分,該部分定義具有該名稱的連接字符串。 這是您在項目中使用的默認連接字符串,如果您未明確向Package Manager Console命令提供連接字符串參數。
與連接字符串名稱MyConnectionStringName
一些示例代碼:
public class MyDbContext : DbContext
{
public MyDbContext() : base("MyConnectionStringName") { ... }
...
}
而在你.config
文件:
<configuration>
...
<connectionStrings>
<add name="MyConnectionStringName" connectionString="..." />
</connectionStrings>
</configuration>
如果不使用這種方法,你仍然可以手動提供正確的連接字符串作爲在包管理器控制檯中的參數,如下所示:
Update-Database -ConnectionString <your connection string here> -ConnectionProviderName System.Data.SqlClient
您也可以使用您在.config
文件中定義的任何連接字符串名稱:
Update-Database -ConnectionStringName MyConnectionStringName
現在大概遷移如何工作:遷移是代碼文件。每次運行Add-Migration
時,都會生成/更新代碼文件,通常位於項目內部名爲Migrations
的文件夾中。遷移文件的名稱由其生成時間戳與運行Add-Migration
時使用的名稱拼接而成。您可以檢查這些文件的內容並查看運行Add-Migration
的效果。您也可以在生成後修改它們,並添加自己的代碼,儘管您暫時不需要這樣做。
遷移旨在是增量式的。您從Initial
遷移開始,每次更改模型代碼時都會生成新的遷移文件。該數據庫包含一個名爲__MigrationsHistory
的表,可以跟蹤在數據庫中運行過哪些遷移。
每一次遷移都有一個方法Up
和一個方法Down
。當您運行Update-Database
時,總是有兩個隱式參數:SourceMigration
和TargetMigration
。 EF逐步應用SourceMigration
和TargetMigration
之間的所有遷移的Up
方法(如果要降級數據庫,則使用Down
方法)。當您未指定SourceMigration
和TargetMigration
參數時的默認方案是SourceMigration
是應用於數據庫的最後一次遷移,而TargetMigration
是最後一個掛起的遷移。 EF通過查詢項目的默認數據庫的__MigrationsHistory
表來確定這些參數,因此如果該數據庫不在一致的狀態,則可能會錯誤地生成遷移。我認爲這是造成你的問題的原因。
所以每次運行Update-Database
EF時間眺望__MigrationsHistory
表知道哪些遷移必須運行,這取決於你的數據庫的狀態,並執行新的記錄被插入在該表中的每個遷移的SQL後應用遷移。
看來,在某些時候你的數據庫__MigrationsHistory
內容搞砸了。發生在運行Update-Database
和Add-Migrations
而沒有按照正確的順序和使用-force
參數。
我的建議,以解決您的問題:從頭開始:刪除數據庫,刪除遷移文件,生成Add-Migration Initial
一個新的清潔Initial
遷移,運行它只有Update-Database
一次。從這一點開始,每次更改模型代碼時,都會生成一個新的增量遷移,其中包含Add Migration YourNewMigrationName
,每次使用不同的名稱,並通過運行Update-Database
一次應用新的遷移。
注意:如果您對遷移的工作方式有足夠的瞭解,您可以只使用一個Initial
遷移,並在模型代碼發生更改時通過執行Add-Migrations Initial -force
來更新它,而不是增量遷移。 -force
參數確保不會生成新的遷移文件,而是會覆蓋現有的Initial
遷移文件。這種方法在開發階段很方便,但在生產中通常不是一種好方法,因爲您可能希望在每次部署新版本代碼時增量運行數據庫更新(您可能無法刪除數據庫並重新創建它,並且還需要維護數據,並確保在更新數據庫時不會丟失數據)。
遷移是由EF生成的用於創建和更新數據庫的代碼文件。當您運行Update-Database
時,遷移將轉換爲針對您的數據庫執行的SQL。如果您想查看針對特定遷移生成的確切SQL,您可以運行Update-Database -Script -SourceMigration SomeMigration -TargetMigration SomeOtherMigration
。此命令不會修改數據庫,只會生成並顯示將在實際Update-Database
執行中應用的SQL。
有關生成和運行遷移的更多信息,請參閱here。
祝你好運!
非常感謝您的見解。我沒有刪除我的數據庫。我嘗試從Migrations文件夾中刪除「初始」文件,而不是整個文件夾。然後我做了'添加遷移初始'和'更新數據庫'。它現在工作! – Nurul
不客氣! – Diana
對不起,但我有關於Code-first的問題。你可以請看看它[這裏](http://stackoverflow.com/questions/42048555/is-there-any-way-i-can-just-create-a-table-in-sql-server-和 - 然後更新-Mag)爲我? – Nurul