使用 MSDeploy 部署一個在 Private Link 封閉網路環境下的 Function App | The Will Will Web

The Will Will Web

記載著 Will 在網路世界的學習心得與技術分享

使用 MSDeploy 部署一個在 Private Link 封閉網路環境下的 Function App

我們有個網站部署在 Azure Function App 之中,不過該 Function App 有設定 Private Link 封閉網路,所以網站部署不能從外網連入,必須從私有 VNet 中的 VM 進行部署。本篇文章我將分享從私有網路環境部署站台到 Function App 的步驟說明。

  1. 安裝 Web Deploy 工具

    choco install webdeploy -y
    
  2. 設定必要的變數

    你必須從 Azure Function App 下載的 發行設定檔(Publish Profile),並取出重要的部署參數:

    <publishProfile profileName="willtestdeploy - Web Deploy"
                    publishMethod="MSDeploy"
                    publishUrl="willtestdeploy.scm.azurewebsites.net:443"
                    msdeploySite="willtestdeploy"
                    userName="$willtestdeploy"
                    userPWD="ClDdGBNMS6h0ooHDlY1uaNlqp7zYFNuzoJgvM6dDQLKSYxMNo4c6g5kZQadX"
                    destinationAppUrl="http://willtestdeploy.azurewebsites.net"
                    SQLServerDBConnectionString=""
                    mySQLDBConnectionString=""
                    hostingProviderForumLink=""
                    controlPanelLink="http://windows.azure.com"
                    webSystem="WebSites">
    </publishProfile>
    

    然後完成以下 PowerShell 變數建立:

    $sourcePath = 'G:\publish'
    $appOffline = $sourcePath + '\app_offline.template.htm'
    $publishUrl = 'willtestdeploy.scm.azurewebsites.net:443'
    $deploySite = 'willtestdeploy'
    $userName = '$willtestdeploy'
    $userPWD = 'ClDdGBNMS6h0ooHDlY1uaNlqp7zYFNuzoJgvM6dDQLKSYxMNo4c6g5kZQadX'
    
  3. 同步 app_offline.htm 檔案到遠端站台

    msdeploy -verb:sync -source:contentPath=$appOffline -dest:contentPath=`"$deploySite/app_offline.htm`",computerName=`"https://$publishUrl/msdeploy.axd?site=$deploySite`",userName=`"$userName`",password=`"$userPWD`",authtype=`"Basic`",includeAcls=`"False`"
    

    其實 MSDeploy 有個 -enableRule:AppOffline 規則,當你在同步站台檔案的時候,這條規則會在遠端站台幫你建立一個 App_Offline.htm 檔案,讓網站的應用程式集區可以暫時關閉。可惜 AspNetCoreModule 一直以來都有個 Bug,他會認不得 App_Offline.htm 檔案,只認得小寫的 app_offline.htm 檔案! 所以這條規則對 .NET Framework 環境有效,但是在 .NET Core 就無效了! 奇怪的地方是,這個問題明明在 2017 年就已經有修正,但是到了 .NET Core 3.1 還是依然無效,我可能要找時間去 GitHub 回報這個問題!

  4. 同步所有檔案到遠端站台

    msdeploy -verb:sync -source:contentPath=$sourcePath -dest:contentPath=`"$deploySite`",computerName=`"https://$publishUrl/msdeploy.axd?site=$deploySite`",userName=`"$userName`",password=`"$userPWD`",authtype=`"Basic`",includeAcls=`"False`" -retryAttempts:10 -retryInterval:3000 -enableRule:DoNotDeleteRule
    

    這裡如果沒加上 -enableRule:DoNotDeleteRule 的話,站台中的 app_offline.htm 檔案就會被刪除,這可能會導致站台中的 *.dll 檔案依然被鎖定!

    如果 Azure Function App 有設定 WEBSITE_RUN_FROM_PACKAGE 並設定為 1 的話,網站將無法正確部署!

  5. 刪除遠端站台的 app_offline.htm 檔案

    msdeploy.exe -verb:delete -dest:contentPath=$deploySite/app_offline.htm,computerName=`"https://$publishUrl/msdeploy.axd?site=$deploySite`",userName=`"$userName`",password=`"$userPWD`",authtype=`"Basic`",includeAcls=`"False`"
    

相關連結

附加資訊

以下是 "C:\Program Files (x86)\IIS\Microsoft Web Deploy V3\msdeploy.exe" 的參數說明,這是一套博大精深的網站同步工具,要完全搞懂他是相當不容易的!

Microsoft (R) Web Deployment Command Line Tool (MSDeploy.exe)
Version 7.1.3802.2056
Copyright (c) Microsoft Corporation. All rights reserved.

MSDeploy.exe <-verb:<name>> <-source:<object>> [-dest:<object>] [args ...]

  -verb:<name>                   Action to perform (required).
  -source:<object>               The source object for the operation (required).
  -dest:<object>                 The destination object for the operation.
  -declareParam:<params>         Declares a parameter for synchronization.
  -setParam:<params>             Sets a parameter for synchronization.
  -setParamFile:<xmlfile>        Applies parameter settings from an XML file.
  -declareParamFile:<xmlfile>    Includes parameter declarations from an XML file.
  -removeParam:<name>            Removes a parameter from the list of declared parameters.
  -disableLink:<name>            Disables the specified link extension(s).
  -enableLink:<name>             Enables the specified link extension(s).
  -disableRule:<name>            Disables the specified synchronization rule(s).
  -enableRule:<name>             Enables the specified synchronization rule(s).
  -replace:<arg settings>        Specifies an attribute replacement rule.
  -retryAttempts                 The number of times a provider will retry after a failed action (not all providers support retrying).
                                 Defaults to 5.
  -retryInterval                 Interval in milliseconds between retry attempts (-retryAttempts). The default is 1000.
  -skip:<arg settings>           Specifies an object to skip during synchronization.
  -disableSkipDirective:<name>   Disables the specified skip directive.
  -enableSkipDirective:<name>    Enables the specified skip directive.
  -verbose                       Enables more verbose output.
  -whatif                        Displays what would have happened without actually performing any operations.
  -disableAppStore               Disables saving to the application store during a sync.
  -xpath:<path>                  An XPath expression to apply to XML output.
  -xml                           Return results in XML format.
  -allowUntrusted                Allow untrusted server certificate when using SSL.
  -showSecure                    Show secure attributes in XML output instead of hiding them.^
  -preSync:<command>             A command to execute before the synchronization on the destination.  For instance, net stop a service.
  -postSync:<command>            A command to execute after the synchronization on the destination.  For instance, net start a service.

Supported Verbs:

  dump                           Displays the details of the specified source object.
  sync                           Synchronizes the destination object with the source object.
  delete                         Deletes specified destination object.
  getDependencies                Retrieve dependencies for given object
  getParameters                  Return parameters supported by object
  getSystemInfo                  Retrieve system information associated with given object

<object> format:

  provider-type=[provider-path],[provider settings],...

Supported provider-types (and sample paths, if applicable):

  appHostAuthOverride            Modifies IIS inheritance rules for different authentication settings to either allow or deny them to be
                                 overridden in a site's web.config file.
  appHostConfig                  IIS 7 configuration
  appHostSchema                  IIS 7 configuration schema
  appPoolConfig                  IIS 7 Application Pool
  appPoolEnable32Bit             Enable 32-bit application pool on IIS7.
  appPoolNetFx                   The appPoolNetFx provider displays or sets the .NET Framework version of an IIS application pool.
  appPoolPipeline                The appPoolPipeline provider displays or sets the managed pipeline mode of the specified IIS application
                                 pool.
  archiveDir                     Archive directory
  auto                           Automatic destination
  backupManager                  Allows you to create, list, restore, and delete backups.
  backupSettings                 Manages your site's backup settings
  cert                           Certificate
  certStoreSettings              This provider is used to sync Centralized SSL Certificates Support store settings. It does not require
                                 any path to be specified and can only be utilized on IIS 8 and later.
  comObject32                    32-bit COM object
  comObject64                    64-bit COM object
  contentPath                    File System Content
  contentPathLib                 Used to deploy ASP.Net libraries that live in the 'approot' folder, which is a sibling to the content
                                 root folder.
  createApp                      Defines an application in the IIS configuration system.
  dbDacFx                        Deploy SQL database using DACFx API
  dbFullSql                      Deploy SQL database
  dbMySql                        Deploy MySQL database
  dbSqlite                       Deploy SQLite database
  dirPath                        Directory
  fcgiExtConfig                  FcgiExt.ini settings or fastCgi section configuration
  filePath                       File
  gacAssembly                    GAC assembly
  gacInstall                     Signed Assembly GAC Installer
  iisApp                         Web Application
  machineConfig32                .NET 32-bit machine configuration
  machineConfig64                .NET 64-bit machine configuration
  manifest                       Custom manifest file
  metaKey                        Metabase key
  package                        A .zip file package
  recycleApp                     Recycles, starts, or stops an application's app pool, or unloads an application's app domains on IIS 7.
  regKey                         Registry key
  regValue                       Registry value
  rootWebConfig32                .NET 32-bit root Web configuration
  rootWebConfig64                .NET 64-bit root Web configuration
  runCommand                     Runs a command on the destination when sync is called.
  setAcl                         Grant permissions
  urlScanConfig                  UrlScan.ini settings or requestFiltering section configuration
  webServer                      Full IIS 7 Web server
  webServer60                    Full IIS 6 Web server

Common settings (can be used with all providers):

  computerName=<name>               Name of remote computer or proxy-URL
  wmsvc=<name>                      Name of remote computer or proxy-URL for the Web Management Service (WMSvc). Assumes that the service
                                    is listening on port 8172.
  authtype=<name>                   Authentication scheme to use. NTLM is the default setting. If the wmsvc option is specified, then
                                    Basic is the default setting.
  userName=<name>                   User name to authenticate for remote connections (required if using Basic authentication).
  password=<password>               Password of the user for remote connections (required if using Basic authentication).
  storeCredentials=<target>         Username and password will be stored in the Windows Credential Manager under the target identifier.
  getCredentials=<target>           Target identifies the credentials (username and password) in the Windows Credential Manager to be used
                                    when connecting to remote computer.
  encryptPassword=<pwd>             Password to use for encrypting/decrypting any secure data.
  includeAcls=<bool>                If true, include ACLs in the operation (applies to the file system, registry, and metabase).
  tempAgent=<bool>                  Temporarily install the remote agent for the duration of a remote operation.
  publishSettings=<filePath>        File path to a publish settings file which contains remote connection information.


Examples:

  MSDeploy.exe -verb:sync -source:contentPath=c:\sourcedir -dest:contentPath=c:\newdir -whatif

  MSDeploy.exe -verb:dump -source:archivedir=c:\mydir

  MSDeploy.exe -verb:sync -source:metakey=lm/w3svc/1,computerName=mycomputer -dest:metakey=lm/w3svc/2

  MSDeploy.exe -verb:sync -source:dbFullSql=c:\myscript.sql -dest:dbFullSql="Data Source=.;Integrated Security=SSPI;Initial Catalog=Northwind"

For more detailed help, add -help to any partial command line.

  MSDeploy.exe -help -verb
  MSDeploy.exe -help -source:apphostconfig
  MSDeploy.exe -help -verb:sync -whatif