Search code examples
c#.netsql-server-data-toolsdacpac

Deploy .dacpac missing assembly reference


I have an SSDT (Sql Server Database Project) which refers to an external .dll (C# Class Library) in order to provide some CLR functions. If I Deploy/Publish locally everything works fine but remotely, using Microsoft.SqlServer.Dac.DacPackage it bombs.

The problem, after further investigation, is inside the .dacpac generated. Somehow my .dacpac file has an "hardcoded" reference path which refers to my local DEV environment but when it runs on TFS the source path is different.

I deploy the .dacpac using this class:

    var file = FileFinder.GetFirstFile("MyFile.dacpac");
    var package = DacPackage.Load(file);
    var deployOptions = new DacDeployOptions
    {
        BlockOnPossibleDataLoss = false,
        CreateNewDatabase = true,
        IncludeCompositeObjects = true
    };

    var dacService = new DacServices(ApplicationConfiguration.GetConnection("MyConn"));            

    dacService.Deploy(
        package: package,
        targetDatabaseName: "MyDB", 
        upgradeExisting: true, 
        options: deployOptions);
}

And remotely the error is always the same, even if the .dlls are in the same folder of the .dacpac file:

No file was supplied for reference Utilities.dll; 
deployment might fail. 
When C:\MyFile.dacpac was created, the original referenced file was located **C:\DEV\MAIN\UTILITIES.DLL**.

Which of course is my local dev path.

I am using: DacDeployOptions.IncludeCompositeObjects but nothing changes.


Solution

  • Dacpacs will look for referenced assemblies in the following order:

    • The same directory as the dacpac is placed in. So if your build system copies the dacpac and references to 1 directory, deploy will work
    • The original file path, as a fallback mechanism

    Essentially you should ensure a dacpac and all references are in 1 directory before deploying. The build system should be doing this for you automatically, but if not you should update to copy to a directory (or create a nuget package as part of the build that does all this for you).