Cette question est un doublon de App_Offline dans MSBuild Remote Web Deploy mais j'ai collé la réponse ci-dessous. MSDeploy v3 a un support pour app_offline directement mais vous avez besoin de MSDeploy v3 des deux côtés. Nous n'avons pas encore mis à jour l'expérience VS Web Publish pour être en mesure de tirer parti de cela, mais nous le ferons dans une mise à jour à un moment donné.
J'ai récemment publié un blog à ce sujet sur http://sedodream.com/2012/01/08/HowToTakeYourWebAppOfflineDuringPublishing.aspx . C'est plus difficile que ça ne devrait l'être et je travaille à simplifier cela pour une version ultérieure. En tout cas, j'ai collé tout le contenu ici pour vous.
J'ai reçu un courriel d'un client qui me demandait comment il pouvait mettre son application/site web hors ligne pendant toute la durée d'une publication à partir de Visual Studio. Une façon simple de mettre votre site hors ligne est de déposer un fichier app_offline.htm dans le répertoire racine du site. Pour plus d'informations à ce sujet, vous pouvez lire l'article de ScottGu, dont le lien figure ci-dessous dans la section des ressources. Malheureusement, Web Deploy lui-même ne supporte pas cela. Si vous souhaitez que Web Deploy (aka MSDeploy) supporte cette fonctionnalité de manière native, veuillez voter à l'adresse suivante http://aspnet.uservoice.com/forums/41199-general/suggestions/2499911-take-my-site-app-offline-during-publishing .
Comme Web Deploy ne prend pas en charge cette fonction, cela va être un peu plus difficile et nous devons effectuer les étapes suivantes :
- Publier app_offline.htm
- Publiez l'application et assurez-vous que le fichier app_offline.htm est contenu dans la charge utile publiée.
- Supprimer app_offline.htm
1 mettra l'application hors ligne avant que le processus de publication ne commence.
2 s'assurera que lorsque nous publierons, app_offline.htm ne sera pas supprimé (et donc que l'application restera hors ligne).
3 supprimera le fichier app_offline.htm et remettra le site en ligne.
Maintenant que nous savons ce qu'il faut faire, examinons l'implémentation. Tout d'abord, la partie facile. Créez un fichier dans votre projet d'application Web (WAP) appelé app_offline-template.htm. Ce sera le fichier qui deviendra le fichier app_offline.htm sur votre serveur cible. Si vous laissez ce fichier vide, vos utilisateurs recevront un message générique indiquant que l'application est hors ligne. HTML statique (pas de balisage ASP.NET) à l'intérieur de ce fichier pour faire savoir aux utilisateurs que le site va revenir et toute autre information que vous jugez utile pour vos utilisateurs. Lorsque vous ajoutez ce fichier, vous devez changer l'action de construction en None dans la grille de propriétés. Cela permettra de s'assurer que le fichier lui-même n'est pas publié/emballé. Comme le fichier se termine par .htm, il sera publié par défaut. Voir l'image ci-dessous.
![enter image description here]()
Maintenant, la partie difficile. Pour les projets d'application Web, nous avons un crochet dans le processus de publication/emballage que nous appelons "wpp.targets". Si vous voulez étendre votre processus de publication/emballage, vous pouvez créer un fichier nommé {Nomduprojet}.wpp.targets dans le même dossier que le fichier du projet lui-même. Voici le fichier que j'ai créé ; vous pouvez copier et coller le contenu dans votre fichier wpp.targets. Je vais expliquer les parties importantes mais je voulais poster le fichier entier pour vous convaincre. Note : vous pouvez récupérer la dernière version de ce fichier sur mon github repo, le lien est dans la section ressources ci-dessous.
<?xml version="1.0" encoding="utf-8"?>
<Project xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Target Name="InitalizeAppOffline">
<!--
This property needs to be declared inside of target because this is imported before
the MSDeployPath property is defined as well as others -->
<PropertyGroup>
<MSDeployExe Condition=" '$(MSDeployExe)'=='' ">$(MSDeployPath)msdeploy.exe</MSDeployExe>
</PropertyGroup>
</Target>
<PropertyGroup>
<PublishAppOfflineToDest>
InitalizeAppOffline;
</PublishAppOfflineToDest>
</PropertyGroup>
<!--
%msdeploy%
-verb:sync
-source:contentPath="C:\path\to\app_offline-template.htm"
-dest:contentPath="Default Web Site/AppOfflineDemo/app_offline.htm"
-->
<!--***********************************************************************
Make sure app_offline-template.htm gets published as app_offline.htm
***************************************************************************-->
<Target Name="PublishAppOfflineToDest"
BeforeTargets="MSDeployPublish"
DependsOnTargets="$(PublishAppOfflineToDest)">
<ItemGroup>
<_AoPubAppOfflineSourceProviderSetting Include="contentPath">
<Path>$(MSBuildProjectDirectory)\app_offline-template.htm</Path>
<EncryptPassword>$(DeployEncryptKey)</EncryptPassword>
<WebServerAppHostConfigDirectory>$(_MSDeploySourceWebServerAppHostConfigDirectory)</WebServerAppHostConfigDirectory>
<WebServerManifest>$(_MSDeploySourceWebServerManifest)</WebServerManifest>
<WebServerDirectory>$(_MSDeploySourceWebServerDirectory)</WebServerDirectory>
</_AoPubAppOfflineSourceProviderSetting>
<_AoPubAppOfflineDestProviderSetting Include="contentPath">
<Path>"$(DeployIisAppPath)/app_offline.htm"</Path>
<ComputerName>$(_PublishMsDeployServiceUrl)</ComputerName>
<UserName>$(UserName)</UserName>
<Password>$(Password)</Password>
<EncryptPassword>$(DeployEncryptKey)</EncryptPassword>
<IncludeAcls>False</IncludeAcls>
<AuthType>$(AuthType)</AuthType>
<WebServerAppHostConfigDirectory>$(_MSDeployDestinationWebServerAppHostConfigDirectory)</WebServerAppHostConfigDirectory>
<WebServerManifest>$(_MSDeployDestinationWebServerManifest)</WebServerManifest>
<WebServerDirectory>$(_MSDeployDestinationWebServerDirectory)</WebServerDirectory>
</_AoPubAppOfflineDestProviderSetting>
</ItemGroup>
<MSdeploy
MSDeployVersionsToTry="$(_MSDeployVersionsToTry)"
Verb="sync"
Source="@(_AoPubAppOfflineSourceProviderSetting)"
Destination="@(_AoPubAppOfflineDestProviderSetting)"
EnableRule="DoNotDeleteRule"
AllowUntrusted="$(AllowUntrustedCertificate)"
RetryAttempts="$(RetryAttemptsForDeployment)"
SimpleSetParameterItems="@(_AoArchivePublishSetParam)"
ExePath="$(MSDeployPath)" />
</Target>
<!--***********************************************************************
Make sure app_offline-template.htm gets published as app_offline.htm
***************************************************************************-->
<!-- We need to create a replace rule for app_offline-template.htm->app_offline.htm for when the app get's published -->
<ItemGroup>
<!-- Make sure not to include this file if a package is being created, so condition this on publishing -->
<FilesForPackagingFromProject Include="app_offline-template.htm" Condition=" '$(DeployTarget)'=='MSDeployPublish' ">
<DestinationRelativePath>app_offline.htm</DestinationRelativePath>
</FilesForPackagingFromProject>
<!-- This will prevent app_offline-template.htm from being published -->
<MsDeploySkipRules Include="SkipAppOfflineTemplate">
<ObjectName>filePath</ObjectName>
<AbsolutePath>app_offline-template.htm</AbsolutePath>
</MsDeploySkipRules>
</ItemGroup>
<!--***********************************************************************
When publish is completed we need to delete the app_offline.htm
***************************************************************************-->
<Target Name="DeleteAppOffline" AfterTargets="MSDeployPublish">
<!--
%msdeploy%
-verb:delete
-dest:contentPath="{IIS-Path}/app_offline.htm",computerName="...",username="...",password="..."
-->
<Message Text="************************************************************************" />
<Message Text="Calling MSDeploy to delete the app_offline.htm file" Importance="high" />
<Message Text="************************************************************************" />
<ItemGroup>
<_AoDeleteAppOfflineDestProviderSetting Include="contentPath">
<Path>$(DeployIisAppPath)/app_offline.htm</Path>
<ComputerName>$(_PublishMsDeployServiceUrl)</ComputerName>
<UserName>$(UserName)</UserName>
<Password>$(Password)</Password>
<EncryptPassword>$(DeployEncryptKey)</EncryptPassword>
<AuthType>$(AuthType)</AuthType>
<WebServerAppHostConfigDirectory>$(_MSDeployDestinationWebServerAppHostConfigDirectory)</WebServerAppHostConfigDirectory>
<WebServerManifest>$(_MSDeployDestinationWebServerManifest)</WebServerManifest>
<WebServerDirectory>$(_MSDeployDestinationWebServerDirectory)</WebServerDirectory>
</_AoDeleteAppOfflineDestProviderSetting>
</ItemGroup>
<!--
We cannot use the MSDeploy/VSMSDeploy tasks for delete so we have to call msdeploy.exe directly.
When they support delete we can just pass in @(_AoDeleteAppOfflineDestProviderSetting) as the dest
-->
<PropertyGroup>
<_Cmd>"$(MSDeployExe)" -verb:delete -dest:contentPath="%(_AoDeleteAppOfflineDestProviderSetting.Path)"</_Cmd>
<_Cmd Condition=" '%(_AoDeleteAppOfflineDestProviderSetting.ComputerName)' != '' ">$(_Cmd),computerName="%(_AoDeleteAppOfflineDestProviderSetting.ComputerName)"</_Cmd>
<_Cmd Condition=" '%(_AoDeleteAppOfflineDestProviderSetting.UserName)' != '' ">$(_Cmd),username="%(_AoDeleteAppOfflineDestProviderSetting.UserName)"</_Cmd>
<_Cmd Condition=" '%(_AoDeleteAppOfflineDestProviderSetting.Password)' != ''">$(_Cmd),password=$(Password)</_Cmd>
<_Cmd Condition=" '%(_AoDeleteAppOfflineDestProviderSetting.AuthType)' != ''">$(_Cmd),authType="%(_AoDeleteAppOfflineDestProviderSetting.AuthType)"</_Cmd>
</PropertyGroup>
<Exec Command="$(_Cmd)"/>
</Target>
</Project>
1 Publier app_offline.htm
L'implémentation pour #1 est contenue dans la cible PublishAppOfflineToDest. La commande msdeploy.exe que nous devons faire exécuter est.
msdeploy.exe
-source:contentPath='C:\Data\Personal\My Repo\sayed-samples\AppOfflineDemo01\AppOfflineDemo01\app_offline-template.htm'
-dest:contentPath='"Default Web Site/AppOfflineDemo/app_offline.htm"',UserName='sayedha',Password='password-here',ComputerName='computername-here',IncludeAcls='False',AuthType='NTLM' -verb:sync -enableRule:DoNotDeleteRule
Pour ce faire, je vais utiliser la tâche MSDeploy. Dans la cible PublishAppOfflineToDest, vous pouvez voir comment cela est accompli en créant un élément pour la source et la destination.
2 Publiez l'application, et assurez-vous que app_offline.htm est contenu dans la charge utile en cours de publication.
Cette partie est accomplie par le fragment
<!--***********************************************************************
Make sure app_offline-template.htm gets published as app_offline.htm
***************************************************************************-->
<!-- We need to create a replace rule for app_offline-template.htm->app_offline.htm for when the app get's published -->
<ItemGroup>
<!-- Make sure not to include this file if a package is being created, so condition this on publishing -->
<FilesForPackagingFromProject Include="app_offline-template.htm" Condition=" '$(DeployTarget)'=='MSDeployPublish' ">
<DestinationRelativePath>app_offline.htm</DestinationRelativePath>
</FilesForPackagingFromProject>
<!-- This will prevent app_offline-template.htm from being published -->
<MsDeploySkipRules Include="SkipAppOfflineTemplate">
<ObjectName>filePath</ObjectName>
<AbsolutePath>app_offline-template.htm</AbsolutePath>
</MsDeploySkipRules>
</ItemGroup>
La valeur de l'élément pour FilesForPackagingFromProject ici convertira votre app_offline-template.htm en app_offline.htm dans le dossier à partir duquel la publication sera traitée. Il y a également une condition pour que cela ne se produise que pendant la publication et non l'emballage. Nous ne voulons pas que app_offline-template.htm soit dans le paquet (mais ce n'est pas la fin du monde si c'est le cas).
L'élément pour MsDeploySkiprules fera en sorte que app_offline-template.htm lui-même ne soit pas publié. Ce n'est peut-être pas nécessaire mais cela ne devrait pas faire de mal.
3 Supprimer app_offline.htm
Maintenant que notre application est publiée, nous devons supprimer le fichier app_offline.htm de l'application web destinataire. La commande msdeploy.exe serait :
%msdeploy% -verb:delete -dest:contentPath="{IIS-Path}/app_offline.htm",computerName="...",username="...",password="..."
Ceci est mis en œuvre à l'intérieur de la cible DeleteAppOffline. Cette cible sera automatiquement exécutée après la publication car j'ai inclus l'attribut AfterTargets="MSDeployPublish". Dans cette cible, vous pouvez voir que je construis la commande msdeploy.exe directement, il semble que la tâche MSDeploy ne supporte pas le verbe supprimer.
Si vous l'essayez, faites-moi savoir si vous rencontrez des problèmes. Je pense créer un paquet Nuget à partir de cela afin que vous puissiez simplement installer ce paquet. Cela demanderait un peu de travail, alors faites-moi savoir si cela vous intéresse.
Ressources
- La dernière version de mon fichier wpp.targets de AppOffline
- Le blog de ScottGu sur app_offline.htm