специфичные для разработчика файлы app.config / web.config в Visual Studio - PullRequest
88 голосов
/ 14 сентября 2010

У нас есть несколько проектов .NET, где мы храним определенные настройки в конфигурационных файлах. Теперь у каждого разработчика будут свои собственные конфигурационные файлы, которые немного отличаются (разные строки подключения для подключения к локальной базе данных, разные конечные точки WCF и т. Д.)

В настоящее время мы стремимся проверить файлы app / web.config и изменить их в соответствии с нашими потребностями. Это приводит ко многим проблемам, так как время от времени кто-то проверяет свои настройки или теряет пользовательские настройки при получении последней версии от tfs.

Мой вопрос: как вы справляетесь с такими ситуациями? Или у вас вообще нет этой проблемы?

Ответы [ 9 ]

65 голосов
/ 13 октября 2010

Мы используем систему, которая объединяет несколько существующих ответов на этой странице, а также опирается на это предложение Скотта Хансельмана .

Короче говоря, у нас был общий app.config / web.config и большинство специфических настроек в отдельных файлах, как подсказывают другие ответы здесь. например для наших настроек SMTP app.config содержит

<system.net>
  <mailSettings>
    <smtp configSource="config\smtp.config" />
  </mailSettings>
</system.net>

Этот файл является в управлении исходным кодом. Однако отдельные файлы, как это, не являются:

<?xml version="1.0" encoding="utf-8" ?>
<smtp deliveryMethod="Network">
  <network host="127.0.0.1" port="25" defaultCredentials="false" password="" userName ="" />
</smtp>

Это не совсем то, где история заканчивается. А как насчет новых разработчиков или установки из свежих источников? Большая часть конфигурации больше не контролируется исходными кодами, и очень сложно вручную создавать все необходимые им файлы .config. Я предпочитаю иметь исходный код, который по крайней мере будет компилироваться прямо из коробки.

Поэтому мы сохраняем версию файлов .config в системе контроля версий с именем .config.default files. Поэтому свежее исходное дерево выглядит так:

alt text

Тем не менее, в действительности нет никакой пользы для разработчика, поскольку для Visual Studio это просто бессмысленные текстовые файлы. Следовательно, пакетный файл copy_default_config.bat заботится о создании исходного набора файлов .config из файлов .config.default:

@echo off
@REM Makes copies of all .default files without the .default extension, only if it doesn't already exist. Does the same recursively through all child folders.
for /r %%f in (*.default) do (
    if not exist "%%~pnf" (echo Copying %%~pnf.default to %%~pnf & copy "%%f" "%%~pnf" /y)
)
echo Done.

Сценарий можно безопасно запустить повторно, поскольку разработчики, у которых уже есть свои файлы .config, не будут перезаписывать их. Следовательно, можно предположительно запустить этот пакетный файл как событие перед сборкой. Значения в файлах .default могут быть не совсем правильными для новой установки, но они являются разумной отправной точкой.

В конечном итоге каждый разработчик получает папку с конфигурационными файлами, которая выглядит примерно так:

alt text

Это может показаться немного запутанным, но это определенно предпочтительнее, чем хлопоты разработчиков, наступающих друг другу на ноги.

21 голосов
/ 14 сентября 2010

В вашем Web.config используйте источник из других файлов

<configuration>
    <connectionStrings configSource="ConnectionStrings.config" />
...
</configuration>

Держите web.config в системе контроля версий и не делайте этого для ConnectionStrings.config. Теперь у всех разработчиков есть один файл для строки подключения.

Вы можете сделать это для всех локальных настроек.

18 голосов
/ 23 января 2012

Вот решение для файлов web.config и Visual Studio 2010:

1) Отредактируйте вручную файл .csproj вашего веб-приложения, добавив цель AfterBuild следующим образом:

  <Project>
   ...
    <Target Name="AfterBuild">
      <Copy SourceFiles="web.config" DestinationFiles="obj\$(Configuration)\tempweb.config" />
      <TransformXml Source="obj\$(Configuration)\tempweb.config"
                  Transform="web.$(USERNAME).config"
                  Destination="obj\$(Configuration)\tempweb2.config" />
      <ReadLinesFromFile File="obj\$(Configuration)\tempweb2.config"><Output TaskParameter="Lines" ItemName="TransformedWebConfig"/></ReadLinesFromFile>
      <ReadLinesFromFile File="web.config"><Output TaskParameter="Lines" ItemName="UnTransformedWebConfig"/></ReadLinesFromFile>
      <Copy Condition=" @(UnTransformedWebConfig) != @(TransformedWebConfig) " SourceFiles="obj\$(Configuration)\tempweb2.config" DestinationFiles="web.config" OverwriteReadOnlyFiles="True" />
    </Target>
  </Project>

