3

メソッドで次のようなことをしようとしていますSeed:

foreach (string sqlFile in Directory.GetFiles(Path.Combine(Directory.GetCurrentDirectory(), @"SqlScripts")))
            {
                string sqlText = File.OpenText(sqlFile).ReadToEnd();
                context.Database.ExecuteSqlCommand(sqlText);
            }

Update-Database を実行すると、次のエラーが表示されます。

Could not find a part of the path 'C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\IDE\SqlScripts'.

したがって、明らかに更新データベースは、プロジェクト ディレクトリではなく、VS bin ディレクトリから実行されています。プロジェクトへのパスをハード コーディングする必要がなく (複数の開発者がこれに取り組んでいます)、どうすれば ? を含むアセンブリのパスを取得できますDbContextか?

4

1 に答える 1

3

私は似たようなことをしたいと思っていましたが、Seed コマンドはバージョン管理を無視するのに対し、Migrations のポイントはバージョン管理されたデータベースであることを考えると、Seed は少し薄暗いことにいつも気付きました。望ましい結果は、代わりに移行でのデータ移動です。それで、ここに行きます:

(完全なソースは GitHub にあり、いくつかの他の Migrations コマンドも含まれています。)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Data.Entity;
using System.Data.Entity.Migrations;
using System.IO;
using System.Text.RegularExpressions;

public abstract class ExpandedDbMigration
    : System.Data.Entity.Migrations.DbMigration
{
    public void SqlFile(string path)
    {
        var cleanAppDir = new Regex(@"\\bin.+");
        var dir = AppDomain.CurrentDomain.BaseDirectory;
        dir = cleanAppDir.Replace(dir, "") + @"\";
        var sql = File.ReadAllLines(dir + path);

        string[] ignore = new string[]
        {
            "GO",   // Migrations doesn't support GO
            "/*",   // Migrations might not support comments
            "print" // Migrations might not support print
        };

        foreach (var line in sql)
        {
            if (ignore.Any(ig => line.StartsWith(ig)))
                continue;   

            Sql(line);
        }
    }
}

AppDomain... 他の方法のように Visual Studio を指すのではなく、モデル プロジェクトの適切なディレクトリを取得します。

正規表現は、bin フォルダーから実行されている場合に返されるものをクリーンアップします。

ReadAllLines は Sql スクリプトを読み取ります。この場合、\Sql\blah.sql に保存されますが、別の場所に置くこともできます。

foreach/ignore は、移行で使用するとエラーになる "GO" などのコマンドが入るのを防ぎ、Sql Server Management Studio Generate Scripts などのツールから頻繁に発行されます。

最後に、foreach は各行を Migrations にダンプします。

使用法:

using Brass9.Data.Entity.Migrations;

public partial class FillZips : ExpandedDbMigration
{
    public override void Up()
    {
        SqlFile(@"Migrations\Sql\2013-08-15 FillTable.sql");
    }

DbMigration から ExpandedDbMigration への継承の変更に注意してください。

SqlFile への引数を、移行が有効なプロジェクト内の sql ファイルへのパスに置き換えます。

于 2014-08-17T07:34:39.370 に答える