Подтвердить что ты не робот

Как мне заставить msdeploy создавать App_Data, если он не существует, но не удаляет содержимое удаленного каталога?

У меня есть настройка приложения со следующими параметрами Пакет/Публикация в Интернете:

  • Только файлы, необходимые для запуска этого приложения
  • (unchecked) Исключить сгенерированные символы отладки
  • (checked) Исключить файлы из папки App_Data​​li >
  • (checked) Включить все базы данных, настроенные на вкладке "Табло/Публикация SQL" - примечание. У меня нет настроенных баз данных.
  • (unchecked) включают параметры IIS, настроенные в IIS Express

В проекте у меня есть настройка папки App_Data, в основном для обработки журналов приложений.

Поведение, которое я хотел бы видеть (и ожидать), следующее:

  • При первоначальном развертывании на совершенно новом сервере приложение копируется и создается папка App_Data с разрешениями на запись, назначенными для приложения.
  • При последующих развертываниях папка App_Data игнорируется, поскольку она уже существует, и отмечен флажок "Исключить файлы из папки App_Data".

Однако msdeploy не выполняет шаг № 1 (шаг 2 в порядке, если я создаю папку вручную). Я не смог найти какую-либо документацию в Интернете, кроме этого ответа без ответа, который, похоже, подтверждает поведение, которое я вижу.

Как мне заставить msdeploy создавать App_Data и назначать разрешения для первоначального развертывания в этом сценарии?

4b9b3361

Ответ 1

Получение развертывания App_Data при запуске с нуля

@tdykstra получил эту часть справа. Чтобы получить App_Data там (и ACL устанавливаются автоматически), я сделал следующее:

  • Добавление файла-заполнителя в App_Data​​li >
  • Установите действие сборки для содержимого на заполнителе (у моего файла-заполнителя есть текст в нем, чтобы люди, спотыкающиеся о нем, знали, почему он там).
  • Не отмечена "Исключить файлы из папки App_Data" на вкладке Пакет/Публикация Web свойств проекта в VS 2010

Это создает мою папку App_Data, созданную и готовую для использования на сервере. Тем не менее, это приведет к удалению всех моих файлов всякий раз, когда я переиздаю. Это проблема №2 в моем вопросе выше и очень близко напоминает этот другой SO question/ответ.

Предотвращение удаления данных на сервере при последующих событиях публикации

В MsDeploy есть два механизма, которые могут запутаться (по крайней мере, я их смутил):

  • Исключение файлов
  • Правила пропустить MsDeploy

Они могут использоваться для решения проблемы в зависимости от сценария:

  • решение @tdykstra, скорее всего, будет работать, если вы:
    • Знайте имена файлов в App_Data заранее (например, база данных sqlite)
    • У вас есть файлы, включенные в папку App_Data в вашем проекте.
  • Использовать правила пропуска MsDeploy, чтобы сообщить MsDeploy полностью пропустить все удаления на сервере для этого каталога и файлов в этом каталоге. Это решает проблему во всех случаях, но гораздо более активно.

Внедрение правил пропуска MsDeploy

Чтобы реализовать правила пропуска, вам придется отказаться от щелчка правой кнопкой мыши по опции "Развернуть" в VS 2010 в пользу щелчка правой кнопкой мыши, "Пакет", перейдите в командную строку, повторно запустите пакетный файл и запустите командную строку), Если вы готовы мириться с этим опытом (я, потому что я автоматизирую все это через процесс CI), вот подробности:

  • Отредактируйте файл проекта и добавьте следующее. Обратите внимание, что аргумент AbsolutePath является регулярным выражением, поэтому вы можете получить фантазию:

    <Target Name="AddCustomSkipRules">
        <ItemGroup>
          <MsDeploySkipRules Include="SkipDeleteAppData">
            <SkipAction>Delete</SkipAction>
            <ObjectName>filePath</ObjectName>
            <AbsolutePath>$(_Escaped_PackageTempDir)\\App_Data\\.*</AbsolutePath>
            <XPath>
            </XPath>
          </MsDeploySkipRules>
          <MsDeploySkipRules Include="SkipDeleteAppData">
            <SkipAction>Delete</SkipAction>
            <ObjectName>dirPath</ObjectName>
            <AbsolutePath>$(_Escaped_PackageTempDir)\\App_Data\\.*</AbsolutePath>
            <XPath>
            </XPath>
          </MsDeploySkipRules>
        </ItemGroup>
    </Target>
    
  • Пакет не развертывает проект. Это создаст zip файл и .cmd файл в целевом каталоге (определяемом "Местоположение, где будет создан пакет" на вкладке "Пакет/Публикация Web" ). По умолчанию это obj\Debug\Package (или obj\Release\Package)
  • Разверните сайт с помощью полученного командного файла

В моем тестировании вы должны упаковать и запустить командный файл. В настройках файла проекта msbuild укажет необходимое правило -skip в командном файле. Однако использование функции "публиковать" прямо из VS 2010 похоже, не запускает командный файл (см. Предупреждение это пошаговое руководство)... он вызывает msdeploy напрямую и, похоже, не соблюдает правила пропуска профайла проекта. Я считаю, что это разница между VS с использованием msbuild -T: Package и msbuild -T: MsDeployPublish для создания проекта, но я этого не тестировал.

