Запускать базу данных SQL Server локально при использовании специфичных для Azure функций? - PullRequest
3 голосов
/ 15 мая 2019

Я пытаюсь перенести проект с использованием локального SQL Server на SQL Azure. База данных имеет зависимости между базами данных, где некоторые представления ссылаются на другую базу данных на том же сервере, которая не поддерживается SQL Azure.

Я успешно изменил их, чтобы использовать внешние таблицы, которые используют внешний источник данных, который создается с использованием следующего:

CREATE EXTERNAL DATA SOURCE [MyExternalDataSource] WITH
(
    TYPE = RDBMS,
    LOCATION = 'SqlServerName',
    DATABASE_NAME = 'SqlServerDatabaseName',
    CREDENTIAL = cred
);

Однако тип СУБД, используемый этим типом источника данных, поддерживается только SQL Azure, а не локальным SQL Server. Выполнение этого сценария для первого работает правильно, в то время как последний вызывает следующую ошибку:

Неверный синтаксис рядом с 'RDBMS'

В результате это означает, что проект базы данных в решении нельзя использовать для установки как Azure SQL, так и локальной установки SQL Server.

В качестве обходного пути я рассматриваю следующие варианты, хотя у каждого есть свои недостатки:

  1. Включение в решение нескольких проектов баз данных, один из которых предназначен для SQL Azure, а другой - для SQL Server - хотя это будет означать дублирование любых обновлений базы данных для обоих проектов.

  2. Отойдите от использования внешних таблиц к функциональности синхронизации данных, предлагаемой взамен Azure, и дублируйте таблицы и данные в обеих базах данных (устраняя необходимость использовать внешний источник данных, вызывающий проблему) - хотя это имеет минимальная 5-минутная задержка (может быть приемлемой в данном конкретном случае, но, конечно, не для всех)

Как другие разработчики справляются с такого рода сценарием, когда такие специфические функции SQL Azure должны использоваться в вашем проекте, но вам также нужно иметь возможность запускать локальную копию базы данных для разработки?

Ответы [ 2 ]

0 голосов
/ 16 мая 2019

Здесь описано несколько подходов: Условная логика в скрипте PostDeployment.sql с использованием SQLCMD

После попытки всех опций, тот, который работал для меня, использовал событие сборки.

Используя этот метод, я настроил проект для использования пустого сценария в качестве сценария предварительной установки, а затем заменил его на правильный сценарий перед сборкой (отладка для On-Premises и выпуск для Azure).После сборки сценарий-заполнитель копируется обратно, чтобы избежать передачи измененного файла в систему контроля версий.

Вот структура папок:

Folder structure

В файле проекта я добавил следующие цели BeforeBuild и AfterBuild:

<Target Name="BeforeBuild">
    <Copy Condition=" '$(Configuration)' == 'Debug' " SourceFiles="Pre-Deployment\OnPremises.PreDeploymentScript.sql" DestinationFiles="Pre-Deployment\PreDeploymentScript.sql" OverwriteReadOnlyFiles="true" />
    <Copy Condition=" '$(Configuration)' == 'Release' " SourceFiles="Pre-Deployment\Azure.PreDeploymentScript.sql" DestinationFiles="Pre-Deployment\PreDeploymentScript.sql" OverwriteReadOnlyFiles="true" />
  </Target>
  <Target Name="AfterBuild">
    <Copy SourceFiles="Pre-Deployment\Empty.PreDeploymentScript.sql" DestinationFiles="Pre-Deployment\PreDeploymentScript.sql" OverwriteReadOnlyFiles="true" />
  </Target>

Сценарий предварительного развертывания Azure создает внешний источник данных (в отдельном сценарии, который здесь не показан) ивнешние таблицы:

IF (NOT EXISTS(SELECT * FROM sys.tables WHERE NAME = 'MyExternalTable' AND is_external = 1))
    BEGIN
        PRINT 'Creating external table: MyExternalTable'

        CREATE EXTERNAL TABLE [MySchema].[MyExternalTable](
            [Id] [int],
            [Name] [nvarchar](3000) NOT NULL
        )
        WITH
        (
            DATA_SOURCE = [ExternalDataSourceName]
        );

        PRINT 'Created external table: MyExternalTable'
    END
ELSE
    BEGIN
        PRINT 'External table ''MyExternalTable'' is already created'
    END
GO

В то время как локальные данные просто создают некоторые синонимы:

IF NOT EXISTS(SELECT * FROM sys.synonyms WHERE name = 'MyExternalTable')
BEGIN
    CREATE SYNONYM [MySchema].[MyExternalTable] FOR [OtherDb].[OtherSchema].[OtherTable]
END

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

CREATE VIEW [dbo].[MyView] AS SELECT * FROM [Myschema].[MyTable]

Несмотря на то, что она выглядит немного неуклюжей, она работает довольно хорошо и позволяет использовать один проект базы данных дляразвертывание как на локальном, так и на Azure SQL Server.

0 голосов
/ 15 мая 2019

Можно попытаться создать 3 проекта:
1. Проект содержит только конкретные ссылки Azure, определенные как представления.
2. Проект содержит только конкретные ссылки SQL Server, определенные как представления.Структура представлений должна быть одинаковой.
3. Ваш основной проект.В этом проекте вы будете ссылаться на один из предыдущих как на «составной проект».
https://docs.microsoft.com/en-us/sql/ssdt/add-database-reference-dialog-box?view=sql-server-2017

...