在过去9个月的项目中,我一直在使用SSDT进行数据库设计,而我即将放弃DbUp。希望有一个更简单的解决方案......
这是问题所在。我有一个包含下表的数据库:
Persons
-----------
Id (PK)
Name
Email
我想升级我的数据库,以允许一个人拥有多个电子邮件地址:
Persons EmailAddresses
----------- ----------------
ID (PK) ID (PK)
Name PersonId (FK)
Email
要在没有dataloss的情况下在SSDT内执行此操作,我需要做一些花哨的Pre&部署后脚本:
-- PreDeployment.sql
IF EXISTS (SELECT 1 FROM sys.Tables where [name] = 'Persons')
BEGIN
CREATE Table TMP_Persons (ID, Name);
CREATE Table TMP_EmailAddresses (ID, PersonId, Email);
SELECT INTO TMP_Persons FROM Persons
SELECT INTO TMP_EmailAddresses FROM Persons
DELETE FROM Persons
END
-- PostDeployment.sql
IF EXISTS (SELECT 1 FROM sys.Tables where [name] = 'TMP_Persons')
BEGIN
SELECT INTO Persons FROM TMP_Persons
SELECT INTO EmailAddresses FROM TMP_EmailAddresses
DROP TABLE TMP_Persons;
DROP TABLE TMP_EmailAddresses;
END
这(尽管很棘手)是可行的,而且我一直在为我的大部分变化做这件事。但是,问题在于您拥有多个版本的数据库。例如,我有以下情况:
如果Production比dev机器更新(可能是暂时不部署或需要回滚),则上述脚本可能会失败。这意味着开发人员需要了解并考虑数据库的先前版本。
例如,假设Persons表以前名为Users。我必须在我的预部署脚本中考虑这种可能性。
-- PreDeployment.sql
IF EXISTS (SELECT 1 FROM sys.Tables where [name] = 'Users')
BEGIN
CREATE Table TMP_Persons (ID, Name);
CREATE Table TMP_EmailAddresses (ID, PersonId, Email);
SELECT INTO TMP_Persons FROM Users
SELECT INTO TMP_EmailAddresses FROM Users
DELETE FROM Persons
END
IF EXISTS (SELECT 1 FROM sys.Tables where [name] = 'Persons')
BEGIN
CREATE Table TMP_Persons (ID, Name);
CREATE Table TMP_EmailAddresses (ID, PersonId, Email);
SELECT INTO TMP_Persons FROM Persons
SELECT INTO TMP_EmailAddresses FROM Persons
DELETE FROM Persons
END
随着时间的推移,出现更多变化,PreDeployment脚本将变得非常混乱且容易出错。这对我来说似乎无法管理。除了切换到DbUp或其他东西,在SSDT中有更好的方法吗?