-
Notifications
You must be signed in to change notification settings - Fork 23
Integrating .NET into Deployment
-
Ensure current working directory is the repository root
-
Create a scaffolding script for the WebAPI project
azure site deploymentscript --aspWAP .\src\api\API.csproj -s .\src\TodoList.sln -o .\apiscript
Select no at the prompt to overwrite the
.deploymentfile
-
Open
apiscript\deploy.cmd. -
Within the
:: Setupsection, copy the items after the definition of KuduSync to the clipboard (lines 50-62)
IF NOT DEFINED DEPLOYMENT_TEMP (
SET DEPLOYMENT_TEMP=%temp%\___deployTemp%random%
SET CLEAN_LOCAL_DEPLOYMENT_TEMP=true
)
IF DEFINED CLEAN_LOCAL_DEPLOYMENT_TEMP (
IF EXIST "%DEPLOYMENT_TEMP%" rd /s /q "%DEPLOYMENT_TEMP%"
mkdir "%DEPLOYMENT_TEMP%"
)
IF NOT DEFINED MSBUILD_PATH (
SET MSBUILD_PATH=%WINDIR%\Microsoft.NET\Framework\v4.0.30319\msbuild.exe
)
- Paste them in the primary
deploy.cmdfile--the one within the repository root--within the:: Setupsection, after the definition ofKUDU_SYNC_CMDand beforegoto Deployment.
:: Locally just running "kuduSync" would also work
SET KUDU_SYNC_CMD=%appdata%\npm\kuduSync.cmd
)
IF NOT DEFINED DEPLOYMENT_TEMP (
SET DEPLOYMENT_TEMP=%temp%\___deployTemp%random%
SET CLEAN_LOCAL_DEPLOYMENT_TEMP=true
)
IF DEFINED CLEAN_LOCAL_DEPLOYMENT_TEMP (
IF EXIST "%DEPLOYMENT_TEMP%" rd /s /q "%DEPLOYMENT_TEMP%"
mkdir "%DEPLOYMENT_TEMP%"
)
IF NOT DEFINED MSBUILD_PATH (
SET MSBUILD_PATH=%WINDIR%\Microsoft.NET\Framework\v4.0.30319\msbuild.exe
)
goto Deployment
-
Note the Deployment commands in the
:: Deploymentsection ofapiscript\deploy.cmd.-
Restore NuGet packages will pull referenced packages from NuGet before the build.
-
Build to the temporary path compiles the API Project and stages all deployable files to a TEMP folder.
-
KuduSync synchronizes compiled output to the target
wwwrootfolder.
-
-
Copy all 3 components to the clipboard (lines 68-89).
-
Paste these sections into the primary
deploy.cmdfile after:Deploymentbut beforeecho Handling node.js deployment.::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::: :: Deployment :: ---------- echo Handling .NET Web Application deployment. :: 1. Restore NuGet packages IF /I "src\TodoList.sln" NEQ "" ( call :ExecuteCmd "%NUGET_EXE%" restore "%DEPLOYMENT_SOURCE%\src\TodoList.sln" IF !ERRORLEVEL! NEQ 0 goto error ) :: 2. Build to the temporary path IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" ( call :ExecuteCmd "%MSBUILD_PATH%" "%DEPLOYMENT_SOURCE%\src\api\API.csproj" /nologo /verbosity:m /t:Build /t:pipelinePreDeployCopyAllFilesToOneFolder /p:_PackageTempDir="%DEPLOYMENT_TEMP%";AutoParameterizationWebConfigConnectionStrings=false;Configuration=Release /p:SolutionDir="%DEPLOYMENT_SOURCE%\src\\" %SCM_BUILD_ARGS% ) ELSE ( call :ExecuteCmd "%MSBUILD_PATH%" "%DEPLOYMENT_SOURCE%\src\api\API.csproj" /nologo /verbosity:m /t:Build /p:AutoParameterizationWebConfigConnectionStrings=false;Configuration=Release /p:SolutionDir="%DEPLOYMENT_SOURCE%\src\\" %SCM_BUILD_ARGS% ) IF !ERRORLEVEL! NEQ 0 goto error :: 3. KuduSync IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" ( call :ExecuteCmd "%KUDU_SYNC_CMD%" -v 50 -f "%DEPLOYMENT_TEMP%" -t "%DEPLOYMENT_TARGET%" -n "%NEXT_MANIFEST_PATH%" -p "%PREVIOUS_MANIFEST_PATH%" -i ".git;.hg;.deployment;deploy.cmd" IF !ERRORLEVEL! NEQ 0 goto error ) echo Handling node.js deployment.This introduces a bug into our KuduSync script that is tricky to track down. Both KuduSync commands are using the same manifest. Right now, the MSBuild occurs first, building into TEMP. Then KuduSync copies from TEMP to the final destination,
wwwroot. After gulp runs, KuduSync is executed again to synchronizegulpoutput to the final destination, deleting the files placed intowwwrootfrom the MSBuild process.
We will fix this now by changing the order and some of the the destinations. -
Move the KuduSync command for the MSBuild step after the KuduSync command for the gulp build
popd
echo 3. KuduSync
IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" (
call :ExecuteCmd "%KUDU_SYNC_CMD%" -v 50 -f "%DEPLOYMENT_SOURCE%\src\web\dist" -t "%DEPLOYMENT_TARGET%" -n "%DEPLOYMENT_SOURCE%" -p "%u%" -i ".git;.hg;.deployment;deploy.cmd"
IF !ERRORLEVEL! NEQ 0 goto error
)
:: 3. KuduSync
IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" (
call :ExecuteCmd "%KUDU_SYNC_CMD%" -v 50 -f "%DEPLOYMENT_TEMP%" -t "%DEPLOYMENT_TARGET%" -n "%NEXT_MANIFEST_PATH%" -p "%PREVIOUS_MANIFEST_PATH%" -i ".git;.hg;.deployment;deploy.cmd"
IF !ERRORLEVEL! NEQ 0 goto error
)
- Update the commented numbers to
echoand re-number for clean output and debugging
Original code:
:: 1. Restore NuGet packages
:: 2. Build to the temporary path
echo 1. Select node version
echo 2. Install npm packages
echo Execute Gulp
echo 3. KuduSync
:: 3. KuduSync
Revised code:
echo 1. Restore NuGet packages
echo 2. Build to the temporary path
echo 3. Select node version
echo 4. Install npm packages
echo 5. Execute Gulp
echo 6. KuduSync from Gulp
echo 7. KuduSync to wwwroot
- Change the destination for the gulp KuduSync step from
%DEPLOYMENT_TARGET%to%DEPLOYMENT_TEMP%.
echo 6. KuduSync from Gulp
IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" (
call :ExecuteCmd "%KUDU_SYNC_CMD%" -v 50 -f "%DEPLOYMENT_SOURCE%\src\web\dist" -t "%DEPLOYMENT_TEMP%" -n "%NEXT_MANIFEST_PATH%" -p "%PREVIOUS_MANIFEST_PATH%" -i ".git;.hg;.deployment;deploy.cmd"
IF !ERRORLEVEL! NEQ 0 goto error
)
- Change the manifest values to %DEPLOYMENT_SOURCE%\src\web\generated\manifest to both the next manifest (
-n) and previous manifest (-p) on the gulp build KuduSync.
echo 6. KuduSync from Gulp
IF /I "%IN_PLACE_DEPLOYMENT%" NEQ "1" (
call :ExecuteCmd "%KUDU_SYNC_CMD%" -v 50 -f "%DEPLOYMENT_SOURCE%\src\web\dist" -t "%DEPLOYMENT_TEMP%" -n "%DEPLOYMENT_SOURCE%\src\web\generated\manifest" -p "%DEPLOYMENT_SOURCE%\src\web\generated\manifest" -i ".git;.hg;.deployment;deploy.cmd"
IF !ERRORLEVEL! NEQ 0 goto error
)
- Make sure NuGet is available for local build.
This is an awful hack. The
NUGET_EXEenvironment variable is not set up when running locally. We need to find the NuGet executable and set the environment variableNUGET_EXEto point at it. Mine happens to be installed by Chocolatey, yours may be elsewhere. Just ensure that the version is NuGet v2.8 or greater.
Within the :: Setup section, after the definition of MSBUILD_PATH and before goto Deployment, add a line that ensures NUGET_EXE is defined and available.
IF NOT DEFINED MSBUILD_PATH (
SET MSBUILD_PATH=%WINDIR%\Microsoft.NET\Framework\v4.0.30319\msbuild.exe
)
IF NOT DEFINED NUGET_EXE (
SET NUGET_EXE=C:\ProgramData\Chocolatey\lib\NuGet.CommandLine.2.8.0\tools\NuGet.exe
)
goto Deployment
-
Return working directory to repository root.
-
Run the deployment script.
deploy.cmd
- Create a SQL Database with a name of
todosampleon Azure and obtain its connection string.
Note that this should be in the same region as your WebSite
- In Package Manager Console, run
update-database, specifying the Azure connection string.
update-database -ConnectionString "<string>" -ConnectionProviderName "System.Data.SqlClient"
-
Visit the CONFIGURE tab of the Azure Website in the management portal.
-
Add a connection string entry for
todosdband set its value to the connection string used above.
What is awesome here is that this allows for your
web.configto remain safe. It will only ever point at a local database. You do not have to expose your production secrets anywhere but on the portal (or configuration script if you prefer). This setting will override the value in theweb.configat runtime.
-
Commit your changes and push to Azure
-
Visit your Website and see your persisted changes now.