Наконец, командный файл не совсем корректен, по крайней мере, в VS 2010 SP1. Там отличное описание того, что пойдет не так в this SO answer, но в основном, VS (или, возможно, цель /t: Цель пакета - лучший преступник) устанавливает командный файл для публикации на машине без указания сайта. Чтобы исправить это, вам нужно как-то получить "? Site = sitename" (возможно, это: site = Default + Web + Site, для полного URL-адреса https://machine: 8172/MsDeploy.axd? Site = Default + Web + Site) в конце аргумента computerName.

Проблема заключалась в том, что командный файл (командный файл) имеет трудное время с использованием site = anything в командной строке, поскольку он неправильно анализирует аргумент командной строки (даже если экранирован). Я не вижу пути вокруг этой проблемы, кроме изменения файла cmd напрямую, но для тестирования я скопировал вывод msdeploy.exe, который я видел из моего неудачного тестового прогона, и изменил его, чтобы вызвать msdeploy.exe напрямую без script.

Теперь, когда он работает, я намерен работать над этим в своих процессах сборки CI. Что я буду делать для окончательного решения:

  • Измените мою сборку script на использование /T: Пакет (прямо сейчас /T: MsDeploy)
  • Попросите сценарий поиска/замены изменить сгенерированное развертывание cmd script
  • Запустите измененное развертывание script

Это действительно должно быть проще.

Обновление

Здесь сценарий поиска/замены, с которым я столкнулся в PowerShell:

(Get-Content "project.deploy.cmd") 
  -replace('^set _ArgComputerName=$'
           ,"set  ArgComputerName=https://server:8172/MsDeploy.axd?Site=Default+Web+Site") 
  | Out-File -Encoding ascii deploy.cmd

Как только это будет запущено, можно вызвать deploy.cmd(без опции /M ), и он будет работать как ожидалось.

Ответ 2

Web Deploy не создаст папку, если нет файлов для ее копирования. Одним из способов обхода в вашем сценарии было бы не использовать флажок Исключить файлы из папки App_Data​​strong > , поместить фиктивный файл в App_Data (например, файл .txt с отсутствием в нем) и указать исключение файла правила для всего, что у вас есть в папке App_Data (например, ваш .sdf файл).

При исключении отдельных файлов (вы можете использовать подстановочные знаки), см. первый вопрос в FAQ по развертыванию в MSDN:

http://msdn.microsoft.com/en-us/library/ee942158.aspx#can_i_exclude_specific_files_or_folders_from_deployment

Используя метод фиктивного файла для создания папки, см. Уверенность, что папка Elmah получает Deployed в этом учебнике:

http://www.asp.net/web-forms/tutorials/deployment-to-a-hosting-provider/deployment-to-a-hosting-provider-configuring-project-properties-4-of-12

Ответ 3

Мне удалось заставить его работать при использовании диалога Publish Web в Visual Studio. Примечание: он работает для любой папки, а не только App_Data.

Это базовый профиль .pubxml:

<?xml version="1.0" encoding="utf-8"?>
<!--
This file is used by the publish/package process of your Web project. You can customize the behavior of this process
by editing this MSBuild file. In order to learn more about this please visit http://go.microsoft.com/fwlink/?LinkID=208121. 
-->
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
  <PropertyGroup>
<AfterAddIisSettingAndFileContentsToSourceManifest>AddCustomSkipRules</AfterAddIisSettingAndFileContentsToSourceManifest>
    <WebPublishMethod>MSDeploy</WebPublishMethod>
    <LastUsedBuildConfiguration>Local</LastUsedBuildConfiguration>
    <LastUsedPlatform>Any CPU</LastUsedPlatform>
    <SiteUrlToLaunchAfterPublish />
    <ExcludeApp_Data>False</ExcludeApp_Data>
    <MSDeployServiceURL>localhost</MSDeployServiceURL>
    <DeployIisAppPath>SuperCoolAwesomeAppName</DeployIisAppPath>
    <RemoteSitePhysicalPath />
    <SkipExtraFilesOnServer>False</SkipExtraFilesOnServer>
    <MSDeployPublishMethod>InProc</MSDeployPublishMethod>
    <EnableMSDeployBackup>False</EnableMSDeployBackup>
    <UserName />
    <_SavePWD>False</_SavePWD>
    <LaunchSiteAfterPublish>True</LaunchSiteAfterPublish>
  </PropertyGroup>

  <PropertyGroup>
    <UseMsDeployExe>true</UseMsDeployExe>
  </PropertyGroup>

  <Target Name="CreateEmptyFolders">
    <Message Text="Adding empty folders to Files" />
    <MakeDir Directories="$(_MSDeployDirPath_FullPath)\Files\Folder 1" />
    <MakeDir Directories="$(_MSDeployDirPath_FullPath)\Files\Folder 2" />
    <MakeDir Directories="$(_MSDeployDirPath_FullPath)\Files\Folder 3\Test"/>
  </Target>

  <Target Name="AddCustomSkipRules" DependsOnTargets="CreateEmptyFolders">
    <Message Text="Adding Custom Skip Rules" />
    <ItemGroup>
      <MsDeploySkipRules Include="SkipFilesInFilesFolder">
        <SkipAction>Delete</SkipAction>
        <ObjectName>filePath</ObjectName>
        <AbsolutePath>$(_DestinationContentPath)\\Files\\.*</AbsolutePath>
        <Apply>Destination</Apply>
      </MsDeploySkipRules>

      <MsDeploySkipRules Include="SkipFoldersInFilesFolders">
        <SkipAction></SkipAction>
        <ObjectName>dirPath</ObjectName>
        <AbsolutePath>$(_DestinationContentPath)\\Files\\.*\\*</AbsolutePath>
        <Apply>Destination</Apply>
      </MsDeploySkipRules>

    </ItemGroup>
  </Target>

</Project>

Вот подробное сообщение, объясняющее это:

Использование MsDeploy публиковать профиль .pubxml для создания пустой структуры папок в IIS и пропустить удаление с помощью MsDeploySkipRules