I have a wpf project for which the installer is created by wix setup project. the wix setup project is compiled to get the .msi. The .exe is generated from the .msi file using wix bootstrapper project.Now my question is how to get the assembly version [assembly: AssemblyFileVersion("x.x.x.xx")] form wpf .cs file?
Andy is right, you will not be able to pull the version number from a .cs file as WiX does not compile or know anything to do with the C# code.
What you want to do is version your main executable file (presumably the .csproj application) using the assembly version properties. (These can be found in the project properties)
1) In the Product.wxs add said main executable as a file in the installer.
<Component Id='MainExecutable' Guid='*'>
<File Id='MainExe' Name='MainExe.exe' Source='Path-to-exe' KeyPath='yes' />
</Component>
2) Bind the version of the .msi to this main executable. This is done in the Version attribute of the Product element.
<Product Id="*" Name="My Product Name" Language="1033" Version="!(bind.FileVersion.MainExe)" Manufacturer="Debabrata" UpgradeCode="PUT-GUID-HERE">
Not that the value after the FileVersion is the ID of your file. This is important.
Now to use this version number in the bootstrapper project - the process is very similar.
1) Add the MSI to the bootstrapper.
<MsiPackage SourceFile="Path-to-msi" Id="MyMSI">
2) In the Version attribute of the Bundle element the binding should be.
<Bundle Name="My Bundle" Version="!(bind.packageVersion.MyMSI)">
Again, note how the ID matches.
Hope this helps!
I have created a C# WinForms Application which depends on the .NET Framework Version 4.6.1 and GhostScript 9.2.1 (32-bit Windows). I made a simple Windows Installer ( .msi file) for the WinForms App, but the GhostScript library refused to install. Therefore, I decided to make a bundle installer using the WiX bootstrapper.
In the bootstrapper project I packaged the GhostScript exe installer and the simple msi installer from earlier. I think I also took care of the .NET framework in the first few lines of the bootstrapper.
Now, I'm still facing an issue while with the Bootstrap Installer. The issue is that the installation skips over the msi installer. How do I get the Bootstrap installation to successfully complete?
Here is the XML for the bootstrapper project:
<?xml version="1.0" encoding="UTF-8"?>
<Wix xmlns="http://schemas.microsoft.com/wix/2006/wi">
<Bundle Name="Bootstrapper1" Version="1.0.0.0" Manufacturer="POD" UpgradeCode="390cbc0b-980b-4f35-a9de-a11228f75b69">
<BootstrapperApplicationRef Id="WixStandardBootstrapperApplication.RtfLicense" />
<PayloadGroup Id="NetFx461RedistPayload">
<Payload Name="redist\NDP461-KB3102436-x86-x64-AllOS-ENU.exe"
SourceFile="C:\Users\Admin\Downloads\NDP461-KB3102436-x86-x64-AllOS-ENU.exe"/>
</PayloadGroup>
<Chain>
<!-- TODO: Define the list of chained packages. -->
<!-- <MsiPackage SourceFile="path\to\your.msi" /> -->
<PackageGroupRef Id="NetFx461Web"/>
<ExePackage Id="Ghostscript_32_bit_Version_9.2.1"
Cache="yes"
Compressed="yes"
PerMachine="yes"
Permanent="yes"
Vital="yes"
SourceFile="C:\Users\Admin\Downloads\gs921w32new.exe"
InstallCommand="/passive /norestart" />
<MsiPackage Id="POD_Measuring_Tool"
Cache="yes"
Compressed="yes"
Permanent="yes"
Vital="yes"
SourceFile="C:\Users\Admin\Documents\POD\Workspace Folder\c# projects\6lumber\toolPOD\Debug\toolPOD.msi" />
</Chain>
</Bundle>
</Wix>
I reference the WixBalExtension and the WixNetFxExtension, and the msi file and ghostscript exe are from my computer.
The issue is that the installation skips over the msi installer.
This may indicate that the product is already install. MsiPackage will automatically detect if the msi is already installed by checking the product code in the registry.
The MsiPackage/#Permanent attribute will also mean that your product will not be removed when uninstalling your Bootstrapper - so check that you did remove your msi manually and logging helps with the -l logfile.txt switch.
I'm building an ASP.NET Core 2.0 Web API application that is hosted in an Ubuntu environment. So far, I've had great success getting things building and running (for the .NET Core app) in Ubuntu.
For the database, I have a SqlProj included in my solution. The project includes typical things such as tables, SPs, and pre/post deployment scripts. I'm using the following command (on my Windows-based dev machine) to build and deploy this project:
msbuild .\MyProject.DB.sqlproj /t:Build /t:Publish /P:SqlPublishProfilePath="./PublishProfiles/MyProject.DB.publish.xml"
When I take this approach, everything builds and deploys properly; however, since I will be taking advantage of the .NET Core CLI commands + CI/CD that targets an Ubuntu environment, I'd like to do something more like:
dotnet msbuild .\MyProject.DB.sqlproj /t:Build /t:Publish /P:SqlPublishProfilePath="./PublishProfiles/MyProject.DB.publish.xml"
In Windows, I immediately get the error:
error MSB4019: The imported project "C:\Program Files\dotnet\sdk\2.1.4\Microsoft\VisualStudio\v11.0\SSDT\Microsoft.Data.Tools.Schema.SqlTasks.targets" was not found. Confirm that the path in the <Import> declaration is correct, and that the file exists on disk.
Basically, what I'm asking is how to successfully build and deploy a SqlProj project in an Ubuntu environment. I've tried Googling, but I have had zero luck thus far. All of the similar issues that I've found were for individuals who were editing their .proj file to target their VS folder's SSDT. All of these individuals were fixing the issue in Windows. This approach will not work in Ubuntu, since the targets file uses Windows registry keys.
EDIT: I'm aware that SSDT is needed in order to perform such a deployment using MSBuild. I've found no evidence that installing/using SSDT is even possible in Ubuntu. If it is not, perhaps there is an alternative solution?
FYI, I'm aware that using a code-first approach with EF Core is possible. I'm attempting to take the raw SP approach (along with leveraging indexes) and keep track of all of my code using SqlProj instead. This will all be stored and CI/CDed from a Git repo.
You can use this NuGet package to deploy without installing SSDT https://www.nuget.org/packages/Microsoft.Data.Tools.Msbuild
I don't know if it will run on Ubuntu or integrate at all with the dotnet cli
My 2020 Solution
I would like to revisit this in 2020 with an updated answer to my original question.
I have taken a different approach to building an deploying SQL Server projects. My current approach is to build a pipeline that uses a vs2017-win2016 agent and use this to build a .dacpac. From there, you build a deployment pipeline to deploy the dacpac (from your artifact drop) out to the SQL Server instance.
This approach better accommodates DevOps methodologies and removes the manual process associated with my previous solution.
You can read more about this here:
https://learn.microsoft.com/en-us/azure/devops/pipelines/apps/aspnet/build-aspnet-dacpac?view=azure-devops
I can't speak to whether or not this will work on Ubuntu, but we recently got through this on a Windows build machine that does not have SSDT installed, using the NuGet package mentioned above. The breakthrough came from piecing together the details in the article below, specifically that using the SDK with MSBuild needed to have environment variables set in order to work.
https://blogs.msdn.microsoft.com/ssdt/2016/08/22/part-5-use-your-own-build-and-deployment-agent/
With that added info, we installed the NuGet package in the root of the solution folder and then wrote a build script in PowerShell. The script sets the environment variables first and then calls MSBuild on the SqlProj file with the appropriate output directory. We don't specifically publish at that point, but instead publish the artifact to Octopus Deploy in our workflow which does the actual deployment.
Again, not sure it will help on Ubuntu, but thought the additional detail might be useful.
As an alternative, it is possible to achieve this with dotnet cli and sqlpackage as explained here using an MSBuild Sdk.
You basically have a database project. Let's call it "DatabaseProject".
You create a new project which is a .NET standard c# library that you can call "DatabaseProject.Build".
Then you can configure you DatabaseProject.Build.csproj as such:
<Project Sdk="MSBuild.Sdk.SqlProj/1.11.4">
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<Configurations>Debug;Release</Configurations>
</PropertyGroup>
<ItemGroup>
<Content Include="..\DatabaseProject\**\*.sql" />
<Content Remove="..\DatabaseProject\bin\*.sql" />
<Content Remove="..\DatabaseProject\**\*.PostDeployment.sql" />
<PostDeploy Include="..\DatabaseProject\**\*.PostDeployment.sql" />
</ItemGroup>
</Project>
Be Aware The version used V1.11.4 is the one that supports the current .NET SDK shipped with visual studio at the time of the edit of this post. Check out the github repo to get the latest nuget version for your projet.
Using dotnet build will generate a dacpac that you will be able to use with either dotnet publish or sqlpackage.
You can then publish to you SqlServer instance.
If you're like me using a linux runner in your CI, you'll probably need SqlServer authentification method and then run either
sqlpackage /Action:Publish \
/SourceFile:\"DatabaseProject.Build/bin/Debug/netstandard2.0/DatabaseProject.Build.dacpac\" \
/TargetServerName:MyDatabaseServerName \
/TargetDatabaseName:MyDatabaseName \
/TargetUser:Username\
/TargetPassword:Password
or using a profile generated by visual studio :
sqlpackage /Action:Publish /Profile:\"DatabaseProject/PublishProfile/MyProfile.publish.xml\" /SourceFile:\"DatabaseProject.Build/bin/Debug/netstandard2.0/DatabaseProject.Build.dacpac\"
or
dotnet publish /p:TargetServerName=MyServerName /p:TargetDatabaseName=MyDatabseName /p:TargetUser=<username> /p:TargetPassword=<password>
Azure Data Studio now has an extension that lets you build database projects (sqlproj) using the dotnet tool. The brains behind building the project lies in the SQL Server Tools package, which is where the extension gets the required "BuildDirectory" DLL and targets dependencies.
Though not documented, if you want to set this up completely headless outside of Azure Data Studio, you can follow their CLI guide, https://learn.microsoft.com/en-us/sql/azure-data-studio/extensions/sql-database-project-extension-build-from-command-line?view=sql-server-ver15, but instead extract the necessary files from the RHEL release in https://github.com/microsoft/sqltoolsservice/releases and then follow the rest of the extension's documentation. Here is a working Dockerfile that demonstrates the approach:
FROM mcr.microsoft.com/dotnet/sdk:6.0
WORKDIR /app
RUN apt-get update \
&& apt-get install -y curl
# SSDT dlls and targets file used by Azure Data Studio Extension can be found in the SQL Tools Service project
RUN curl -sSL -o /tmp/sqltools.tar.gz https://github.com/microsoft/sqltoolsservice/releases/download/v3.0.0-release.181/Microsoft.SqlTools.ServiceLayer-rhel-x64-net6.0.tar.gz
# Extract files that are required per https://learn.microsoft.com/en-us/sql/azure-data-studio/extensions/sql-database-project-extension-build-from-command-line?view=sql-server-ver15
RUN mkdir /tmp/sqltools && tar -xzf /tmp/sqltools.tar.gz -C /tmp/sqltools && \
mkdir /app/BuildDirectory && cd /tmp/sqltools && cp \
Microsoft.Data.SqlClient.dll \
Microsoft.Data.Tools.Schema.Sql.dll \
Microsoft.Data.Tools.Schema.SqlTasks.targets \
Microsoft.Data.Tools.Schema.Tasks.Sql.dll \
Microsoft.Data.Tools.Utilities.dll \
Microsoft.SqlServer.Dac.dll \
Microsoft.SqlServer.Dac.Extensions.dll \
Microsoft.SqlServer.TransactSql.ScriptDom.dll \
Microsoft.SqlServer.Types.dll \
System.ComponentModel.Composition.dll \
System.IO.Packaging.dll \
/app/BuildDirectory && \
rm -r /tmp/sqltools
#dotnet build your-database-project.sqlproj /p:NetCoreBuild=true /p:NETCoreTargetsPath="/app/BuildDirectory"
The commented command at the end shows what you could run inside the container in the directory with your database project.
This can also then be combined with a container utilizing sqlpackage to implement a full dacpac build and publish automation toolset.
As mentioned, the easiest way to build DacPac file on a linux agent is done via MSBuild.Sdk.SqlProj
Go to your database project directory in parallel to .sqlproj file create a directory like DB.Build under it create DB.Build.csproj copy.pase the content as below
<Project Sdk="MSBuild.Sdk.SqlProj/1.1.0"> <!-- This will pull in the required tools and dependencies to build a .dacpac with .NET Core -->
<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
</PropertyGroup>
<ItemGroup>
<Content Include="..\src\DB\masterdata\**\*.sql" /> <!-- link in the new .csproj to the .sql scripts in your existing database project -->
</ItemGroup>
</Project>
After run you will see dacpac file appears under DB.Build/bin/Release/netstandard2.0/DB.Build.dacpac
Here's my build agent output (Ubuntu agent on Azure devops)
Starting: SQL DB build Release
==============================================================================
Task : .NET Core
Description : Build, test, package, or publish a dotnet application, or run a custom dotnet command
Version : 2.187.0
Author : Microsoft Corporation
Help : https://learn.microsoft.com/azure/devops/pipelines/tasks/build/dotnet-core-cli
==============================================================================
Info: .NET Core SDK/runtime 2.2 and 3.0 are now End of Life(EOL) and have been removed from all hosted agents. If you're using these SDK/runtimes on hosted agents, kindly upgrade to newer versions which are not EOL, or else use UseDotNet task to install the required version.
/opt/hostedtoolcache/dotnet/dotnet build /home/vsts/work/1/s/src/RecommenderAPI.DB/RecommenderAPI.DB/RecommenderAPI.DB.Build/RecommenderAPI.DB.Build.csproj -dl:CentralLogger,"/home/vsts/work/_tasks/DotNetCoreCLI_5541a522-603c-47ad-91fc-a4b1d163081b/2.187.0/dotnet-build-helpers/Microsoft.TeamFoundation.DistributedTask.MSBuild.Logger.dll"*ForwardingLogger,"/home/vsts/work/_tasks/DotNetCoreCLI_5541a522-603c-47ad-91fc-a4b1d163081b/2.187.0/dotnet-build-helpers/Microsoft.TeamFoundation.DistributedTask.MSBuild.Logger.dll" --configuration Release /p:DeployOnBuild=true /p:WebPublishMethod=Package /p:PackageAsSingleFile=true /p:SkipInvalidConfigurations=true /p:PackageLocation=/home/vsts/work/1/recommender-service-cicd/DacPac/
Microsoft (R) Build Engine version 16.5.0+d4cbfca49 for .NET Core
Copyright (C) Microsoft Corporation. All rights reserved.
Restore completed in 51.72 ms for /home/vsts/work/1/s/src/RecommenderAPI.DB/RecommenderAPI.DB/RecommenderAPI.DB.Build/RecommenderAPI.DB.Build.csproj.
Using package name RecommenderAPI.DB.Build and version 1.0.0
Using SQL Server version Sql150
Deleting existing file /home/vsts/work/1/s/src/RecommenderAPI.DB/RecommenderAPI.DB/RecommenderAPI.DB.Build/obj/Release/netstandard2.0/RecommenderAPI.DB.Build.dacpac
Writing model to /home/vsts/work/1/s/src/RecommenderAPI.DB/RecommenderAPI.DB/RecommenderAPI.DB.Build/obj/Release/netstandard2.0/RecommenderAPI.DB.Build.dacpac
RecommenderAPI.DB.Build -> /home/vsts/work/1/s/src/RecommenderAPI.DB/RecommenderAPI.DB/RecommenderAPI.DB.Build/bin/Release/netstandard2.0/RecommenderAPI.DB.Build.dacpac
Build succeeded.
0 Warning(s)
0 Error(s)
Time Elapsed 00:00:01.71
Finishing: SQL DB build Release
Note: Make sure to restore you NuGet packages in step prior to build
We create an installation .exe with burn that successfully installs .NET4 as a prerequisite and our .msi which was created with a wix script. All this works quite well.
Our wix script creates an uninstall shortcut (pretty much taken from the wix how-to pages):
<Shortcut Id="UninstallProduct"
Name="Uninstall Product Name"
Target="[SystemFolder]msiexec.exe"
Arguments="/x [ProductCode]"
Description="Uninstalls Product" />
If I use this shortcut, the application is correctly uninstalled and all relevant files are removed. However, the entry in the installed programs table in "Programs and Feature" is still there. I also notice that it is not the burn UI that comes up if I use the uninstall shortcut. Basically, my question is: How can I create an uninstall shortcut that removes the entry in the Programs and Features table when using burn?
I have a Wix bootstrapper project that installs .Net framework from the web if needed.
No I would like to do the same for Silverlight.
Ideally from the web but if I have to I will bundle it.
So how do I add Silverlight as a prerequisite?
Solved it:
<ExePackage Id="sl"
Compressed="no"
DownloadUrl="http://go.microsoft.com/fwlink/?LinkID=149156"
SourceFile="C:\Users\mah67\Downloads\silverlight.exe"
Cache="yes"
PerMachine="yes"
Protocol="netfx4"
Vital="yes"
InstallCommand="/q"
Permanent="yes"
Description="Silverlight Runtime"
DisplayName="Silverlight"
SuppressSignatureVerification="yes" >
The source file attribute is apparently needed so Wix can extract info about the file at compile time. Compressed="no" means that it should not be bundled at compile time. RemotePayload is used when the file isnt available at the time of building the package.