git 中的 web.config 和 app.config 机器特定设置

Posted

技术标签:

【中文标题】git 中的 web.config 和 app.config 机器特定设置【英文标题】:web.config and app.config machine-specific settings in git 【发布时间】:2012-04-25 21:34:54 【问题描述】:

我们在不同的办公室有多个开发团队,他们需要为我们项目的web.configapp.config 文件中的一些配置设置提供不同的值。

我们希望使用一组合理的默认值签入这些配置文件,这样通过签出trunk/master 分支,您就可以工作,而无需四处寻找配置文件。

过去我们使用过 Subversion,特别是 TortoiseSVN,这提供了一种管理本地更改的简单方法:我们只是将这些文件添加到 TortoiseSVN 的自动 ignore-on-commit 更改列表中。这可以防止意外签入这些文件,因为您随后需要专门选择它们以将它们包含在签入中(并且您可以确保您正在签入重大更改,而不是本地配置噪音)。这种方法的主要缺点是配置文件看起来总是“更改”,因此无法一目了然地知道您是否有任何本地更改。

我们正在寻求切换到 Git,并且我正在尝试找出最佳方法。

首先,其他 *** 答案中已有的内容:

选项 1:签入 xxx.sample 文件并 .gitignore 实际配置文件:建议这样做,例如在 this answer 中。我看到的主要问题是配置文件的更改很容易被遗忘,在两个不同的点:提交者很容易错过他们需要添加到.sample文件的更改,以及消费者(尤其是持续集成服务器)很容易错过他们需要从.sample 文件合并到本地配置文件中的更改。所以基本上,这似乎不是一个很好的解决方案。

选项 2:有一个签入的 xxx.defaults 文件和一个 .gitignored xxx.local 配置文件,它会覆盖它定义的任何设置:这是提供的,例如 here。问题在于我们正在与标准的 .Net 配置提供程序合作 - 我真的不希望我们在 Mirosoft 已经完成所有工作时实现一个全新的设置加载框架。有谁知道获取 app.config 和 web.config 文件以引用可选本地覆盖文件的方法?

选项 3:让开发人员保留本地分支,然后让他们始终将 cherry-picks 或 rebase 分支签入 master,以始终绕过/避免本地分支中不需要的提交:这是作为一个可能的工作流here 提供,虽然我很欣赏它在更改跟踪(所有签入)方面的简洁性,但它在每次签入时引入了大量必需开销;这是一个巨大的痛苦!

选项 4:签入配置文件,但将它们标记为 --assume-unchanged:这是作为一个可能的选项 here 提供的;据我所知,它在精神上与 TortoiseSVN 中的ignore-on-commit 更改列表非常相似,除了在提交过程中您无法看到这些“隐藏”的更改文件;例如,TortoiseGit 确实显示带有“已更改”图标覆盖的文件,但在提交对话框中该文件根本不显示。这似乎有点吓人,又很容易忘记检查更改。

鉴于这些选项,这是我找到的所有选项,我真的希望有一种方法可以选择性地将本地配置文件“包含”到/覆盖签入的 app.config/web.config 文件中,并且选择选项2;有谁知道这样做的方法,或者我缺少的其他选项? (我有点想考虑一个自定义的 Xml 合并预构建步骤......)

我应该在前面提到,我们仍然在 VS2008 上,所以配置转换不可用。


更新:(已删除,完全错误)

更新 2:我已经删除了我之前的更新和回答,这是愚蠢的/没有用。我没有意识到在“我们的”合并之后,另一个方向的下一次合并会将这些文件的“原始”版本带回(覆盖本地分支更改);如果您有兴趣,请参阅编辑历史。这个问题一如既往的开放。

【问题讨论】:

你最终采取了什么方法?谢谢。 我们最终构建了一个内部工具,如果不跳过太多的圈数,我就无法分享它。它只支持“模板”文件中的占位符,并将其转换为“最终”文件。占位符到值的映射存储在一对简单的 Xml 文档中,一个签入的“默认”文档和一个未签入的“本地”文档 (.gitignored)。模板文件已签入,但所有输出文件都是 .gitignored。它可以运行在“覆盖差异”模式,或“警告差异”模式,您希望使用最终(例如 web.config)文件来更新相应的模板。 【参考方案1】:

我会看看Dan 的this answer for Managing complex Web.Config files between deployment environments 寻找潜在的解决方案。我使用 mercurial 并使用相同的流程签入通用 web.config 文件,并使用 Web 转换更改 configSource 的位置以指向我的部署特定内容。

使用此路由的优点是它完全内置在框架中,不需要额外的代码,并且适用于 Web 部署。

在 web.config 中签入:

<?xml version="1.0"?>
<configuration>
  <!-- snip -->
  <connectionStrings configSource="config/connectionStrings.config" />
</configuration>

在 web.debug.config 中签入:

<?xml version="1.0"?>
<configuration>
  <connectionStrings
      configSource="config/dev.connectionStrings.config"
      xdt:Transform="Replace(configSource)" />
