Наилучшая практика для заполнения статических данных с помощью проекта базы данных Visual Studio 2010? - PullRequest
24 голосов
/ 25 ноября 2010

Как вы заполняете свою базу данных статическими данными, контролируемыми источником, используя проект базы данных Visual Studio? Я попробовал все три стратегии ниже, находя, что каждая из них прогрессивно лучше, чем предыдущая. Я использую, но не полностью удовлетворен стратегией 3. У вас есть другая альтернатива?

  1. Поместите сценарии вставки в папку «Планы создания данных». Ссылка на сценарии в файле «Script.PostDeployment.sql», чтобы включить их в процесс развертывания.

    - преимущество: прямолинейно
    - недостаток: slooooooow
    - недостаток: при последующем развертывании необходимо сначала удалить статические данные или проверить их на отсутствие => неэффективно

  2. Вставьте данные в базу данных в первый раз, используя тот метод, который наиболее удобен (например, это может быть функция таблицы редактирования SSMS). Извлеките эти данные с помощью утилиты командной строки bcp, чтобы создать кучу файлов данных и добавить их в свой проект. Создайте сценарий, указанный в файле «Scripts.PostDeployment.sql», который выполняет оператор «массовой вставки» для каждого файла данных.

    - преимущество: намного быстрее, чем операторы вставки
    - преимущество: можно использовать функцию редактирования таблицы SSMS
    - недостаток: для каждого оператора массовой вставки требуется полное имя файла с файлом данных, поэтому, если файлы данных находятся на моем компьютере в папке «C: \ Projects \ Dev \ Source \ foo.dat», удаленный компьютер разработчика также иметь их в этом месте, или оператор массовой вставки не может
    - недостаток: необходимо удалить существующие статические данные перед выполнением операторов массовой вставки при последующих развертываниях

  3. Создание временных таблиц во время развертывания для хранения статических данных и использование оператора слияния sql для синхронизации этих таблиц с целевыми таблицами. См. либо из этих сообщений в блоге.

    - преимущество: похоже, что sql merge имеет идеальную семантику для проблемы
    - недостаток: логика для этой стратегии повторяется в каждом файле - недостаток: определения таблиц повторяются как временные таблицы в файлах слияния sql

Существует ли превосходящая альтернативная стратегия? Я отказался от стратегии 1, потому что она была слишком медленной. Мне не нравится стратегия 2 из-за проблемы с полным именем файла. Я удовлетворен, но не в восторге от стратегии 3. Есть ли лучшая практика?

Ответы [ 4 ]

8 голосов
/ 08 марта 2011

В вашем скрипте insert.sql вы можете поместить GUID в таблицу [__RefactorLog] (которая является системной таблицей, используемой при развертывании) и проверить, существует ли этот GUID перед вставкой ваших данных следующим образом:

: setvar SOMEID "784B2FC9-2B1E-5798-8478-24EE856E62AE" // создать guid с помощью Tools \ CreateGuid в VS2010

ЕСЛИ НЕ СУЩЕСТВУЕТ (ВЫБЕРИТЕ [OperationKey] ОТ [dbo]. [__ RefactorLog] где [OperationKey] = '$ (SOMEID)')

НАЧАТЬ

...

INSERT INTO [dbo]. [__ RefactorLog] ([OperationKey]) значения ('$ (SOMEID)')

END

Затем вы вставляете данные только в том случае, если их не существует или если вы хотите (изменяя Guid).

2 голосов
/ 30 ноября 2013

Вот как я решил эту проблему на тот случай, если кому-то это покажется полезным ...

Стратегия заключается в установке переменной sqlcmdvars перед созданием проекта базы данных.Эта переменная будет содержать абсолютный путь к папке сборки, на который можно ссылаться из сценария после развертывания.Тогда было бы просто использовать это в сценарии развертывания для любых дополнительных файлов или ресурсов, которые вам могут понадобиться.Преимущество этой стратегии заключается в том, что все пути относятся к файлу проекта, а не требуют жестко закодированного общего пути.

Создайте новую переменную команды Sql с именем $ (MSBuildProjectDirectory).Это будет переопределено в сценарии предварительной сборки.

Создайте сценарий msbuild, который установит переменную команды sql, и создайте базу данных.

<Project ToolsVersion="4.0" DefaultTargets="BuildDatabase"  xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\MSBuildCommunityTasks\MSBuild.Community.Tasks.Targets"/>
<PropertyGroup>
    <DatabaseServer>(Local)</DatabaseServer>
    <DeploymentConnectionString>Data Source=$(DatabaseServer)%3BIntegrated Security=True%3BPooling=False</DeploymentConnectionString>
    <Configuration>Release</Configuration>
</PropertyGroup>
<Target Name="BuildDatabase">
    <!-- Sets the projet path variable so that the post deployment script can determine the location of the bulk insert csv files. -->
    <XmlUpdate
        Prefix="urn"
        Namespace="urn:Microsoft.VisualStudio.Data.Schema.Package.SqlCmdVars"
        XmlFileName="$(MSBuildProjectDirectory)\DatabaseProjectName\Properties\Database.sqlcmdvars"
        XPath="/urn:SqlCommandVariables/urn:Properties/urn:Property[urn:PropertyName='MSBuildProjectDirectory']/urn:PropertyValue"
        Value="$(MSBuildProjectDirectory)\DatabaseProjectName" />

    <MSBuild
            Projects="DatabaseProjectName\DatabaseProjectName.dbproj"
            Properties="Configuration=$(Configuration);
                    TargetDatabase=DatabaseName;
                    TargetConnectionString=$(DeploymentConnectionString);
                    GenerateDropsIfNotInProject=True;
                    BlockIncrementalDeploymentIfDataLoss=False;
                    DeployToDatabase=True;
                    IgnorePermissions=True"
            Targets="Build;Deploy">
        <Output TaskParameter="TargetOutputs" ItemName="SqlFiles"/>
    </MSBuild>
</Target>

Обновите сценарий развертывания после публикации следующим образом ...

BULK INSERT [dbo].[TableName] FROM '$(MSBuildProjectDirectory)\Scripts\Post-Deployment\Data\YourDataFile.csv'
WITH (FIELDTERMINATOR = ',', ROWTERMINATOR='\n')
1 голос
/ 05 мая 2011

Вы можете использовать выходные данные схемы из проекта базы данных для обновления целевой базы данных. Существует инструмент cmd для запуска его на другом компьютере, который не доступен для вас.то же самое, если у вас нет капель на любом столбце

0 голосов
/ 28 февраля 2011

Мы еще не внедрили наш проект VS 2010 db в производство, но для нашего собственного проекта мы загружаем производственную базу данных в целевую базу данных и собираем / внедряем ее на этапе разработки / тестирования.Тем не менее, я понимаю, что, вероятно, не будет работать для вас, Тим, если у вас есть несколько баз данных prod и статические данные, которые поступают в каждую.Но это может быть сделано для однодневных магазинов, таких как наш.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...