From d0d67373d1494bd19f565016954b6f170ee99856 Mon Sep 17 00:00:00 2001 From: Benjin Dubishar Date: Fri, 10 Feb 2023 11:36:31 -0800 Subject: [PATCH] Adding support for database literal references for Dacpac and SqlProj references (#1858) * fixing up some nullable spots * Adding database literal support * Adding tests and support for same database refs * Fixing test * merge laggard * Split database reference tests up * PR feedback * Normalizing strings for cross-plat test passing * Updating Projects nuget package * Fixing up test --- Packages.props | 2 +- ...rver.DacFx.Projects.161.8086.0-alpha.nupkg | Bin 52560 -> 0 bytes ...rver.DacFx.Projects.161.8093.0-alpha.nupkg | Bin 0 -> 52711 bytes .../AddDacpacReferenceParams.cs | 8 +- .../AddDatabaseReferenceParams.cs | 6 +- .../AddSqlProjectReferenceParams.cs | 10 +- .../AddSystemDatabaseReference.cs | 2 - .../AddUserDatabaseReferenceParams.cs | 36 ++++ .../Contracts/Folders/AddFolder.cs | 2 + .../Contracts/Projects/CloseSqlProject.cs | 2 - .../Projects/GetCrossPlatformCompatibility.cs | 2 - .../Contracts/Projects/NewSqlProject.cs | 2 - .../Contracts/Projects/OpenSqlProject.cs | 2 - .../SqlCmdVariables/DeleteSqlCmdVariable.cs | 4 +- .../SqlCmdVariables/UpdateSqlCmdvariable.cs | 2 - .../SqlObjectScripts/AddSqlObjectScript.cs | 2 - .../SqlObjectScripts/DeleteSqlObjectScript.cs | 2 - .../ExcludeSqlObjectScript.cs | 2 - .../SqlProjects/SqlProjectsService.cs | 90 ++++++--- .../SqlProjects/SqlProjectsServiceTests.cs | 179 ++++++++++++++---- .../SqlProjects/SqlProjectTests.cs | 37 ++++ 21 files changed, 293 insertions(+), 99 deletions(-) delete mode 100644 bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8086.0-alpha.nupkg create mode 100644 bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8093.0-alpha.nupkg create mode 100644 src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddUserDatabaseReferenceParams.cs create mode 100644 test/Microsoft.SqlTools.ServiceLayer.UnitTests/SqlProjects/SqlProjectTests.cs diff --git a/Packages.props b/Packages.props index 5912fb2f..d662de1e 100644 --- a/Packages.props +++ b/Packages.props @@ -21,7 +21,7 @@ - + diff --git a/bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8086.0-alpha.nupkg b/bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8086.0-alpha.nupkg deleted file mode 100644 index d9a24430088d960b1ebc8d80cc3f8459d0de8e86..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 52560 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

c&SxG|C*988rJdi$`)JIUP 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
bqe1Tq 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 diff --git a/bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8093.0-alpha.nupkg b/bin/nuget/Microsoft.SqlServer.DacFx.Projects.161.8093.0-alpha.nupkg new file mode 100644 index 0000000000000000000000000000000000000000..9fef77346a5d880154276449de3326ddf7cd5ae1 GIT binary patch literal 52711 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 Y@rp9gpe-*?eGd /// Parameters for adding a Dacpac reference to a SQL project /// - public class AddDacpacReferenceParams : AddDatabaseReferenceParams + public class AddDacpacReferenceParams : AddUserDatabaseReferenceParams { ///

/// Path to the .dacpac file /// public string DacpacPath { get; set; } - - /// - /// SQLCMD variable name for specifying the other server this reference is to, if different from that of the current project. - /// If this is set, DatabaseVariable must also be set. - /// - public string? ServerVariable { get; set; } } public class AddDacpacReferenceRequest diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddDatabaseReferenceParams.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddDatabaseReferenceParams.cs index ddad37a0..1a6a18d5 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddDatabaseReferenceParams.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddDatabaseReferenceParams.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts { /// @@ -18,8 +16,8 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts public bool SuppressMissingDependencies { get; set; } /// - /// SQLCMD variable name for specifying the other database this reference is to, if different from that of the current project + /// Literal name used to reference another database in the same server, if not using SQLCMD variables /// - public string? DatabaseVariable { get; set; } + public string? DatabaseLiteral { get; set; } } } \ No newline at end of file diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSqlProjectReferenceParams.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSqlProjectReferenceParams.cs index 1e96aa5c..25343441 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSqlProjectReferenceParams.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSqlProjectReferenceParams.cs @@ -13,7 +13,7 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts /// /// Parameters for adding a reference to another SQL project /// - public class AddSqlProjectReferenceParams : AddDatabaseReferenceParams + public class AddSqlProjectReferenceParams : AddUserDatabaseReferenceParams { /// /// Path to the referenced .sqlproj file @@ -23,13 +23,7 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts /// /// GUID for the referenced SQL project /// - public string? ProjectGuid { get; set; } - - /// - /// SQLCMD variable name for specifying the other server this reference is to, if different from that of the current project. - /// If this is set, DatabaseVariable must also be set. - /// - public string? ServerVariable { get; set; } + public string ProjectGuid { get; set; } } diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSystemDatabaseReference.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSystemDatabaseReference.cs index 83b1fc7e..95951cf5 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSystemDatabaseReference.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddSystemDatabaseReference.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlServer.Dac.Projects; using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddUserDatabaseReferenceParams.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddUserDatabaseReferenceParams.cs new file mode 100644 index 00000000..17420ac7 --- /dev/null +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/DatabaseReferences/AddUserDatabaseReferenceParams.cs @@ -0,0 +1,36 @@ +// +// Copyright (c) Microsoft. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. +// + +using System; + +namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts +{ + public abstract class AddUserDatabaseReferenceParams : AddDatabaseReferenceParams + { + /// + /// SQLCMD variable name for specifying the other database this reference is to, if different from that of the current project + /// + public string? DatabaseVariable { get; set; } + + /// + /// SQLCMD variable name for specifying the other server this reference is to, if different from that of the current project. + /// If this is set, DatabaseVariable must also be set. + /// + public string? ServerVariable { get; set; } + + /// + /// Throws if either both DatabaseVariable and DatabaseLiteral are set. This only validates + /// what is necessary for Tools Service. The DacFx Projects library does comprehensive validation. + /// + /// + internal void Validate() + { + if (DatabaseVariable != null && DatabaseLiteral != null) + { + throw new ArgumentException($"Both {nameof(DatabaseVariable)} and {nameof(DatabaseLiteral)} cannot be set."); + } + } + } +} diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Folders/AddFolder.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Folders/AddFolder.cs index 8b5de800..b591e690 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Folders/AddFolder.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Folders/AddFolder.cs @@ -3,6 +3,8 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // +#nullable disable + using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/CloseSqlProject.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/CloseSqlProject.cs index a00688ca..f6b3d7d1 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/CloseSqlProject.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/CloseSqlProject.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/GetCrossPlatformCompatibility.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/GetCrossPlatformCompatibility.cs index cd6bbdd4..8c221450 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/GetCrossPlatformCompatibility.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/GetCrossPlatformCompatibility.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/NewSqlProject.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/NewSqlProject.cs index 7a01457c..5bb93594 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/NewSqlProject.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/NewSqlProject.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlServer.Dac.Projects; using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/OpenSqlProject.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/OpenSqlProject.cs index 8d7088f0..3d0af8e5 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/OpenSqlProject.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/Projects/OpenSqlProject.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/DeleteSqlCmdVariable.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/DeleteSqlCmdVariable.cs index 492e8b33..84331c30 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/DeleteSqlCmdVariable.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/DeleteSqlCmdVariable.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; @@ -18,7 +16,7 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts /// /// Name of the SQLCMD variable to be deleted /// - public string Name { get; set; } + public string? Name { get; set; } } public class DeleteSqlCmdVariableRequest diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/UpdateSqlCmdvariable.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/UpdateSqlCmdvariable.cs index 504a9918..05bae35a 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/UpdateSqlCmdvariable.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlCmdVariables/UpdateSqlCmdvariable.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/AddSqlObjectScript.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/AddSqlObjectScript.cs index 2396ba93..54d828ac 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/AddSqlObjectScript.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/AddSqlObjectScript.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/DeleteSqlObjectScript.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/DeleteSqlObjectScript.cs index 2615ec79..fce63055 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/DeleteSqlObjectScript.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/DeleteSqlObjectScript.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/ExcludeSqlObjectScript.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/ExcludeSqlObjectScript.cs index b48aaa13..2405e7a2 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/ExcludeSqlObjectScript.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/Contracts/SqlObjectScripts/ExcludeSqlObjectScript.cs @@ -3,8 +3,6 @@ // Licensed under the MIT license. See LICENSE file in the project root for full license information. // -#nullable disable - using Microsoft.SqlTools.Hosting.Protocol.Contracts; using Microsoft.SqlTools.ServiceLayer.Utility; diff --git a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/SqlProjectsService.cs b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/SqlProjectsService.cs index 666984de..9663f92f 100644 --- a/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/SqlProjectsService.cs +++ b/src/Microsoft.SqlTools.ServiceLayer/SqlProjects/SqlProjectsService.cs @@ -81,20 +81,20 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects internal async Task HandleOpenSqlProjectRequest(SqlProjectParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!), requestContext); } internal async Task HandleCloseSqlProjectRequest(SqlProjectParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => Projects.TryRemove(requestParams.ProjectUri, out _), requestContext); + await RunWithErrorHandling(() => Projects.TryRemove(requestParams.ProjectUri!, out _), requestContext); } internal async Task HandleNewSqlProjectRequest(NewSqlProjectParams requestParams, RequestContext requestContext) { await RunWithErrorHandling(async () => { - await SqlProject.CreateProjectAsync(requestParams.ProjectUri, new CreateSqlProjectParams() { ProjectType = requestParams.SqlProjectType, DspVersion = requestParams.DatabaseSchemaProvider }); - GetProject(requestParams.ProjectUri); // load into the cache + await SqlProject.CreateProjectAsync(requestParams.ProjectUri!, new CreateSqlProjectParams() { ProjectType = requestParams.SqlProjectType, DspVersion = requestParams.DatabaseSchemaProvider }); + GetProject(requestParams.ProjectUri!); // load into the cache }, requestContext); } @@ -106,14 +106,14 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects { Success = true, ErrorMessage = null, - IsCrossPlatformCompatible = GetProject(requestParams.ProjectUri).CrossPlatformCompatible + IsCrossPlatformCompatible = GetProject(requestParams.ProjectUri!).CrossPlatformCompatible }; }, requestContext); } internal async Task HandleUpdateProjectForCrossPlatformRequest(SqlProjectParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).UpdateForCrossPlatform(), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).UpdateForCrossPlatform(), requestContext); } #endregion @@ -124,17 +124,17 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects internal async Task HandleAddSqlObjectScriptRequest(SqlProjectScriptParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).SqlObjectScripts.Add(new SqlObjectScript(requestParams.Path)), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).SqlObjectScripts.Add(new SqlObjectScript(requestParams.Path!)), requestContext); } internal async Task HandleDeleteSqlObjectScriptRequest(SqlProjectScriptParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).SqlObjectScripts.Delete(requestParams.Path), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).SqlObjectScripts.Delete(requestParams.Path!), requestContext); } internal async Task HandleExcludeSqlObjectScriptRequest(SqlProjectScriptParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).SqlObjectScripts.Exclude(requestParams.Path), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).SqlObjectScripts.Exclude(requestParams.Path!), requestContext); } #endregion @@ -193,11 +193,11 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects internal async Task HandleAddSystemDatabaseReferenceRequest(AddSystemDatabaseReferenceParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).DatabaseReferences.Add( + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).DatabaseReferences.Add( new SystemDatabaseReference( requestParams.SystemDatabase, requestParams.SuppressMissingDependencies, - requestParams.DatabaseVariable)), + requestParams.DatabaseLiteral)), requestContext); } @@ -205,14 +205,32 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects { await RunWithErrorHandling(() => { - SqlProject project = GetProject(requestParams.ProjectUri); + requestParams.Validate(); - project.DatabaseReferences.Add( - new DacpacReference( + SqlProject project = GetProject(requestParams.ProjectUri!); + DacpacReference reference; + + if (requestParams.DatabaseLiteral != null) // same server, different database via database name literal + { + reference = new DacpacReference( requestParams.DacpacPath, requestParams.SuppressMissingDependencies, - project.SqlCmdVariables.Get(requestParams.DatabaseVariable), - project.SqlCmdVariables.Get(requestParams.ServerVariable))); + requestParams.DatabaseLiteral); + } + else if (requestParams.DatabaseVariable != null) // different database, possibly different server via sqlcmdvar + { + reference = new DacpacReference( + requestParams.DacpacPath, + requestParams.SuppressMissingDependencies, + project.SqlCmdVariables.Get(requestParams.DatabaseVariable!), + requestParams.ServerVariable != null ? project.SqlCmdVariables.Get(requestParams.ServerVariable) : null); + } + else // same database + { + reference = new DacpacReference(requestParams.DacpacPath, requestParams.SuppressMissingDependencies); + } + + project.DatabaseReferences.Add(reference); }, requestContext); } @@ -220,42 +238,64 @@ namespace Microsoft.SqlTools.ServiceLayer.SqlProjects { await RunWithErrorHandling(() => { - SqlProject project = GetProject(requestParams.ProjectUri); + requestParams.Validate(); - project.DatabaseReferences.Add( - new SqlProjectReference( + SqlProject project = GetProject(requestParams.ProjectUri!); + SqlProjectReference reference; + + if (requestParams.DatabaseLiteral != null) // same server, different database via database name literal + { + reference = new SqlProjectReference( requestParams.ProjectPath, requestParams.ProjectGuid, requestParams.SuppressMissingDependencies, - project.SqlCmdVariables.Get(requestParams.DatabaseVariable), - project.SqlCmdVariables.Get(requestParams.ServerVariable))); + requestParams.DatabaseLiteral); + } + else if (requestParams.DatabaseVariable != null) // different database, possibly different server via sqlcmdvar + { + reference = new SqlProjectReference( + requestParams.ProjectPath, + requestParams.ProjectGuid, requestParams.SuppressMissingDependencies, + project.SqlCmdVariables.Get(requestParams.DatabaseVariable!), + requestParams.ServerVariable != null ? project.SqlCmdVariables.Get(requestParams.ServerVariable) : null); + } + else // same database + { + reference = new SqlProjectReference( + requestParams.ProjectPath, + requestParams.ProjectGuid, + requestParams.SuppressMissingDependencies); + } + + project.DatabaseReferences.Add(reference); }, requestContext); } internal async Task HandleDeleteDatabaseReferenceRequest(DeleteDatabaseReferenceParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).DatabaseReferences.Delete(requestParams.Name), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).DatabaseReferences.Delete(requestParams.Name!), requestContext); } #endregion + #region SQLCMD variable functions internal async Task HandleAddSqlCmdVariableRequest(AddSqlCmdVariableParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).SqlCmdVariables.Add(new SqlCmdVariable(requestParams.Name, requestParams.DefaultValue, requestParams.Value)), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).SqlCmdVariables.Add(new SqlCmdVariable(requestParams.Name, requestParams.DefaultValue, requestParams.Value)), requestContext); } internal async Task HandleDeleteSqlCmdVariableRequest(DeleteSqlCmdVariableParams requestParams, RequestContext requestContext) { - await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri).SqlCmdVariables.Delete(requestParams.Name), requestContext); + await RunWithErrorHandling(() => GetProject(requestParams.ProjectUri!).SqlCmdVariables.Delete(requestParams.Name), requestContext); } internal async Task HandleUpdateSqlCmdVariableRequest(AddSqlCmdVariableParams requestParams, RequestContext requestContext) { await RunWithErrorHandling(() => { - SqlProject project = GetProject(requestParams.ProjectUri); + SqlProject project = GetProject(requestParams.ProjectUri!); project.SqlCmdVariables.Delete(requestParams.Name); // idempotent (won't throw if doesn't exist) project.SqlCmdVariables.Add(new SqlCmdVariable(requestParams.Name, requestParams.DefaultValue, requestParams.Value)); }, requestContext); diff --git a/test/Microsoft.SqlTools.ServiceLayer.IntegrationTests/SqlProjects/SqlProjectsServiceTests.cs b/test/Microsoft.SqlTools.ServiceLayer.IntegrationTests/SqlProjects/SqlProjectsServiceTests.cs index baf32e57..eb5d037d 100644 --- a/test/Microsoft.SqlTools.ServiceLayer.IntegrationTests/SqlProjects/SqlProjectsServiceTests.cs +++ b/test/Microsoft.SqlTools.ServiceLayer.IntegrationTests/SqlProjects/SqlProjectsServiceTests.cs @@ -283,40 +283,77 @@ namespace Microsoft.SqlTools.ServiceLayer.IntegrationTests.SqlProjects Assert.IsFalse(File.Exists(scriptFullPath), $"{scriptFullPath} expected to have been deleted from disk"); } + #region Database reference tests + [Test] - public async Task TestDatabaseReferenceAddDelete() + public async Task TestDatabaseReferenceDelete() { - // Setup - SqlProjectsService service = new(); - string projectUri = await service.CreateSqlProject(); + var (service, projectUri, _, _) = await SetUpDatabaseReferenceTest(); - SqlCmdVariable databaseVar = new SqlCmdVariable("$(OtherDb)", "OtherDbDefaultValue", "OtherDbValue"); - SqlCmdVariable serverVar = new SqlCmdVariable("$(OtherServer)", "OtherServerDefaultValue", "OtherServerValue"); + // directly add a reference so there's something to delete + service.Projects[projectUri].DatabaseReferences.Add(new SystemDatabaseReference(SystemDatabase.Master, suppressMissingDependencies: true)); - service.Projects[projectUri].SqlCmdVariables.Add(databaseVar); - service.Projects[projectUri].SqlCmdVariables.Add(serverVar); + Assert.AreEqual(1, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding reference"); - Assert.AreEqual(0, service.Projects[projectUri].DatabaseReferences.Count, "Baseline number of database references"); + MockRequest requestMock = new(); + await service.HandleDeleteDatabaseReferenceRequest(new DeleteDatabaseReferenceParams() + { + ProjectUri = projectUri, + Name = SystemDatabase.Master.ToString() + }, requestMock.Object); + + requestMock.AssertSuccess(nameof(service.HandleDeleteDatabaseReferenceRequest)); + Assert.AreEqual(0, service.Projects[projectUri].DatabaseReferences.Count, "Database references after deleting reference"); + } + + [Test] + public async Task TestSystemDatabaseReferenceAdd() + { + var (service, projectUri, _, _) = await SetUpDatabaseReferenceTest(); - // Validate adding a system database reference MockRequest requestMock = new(); await service.HandleAddSystemDatabaseReferenceRequest(new AddSystemDatabaseReferenceParams() { ProjectUri = projectUri, SystemDatabase = SystemDatabase.MSDB, - DatabaseVariable = "$(EmEssDeeBee)", + DatabaseLiteral = "EmEssDeeBee", SuppressMissingDependencies = false }, requestMock.Object); requestMock.AssertSuccess(nameof(service.HandleAddSystemDatabaseReferenceRequest)); Assert.AreEqual(1, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding system db reference"); - SystemDatabaseReference systemDbRef = (SystemDatabaseReference)service.Projects[projectUri].DatabaseReferences.First(x => x is SystemDatabaseReference); + SystemDatabaseReference systemDbRef = (SystemDatabaseReference)service.Projects[projectUri].DatabaseReferences.Get(SystemDatabase.MSDB.ToString()); Assert.AreEqual(SystemDatabase.MSDB, systemDbRef.SystemDb, "Referenced system DB"); - Assert.AreEqual("$(EmEssDeeBee)", systemDbRef.DatabaseVariableLiteralName); + Assert.AreEqual("EmEssDeeBee", systemDbRef.DatabaseVariableLiteralName); Assert.IsFalse(systemDbRef.SuppressMissingDependencies, nameof(systemDbRef.SuppressMissingDependencies)); + } - // Validate adding a dacpac reference - string mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "OtherDatabase.dacpac"); + [Test] + public async Task TestDacpacReferenceAdd() + { + var (service, projectUri, databaseVar, serverVar) = await SetUpDatabaseReferenceTest(); + + // Validate adding a dacpac reference on the same server + string mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "OtherDatabaseSameServer.dacpac"); + + MockRequest requestMock = new(); + await service.HandleAddDacpacReferenceRequest(new AddDacpacReferenceParams() + { + ProjectUri = projectUri, + DacpacPath = mockReferencePath, + SuppressMissingDependencies = false + }, requestMock.Object); + + requestMock.AssertSuccess(nameof(service.HandleAddDacpacReferenceRequest), "same server"); + Assert.AreEqual(1, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding dacpac reference (same server)"); + DacpacReference dacpacRef = (DacpacReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); + Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), dacpacRef.DacpacPath, "Referenced dacpac"); + Assert.IsFalse(dacpacRef.SuppressMissingDependencies, nameof(dacpacRef.SuppressMissingDependencies)); + Assert.IsNull(dacpacRef.DatabaseVariableLiteralName, nameof(dacpacRef.DatabaseVariableLiteralName)); + Assert.IsNull(dacpacRef.DatabaseVariable, nameof(dacpacRef.DatabaseVariable)); + + // Validate adding a dacpac reference via SQLCMD variable + mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "OtherDatabaseSqlCmd.dacpac"); requestMock = new(); await service.HandleAddDacpacReferenceRequest(new AddDacpacReferenceParams() @@ -328,16 +365,60 @@ namespace Microsoft.SqlTools.ServiceLayer.IntegrationTests.SqlProjects ServerVariable = serverVar.Name }, requestMock.Object); - requestMock.AssertSuccess(nameof(service.HandleAddDacpacReferenceRequest)); - Assert.AreEqual(2, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding dacpac reference"); - DacpacReference dacpacRef = (DacpacReference)service.Projects[projectUri].DatabaseReferences.First(x => x is DacpacReference); + requestMock.AssertSuccess(nameof(service.HandleAddDacpacReferenceRequest), "sqlcmdvar"); + Assert.AreEqual(2, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding dacpac reference (sqlcmdvar)"); + dacpacRef = (DacpacReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), dacpacRef.DacpacPath, "Referenced dacpac"); - Assert.AreEqual(databaseVar.Name, dacpacRef.DatabaseVariable.VarName); - Assert.AreEqual(serverVar.Name, dacpacRef.ServerVariable.VarName); + Assert.AreEqual(databaseVar.Name, dacpacRef.DatabaseVariable!.VarName); + Assert.AreEqual(serverVar.Name, dacpacRef.ServerVariable!.VarName); Assert.IsFalse(dacpacRef.SuppressMissingDependencies, nameof(dacpacRef.SuppressMissingDependencies)); - // Validate adding a project reference - mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "..", "OtherDatabase", "OtherDatabase.sqlproj"); + // Validate adding a dacpac reference via database literal + mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "OtherDatabaseLiteral.dacpac"); + + requestMock = new(); + await service.HandleAddDacpacReferenceRequest(new AddDacpacReferenceParams() + { + ProjectUri = projectUri, + DacpacPath = mockReferencePath, + SuppressMissingDependencies = false, + DatabaseLiteral = "DacpacLiteral" + }, requestMock.Object); + + requestMock.AssertSuccess(nameof(service.HandleAddDacpacReferenceRequest), "db literal"); + Assert.AreEqual(3, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding dacpac reference (db literal)"); + dacpacRef = (DacpacReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); + Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), dacpacRef.DacpacPath, "Referenced dacpac"); + Assert.AreEqual("DacpacLiteral", dacpacRef.DatabaseVariableLiteralName, nameof(dacpacRef.DatabaseVariableLiteralName)); + Assert.IsFalse(dacpacRef.SuppressMissingDependencies, nameof(dacpacRef.SuppressMissingDependencies)); + } + + [Test] + public async Task TestSqlProjectReferenceAdd() + { + var (service, projectUri, databaseVar, serverVar) = await SetUpDatabaseReferenceTest(); + + // Validate adding a project reference on the same server + string mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "..", "SameDatabase", "SameDatabaseSqlCmd.sqlproj"); + + MockRequest requestMock = new(); + await service.HandleAddSqlProjectReferenceRequest(new AddSqlProjectReferenceParams() + { + ProjectUri = projectUri, + ProjectPath = mockReferencePath, + SuppressMissingDependencies = false + }, requestMock.Object); + + requestMock.AssertSuccess(nameof(service.HandleAddSqlProjectReferenceRequest), "same server"); + Assert.AreEqual(1, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding SQL project reference (same server)"); + SqlProjectReference projectRef = (SqlProjectReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); + Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), projectRef.ProjectPath, "Referenced project"); + Assert.IsFalse(projectRef.SuppressMissingDependencies, nameof(projectRef.SuppressMissingDependencies)); + Assert.IsNull(projectRef.DatabaseVariableLiteralName, nameof(projectRef.DatabaseVariableLiteralName)); + Assert.IsNull(projectRef.DatabaseVariable, nameof(projectRef.DatabaseVariable)); + + // Validate adding a project reference via SQLCMD variable + mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "..", "OtherDatabase", "OtherDatabaseSqlCmd.sqlproj"); requestMock = new(); await service.HandleAddSqlProjectReferenceRequest(new AddSqlProjectReferenceParams() @@ -351,27 +432,38 @@ namespace Microsoft.SqlTools.ServiceLayer.IntegrationTests.SqlProjects }, requestMock.Object); requestMock.AssertSuccess(nameof(service.HandleAddSqlProjectReferenceRequest)); - Assert.AreEqual(3, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding SQL project reference"); - SqlProjectReference projectRef = (SqlProjectReference)service.Projects[projectUri].DatabaseReferences.First(x => x is SqlProjectReference); - Assert.AreEqual(mockReferencePath, projectRef.ProjectPath, "Referenced project"); + Assert.AreEqual(2, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding SQL project reference (sqlcmdvar)"); + projectRef = (SqlProjectReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); + Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), projectRef.ProjectPath, "Referenced project"); Assert.AreEqual(TEST_GUID, projectRef.ProjectGuid, "Referenced project GUID"); - Assert.AreEqual(databaseVar.Name, projectRef.DatabaseVariable.VarName); - Assert.AreEqual(serverVar.Name, projectRef.ServerVariable.VarName); + Assert.AreEqual(databaseVar.Name, projectRef.DatabaseVariable!.VarName); + Assert.AreEqual(serverVar.Name, projectRef.ServerVariable!.VarName); Assert.IsFalse(projectRef.SuppressMissingDependencies, nameof(projectRef.SuppressMissingDependencies)); - // Validate deleting a reference + // Validate adding a project reference via database literal + mockReferencePath = Path.Join(Path.GetDirectoryName(projectUri), "..", "OtherDatabase", "OtherDatabaseLiteral.sqlproj"); + requestMock = new(); - await service.HandleDeleteDatabaseReferenceRequest(new DeleteDatabaseReferenceParams() + await service.HandleAddSqlProjectReferenceRequest(new AddSqlProjectReferenceParams() { ProjectUri = projectUri, - Name = mockReferencePath + ProjectPath = mockReferencePath, + ProjectGuid = TEST_GUID, + SuppressMissingDependencies = false, + DatabaseLiteral = "ProjectLiteral" }, requestMock.Object); - requestMock.AssertSuccess(nameof(service.HandleDeleteDatabaseReferenceRequest)); - Assert.AreEqual(2, service.Projects[projectUri].DatabaseReferences.Count, "Database references after deleting SQL project reference"); - Assert.IsFalse(service.Projects[projectUri].DatabaseReferences.Any(x => x is SqlProjectReference), "Database references list expected to not contain the SQL Project reference"); + requestMock.AssertSuccess(nameof(service.HandleAddSqlProjectReferenceRequest)); + Assert.AreEqual(3, service.Projects[projectUri].DatabaseReferences.Count, "Database references after adding SQL project reference (db literal)"); + projectRef = (SqlProjectReference)service.Projects[projectUri].DatabaseReferences.Get(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT)); + Assert.AreEqual(FileUtils.NormalizePath(mockReferencePath, PlatformID.Win32NT), projectRef.ProjectPath, "Referenced project"); + Assert.AreEqual(TEST_GUID, projectRef.ProjectGuid, "Referenced project GUID"); + Assert.AreEqual("ProjectLiteral", projectRef.DatabaseVariableLiteralName); + Assert.IsFalse(projectRef.SuppressMissingDependencies, nameof(projectRef.SuppressMissingDependencies)); } + #endregion + [Test] public async Task TestFolderAddDelete() { @@ -497,6 +589,27 @@ namespace Microsoft.SqlTools.ServiceLayer.IntegrationTests.SqlProjects getRequestMock.AssertSuccess(nameof(service.HandleGetCrossPlatformCompatibilityRequest)); Assert.IsTrue(((GetCrossPlatformCompatiblityResult)getRequestMock.Result).IsCrossPlatformCompatible, "Input file should be cross-platform compatible after conversion"); } + + #region Helpers + + private async Task<(SqlProjectsService Service, string ProjectUri, SqlCmdVariable DatabaseVar, SqlCmdVariable ServerVar)> SetUpDatabaseReferenceTest() + { + // Setup + SqlProjectsService service = new(); + string projectUri = await service.CreateSqlProject(); + + SqlCmdVariable databaseVar = new SqlCmdVariable("$(OtherDb)", "OtherDbDefaultValue", "OtherDbValue"); + SqlCmdVariable serverVar = new SqlCmdVariable("$(OtherServer)", "OtherServerDefaultValue", "OtherServerValue"); + + service.Projects[projectUri].SqlCmdVariables.Add(databaseVar); + service.Projects[projectUri].SqlCmdVariables.Add(serverVar); + + Assert.AreEqual(0, service.Projects[projectUri].DatabaseReferences.Count, "Baseline number of database references"); + + return (service, projectUri, databaseVar, serverVar); + } + + #endregion } internal static class SqlProjectsExtensions diff --git a/test/Microsoft.SqlTools.ServiceLayer.UnitTests/SqlProjects/SqlProjectTests.cs b/test/Microsoft.SqlTools.ServiceLayer.UnitTests/SqlProjects/SqlProjectTests.cs new file mode 100644 index 00000000..6bd26308 --- /dev/null +++ b/test/Microsoft.SqlTools.ServiceLayer.UnitTests/SqlProjects/SqlProjectTests.cs @@ -0,0 +1,37 @@ +// +// Copyright (c) Microsoft. All rights reserved. +// Licensed under the MIT license. See LICENSE file in the project root for full license information. +// + +using System; +using Microsoft.SqlTools.ServiceLayer.SqlProjects.Contracts; +using NUnit.Framework; + +namespace Microsoft.SqlTools.ServiceLayer.UnitTests.SqlProjects +{ + public class SqlProjectTests + { + [Test] + public void DatabaseReferenceValidationTest() + { + // Verify that Validate() throws when both DatabaseLiteral and DatabaseVariable are set + AddUserDatabaseReferenceParams reference = new AddDacpacReferenceParams() // any concrete class will do + { + DatabaseLiteral = "DatabaseName", + DatabaseVariable = "$(DatabaseVariable)" + }; + + Assert.Throws(() => reference.Validate(), $"Validate() for a reference with both {nameof(reference.DatabaseLiteral)} and {nameof(reference.DatabaseVariable)} should have failed"); + + // Verify that Validate() passes any other time + reference = new AddDacpacReferenceParams() { DatabaseLiteral = "DatabaseName" }; + reference.Validate(); + + reference = new AddDacpacReferenceParams() { DatabaseVariable = "$(DatabaseVariable)" }; + reference.Validate(); + + reference = new AddDacpacReferenceParams(); + reference.Validate(); + } + } +}