</configuration>

我使用默认值签入了 config/connectionStrings.config,但开发服务器 config/dev.connectionStrings.config 未签入,并且未在新部署中被替换。

【讨论】:

这仅在您在本地发布或作为调试发布到开发服务器时有效,而不是在您在 VS 中运行时。 您仍然可以反向应用相同的逻辑。在 web.config 中指定自定义 .config 文件,然后在发布时使用转换文件,然后在本地配置文件上执行 .gitignore。通过使用configSource .Net 将自动将不同的文件合并在一起,而无需额外的代码。 hmm,我们被困在 VS2008 上并且不使用 Web 部署(并且有其他非 ASP 应用程序组件),但无论如何,这 configSource 的事情值得深思,谢谢!跨度> 【参考方案2】:

我想建议你看看ConfigGen。我们在所有项目中都使用它,它为所有开发人员和我们所有的环境创造了奇迹。它基本上运行一个声明机器名称和输出配置文件的电子表格,然后标记模板 App.Config 或 Web.Config,将电子表格中的值替换到其中。在您的项目中添加一个简单的预构建步骤以运行 configgen,在构建开始之前,您拥有一个为您的机器量身定制的配置文件。它还支持默认设置。

看看这个网站并自己决定,但我绝对可以保证。

编辑:值得注意的是,您可以忽略所有 Web.config 和 App.config 文件(以 .git 形式)。但是您确实需要将模板和电子表格添加到存储库中。此外,我确信有一个更新可能包括电子表格的 xml 替换,它有自己的编辑器,使其更适合 DVCS。

Edit2:还可以在这里查看 Daniel 的帖子:https://***.com/a/8082937/186184。他给出了一个非常清晰的模板和电子表格示例,以及如何使其在您的解决方案中发挥作用。

【讨论】:

谢谢,这看起来是最简单/最明智的解决方案,去试试吧 为了清楚起见,我没有否决你的答案;)(特别是因为我在这个页面上有自己的答案) ConfigGen 现在支持 csv 设置文件以及全局默认设置文件,允许您将全局设置存储在一个文件中,并将它们与每个应用程序更具体的设置文件合并。【参考方案3】:

我们公司也遇到了类似的困境。我们最终创建了单独的配置分支来补充主分支。例如 - 开发配置、主配置等。然后我们有一个小脚本,它将根据部署环境使用正确的源分支重新定位这些分支。因此,例如在开发机器上,我们会将develop-config 重新设置为develop。如果你在本地机器上工作,你会得到默认配置(所有开发人员都同意),它被检查到主分支中(如本地数据库名称、密码等)。当然,缺点是您必须始终保持这些 *-config 分支是最新的,或者在部署时让它们跟上速度。

自从实施此工作流程以来,我遇到了几个部署工具,例如 whiskey_disk,它们采用了类似的方法。事实上,我更喜欢他们的解决方案,因为它更加安全和灵活。虽然可能不适合你们,因为它更适合 LAMP/RoR 开发堆栈。

除此之外,还有一些商业解决方案可供您参考,例如 Beanstalk

【讨论】:

【参考方案4】:

你考虑过content filter driver吗?

这意味着,在每个 git checkout 上,smudge 脚本将生成实际的配置文件,基于:

一个配置模板文件(带有配置值占位符,如@@A_PARAM_VALUE@@) 配置值文件之一(每个开发人员可以保留他/她自己的配置文件值的版本)

避免任何合并问题和 gitignore 设置:每个“配置值文件”都不同并且保持独立。 这也与pms1969 的answer 中提到的ConfigGen 等其他配置生成解决方案兼容。

【讨论】:

嗯,这看起来很有趣 - 需要去玩 好的,除非我在这里误解了某些东西,否则为了使这种流程起作用,我们需要建立双向内容转换;从签入到本地(替换占位符,或从某个单个占位符 + 模板 + 值文件构建文件内容),以及从本地到签入(根据一些公认的部分内容)。好消息是它会在结帐时自动执行(只要您使用 git 而不是 libgit2 之类的东西?),但这看起来比自定义构建步骤复杂得多...... @Tao 是的,如果您需要存储对生成的文件所做的本地修改,将使用“clean”脚本。而libgit2 确实支持smudge(至少有点污迹)。因为,错误... 4 天:article.gmane.org/gmane.comp.version-control.git/197996【参考方案5】:

自 2012 年以来发生了一些变化,现在我建议您使用构建/部署工具(VS Team Services、TeamCity、Octopus Deploy)管理环境特定配置。

如果您在 azure 中工作,则可以将应用设置和连接字符串定义为应用定义的一部分。

【讨论】:

以上是关于git 中的 web.config 和 app.config 机器特定设置的主要内容,如果未能解决你的问题,请参考以下文章

WCF开发中的Web.config和App.config

web.config配置文件中的configSource属性

关于 web.config 中的模拟、身份验证和授权的困惑

web.config中的configSource

web.config 文件中的特殊字符

web.config与.dll中的app.config