Эта цель преобразует файл Web.config, соответствующий текущему разработчику, вошедшему в систему - следовательно, переменной $(USERNAME), с соответствующим файлом, созданным в 1). Он заменит локальный Web.config только в том случае, если содержимое менялось (чтобы избежать перезапуска) при каждой сборке, даже если локальный Web.config контролируется исходным кодом, поэтому для OverwriteReadOnlyFiles установлено значение True. Этот факт на самом деле спорен.

2) Создайте файл с именем Web.[developer windows login].config для каждого разработчика в проекте. (например, на следующих скриншотах у меня есть два разработчика с именами smo и smo2):

enter image description here

Эти файлы (1 на разработчика) могут / должны контролироваться исходными кодами. Они не должны быть помечены как зависимые от основного Web.config, потому что мы хотим иметь возможность проверить их по отдельности.

Каждый из этого файла представляет преобразование, которое применяется к основному файлу Web.Config. Синтаксис преобразования описан здесь: Синтаксис преобразования Web.config для развертывания проекта веб-приложения . Мы повторно используем эту классную задачу преобразования файлов Xml, которая поставляется с Visual Studio. Цель этой задачи - объединить элементы и атрибуты XML вместо перезаписи всего файла.

Например, вот пример web.[dev login].config, который изменяет строку подключения с именем «MyDB» независимо от остальной части файла Web.config:

<?xml version="1.0"?>
<configuration xmlns:xdt="http://schemas.microsoft.com/XML-Document-Transform">
    <connectionStrings>
      <add name="MyDB" 
        connectionString="Data Source=ReleaseSQLServer;Initial Catalog=MyReleaseDB;Integrated Security=True" 
        xdt:Transform="SetAttributes" xdt:Locator="Match(name)" />
    </connectionStrings>
</configuration>

Теперь, это решение не идеально, потому что:

  • после сборки разработчики могут иметь другой Web.Config локально, чем в системе контроля версий
  • им может потребоваться принудительная локальная запись при получении нового Web.Config из системы управления версиями
  • разработчики не должны проверять / в основном web.config. Это должно быть зарезервировано для нескольких человек.

Но, по крайней мере, вам нужно только поддерживать уникальный основной файл web.config плюс один файл преобразования на разработчика.

Аналогичный подход может быть использован для файлов App.config (не web), но я не стал останавливаться на этом подробнее.

2 голосов
/ 14 сентября 2010

Мы используем machine.config, чтобы избежать различий в web.config между средами.

0 голосов
/ 23 января 2012

Если вы используете Visual Studio, почему бы вам не использовать разные конфигурации решений?Например: вы можете иметь конфигурацию Debug, которая использует Web.config.debug, и конфигурацию Release, которая использует Web.config.release.В файле Web.config.debug должно быть что-то вроде

<appSettings file="C:/Standard_Path_To_Configs/Standard_Name_For_Config.config"> 

с файлом Standard_Name_For_Config.config, в котором хранятся все персональные настройки разработчика, тогда как в файле Web.config.release всегда есть производственные настройки.Вы можете сохранить настройки по умолчанию в некоторой папке, контролируемой источником, и заставить нового пользователя взять их оттуда.

0 голосов
/ 20 января 2012

У нас та же проблема, и мы делаем следующее:

  • Проверьте в web.config значения testserver / production
  • Разработчик переходит в проводник Windows и меняет только чтениережим файла
  • Измените конфигурацию в соответствии со своей средой.
  • Регистрация в файле web.config происходит только при изменении значений развертывания или при добавлении или удалении любой записи конфигурации.
  • Это требует большого количества комментариев для каждой записи конфигурации, поскольку оно должно быть изменено каждым разработчиком
0 голосов
/ 14 сентября 2010

Игнорировать файлы и иметь Commom_Web.Config и Common_App.Config. Использование сервера сборки с непрерывной интеграцией с задачами сборки, которые переименовывают эти два имени в обычные, чтобы сервер сборки мог выполнять свою работу.

0 голосов
/ 14 сентября 2010

Один из способов справиться с ситуацией - использовать систему токенов и использовать скрипт rake для изменения значений.

Более примитивным методом может быть ссылка на файл AppSettings.config для всех AppSettings в вашем файле web.config (аналогично соединениям), т.е.

<appSettings configSource="_configs/AppSettings.config" />

Затем по папке с каждым из ваших разработчиков есть версия в подпапке (т.е. / _configs / dave /). Затем, когда разработчик работает над собственным кодом, он копирует из подпапки в корень связанной папки.

Вам нужно будет убедиться, что вы сообщаете об изменениях в этих файлах (если вы не токенизируете). Если вы оставите файл AppSettings.config вне контроля исходного кода и отметите только отдельные папки разработчиков (все они), то они будут вынуждены скопировать правильную.

Я предпочитаю токенизацию, но может быть сложнее запустить и запустить, если это только для быстрого решения.

0 голосов
/ 14 сентября 2010

Как насчет игнорирования файла, чтобы он никогда не регистрировался? Я столкнулся с подобной проблемой и добавил web.config в список игнорирования в Subversion.

В TFS все немного сложнее, см. этот пост о том, как это сделать.

...