如何在不重新编译的情况下在 .NET 中动态切换 Web 服务地址?
Posted
技术标签:
【中文标题】如何在不重新编译的情况下在 .NET 中动态切换 Web 服务地址?【英文标题】:How can I dynamically switch web service addresses in .NET without a recompile? 【发布时间】:2010-09-12 15:05:43 【问题描述】:我有引用 Web 服务的代码,我希望该 Web 服务的地址是动态的(从数据库、配置文件等读取),以便轻松更改。它的一个主要用途是部署到机器名称和 IP 地址不同的多个环境中。 Web 服务签名在所有部署中都是相同的,只是位于其他位置。
也许我刚刚被 Visual Studio“添加 Web 引用”向导宠坏了——不过,这似乎应该相对容易。
【问题讨论】:
您使用的是 Visual Studio 2005 还是 2008。我相信每个向导都略有不同。 【参考方案1】:将 URL 行为更改为“Dynamic”。
【讨论】:
链接好像打不开。【参考方案2】:当您生成 Web 引用并单击解决方案资源管理器中的 Web 引用时。在属性窗格中,您应该会看到如下内容:
将值更改为动态将在您的 app.config 中添加一个条目。
这里是CodePlex article,有更多信息。
【讨论】:
发布时app.config去哪了。在发布输出目录中看不到 它将被重命名为 [OutputAssemblyName].config。示例:MyProject.exe.config 以下 Brad Bruce 的回答在某些情况下更有帮助——您可以更改 Web 服务对象的 Url 属性。 我可以将值存储在 machine.config 中吗? @Shyju ,我正在使用this small .net wrapper 使用邮件枪api
发送邮件,正如您在他们编译的代码中看到的那样https://api.mailgun.net/v2/
api i 版本2想改成第3版https://api.mailgun.net/v3/
,怎么办?【参考方案3】:
如果您从数据库中获取 URL,您可以手动将其分配给 Web 服务代理类 URL 属性。这应该在调用 web 方法之前完成。
如果您想使用配置文件,可以将代理类 URL 行为设置为动态。
【讨论】:
【参考方案4】:只要 Web 服务方法和底层公开的类不改变,就相当简单。在 Visual Studio 2005(及更高版本)中,添加 Web 引用会创建一个包含此 URL 的 app.config(或 web.config,对于 Web 应用程序)部分。您所要做的就是编辑 app.config 文件以反映所需的 URL。
在我们的项目中,我们的简单方法是根据环境类型(开发、测试、生产)对 app.config 条目进行注释。因此,我们只需取消注释所需环境类型的条目。那里不需要特殊编码。
【讨论】:
【参考方案5】:只是说明静态和动态之间的区别。
静态:每次调用 Web 服务时都必须设置 URL 属性。这是因为如果 Web 服务位于代理类构造函数中,则为基本 URL。 动态:将在您的 web.config 文件中为您创建一个特殊的配置密钥。默认情况下,代理类将从此键读取 URL。【讨论】:
【参考方案6】:如果你真的是动态设置这个,你应该设置你正在调用的代理类实例的 .Url 字段。
在程序中设置 .config 文件中的值:
一团糟;
在下一个应用程序启动之前可能不会被读取。
如果每次安装只需要执行一次,我会同意其他海报并使用 .config 文件和动态设置。
【讨论】:
例如。var api = new MyApi.Service(); api.Url = "http://yetanotherurl.com";
这是我所做的,但在生产中链接没有改变它仍然采用旧链接..【参考方案7】:
绝对使用 Url 属性是要走的路。是否将其设置在 app.config、数据库或第三个位置取决于您的配置需求。有时您不希望应用程序在您更改 Web 服务位置时重新启动。您可能没有负载均衡器来扩展后端。您可能正在热修补 Web 服务错误。您的实现也可能存在安全配置问题。无论是生产数据库用户名和密码,还是 ws 安全身份验证信息。适当的职责分离可以让您进入一些更复杂的配置设置。
如果您在代理生成的类周围添加包装类,则可以在每次创建包装类以调用 Web 方法时以某种统一的方式设置 Url 属性。
【讨论】:
【参考方案8】:我在这个问题上苦苦挣扎了几天,最后灯泡发出了咔嗒声。能够在运行时更改 Web 服务的 URL 的关键是覆盖构造函数,这是我使用部分类声明所做的。如上所述,将 URL 行为设置为 Dynamic 也必须完成。
这基本上创建了一个 Web 服务包装器,如果您必须在某个时候重新加载 Web 服务,通过添加服务引用,您不会丢失您的工作。 Microsoft 对 Partial 类的帮助特别指出,这种构造的部分原因是创建 Web 服务包装器。 http://msdn.microsoft.com/en-us/library/wa80x488(v=vs.100).aspx
// Web Service Wrapper to override constructor to use custom ConfigSection
// app.config values for URL/User/Pass
namespace myprogram.webservice
public partial class MyWebService
public MyWebService(string szURL)
this.Url = szURL;
if ((this.IsLocalFileSystemWebService(this.Url) == true))
this.UseDefaultCredentials = true;
this.useDefaultCredentialsSetExplicitly = false;
else
this.useDefaultCredentialsSetExplicitly = true;
【讨论】:
【参考方案9】:打开solition explorer
右键单击 web 服务将 URL 行为更改为动态
点击解决方案资源管理器中的“显示所有文件”图标
在网络参考中编辑 Reference.cs 文件
改变构造函数
public Service1()
this.Url = "URL"; // etc. string variable this.Url = ConfigClass.myURL
【讨论】:
【参考方案10】:对我来说,对 WebService 的引用是一个
服务参考
.
无论如何,这很容易。正如有人所说,您只需更改 web.config 文件中的 URL。
<system.serviceModel>
<bindings>
<basicHttpBinding>
<binding name="YourServiceSoap" />
</basicHttpBinding>
</bindings>
<client>
**** CHANGE THE LINE BELOW TO CHANGE THE URL ****
<endpoint address="http://10.10.10.100:8080/services/YourService.asmx"
binding="basicHttpBinding" bindingConfiguration="YourServiceSoap"
contract="YourServiceRef.YourServiceSoap" name="YourServiceSoap" />
</client>
【讨论】:
【参考方案11】:我知道这是一个老问题,但我们的解决方案比我在这里看到的要简单得多。我们将它用于 VS2010 及更高版本的 WCF 调用。字符串 url 可以来自应用设置或其他来源。在我的情况下,它是用户选择服务器的下拉列表。 TheService 是通过 VS 添加服务引用配置的。
private void CallTheService( string url )
TheService.TheServiceClient client = new TheService.TheServiceClient();
client.Endpoint.Address = new System.ServiceModel.EndpointAddress(url);
var results = client.AMethodFromTheService();
【讨论】:
很好,这似乎是最简单的解决方案,并且在 asmx Web 服务上也适用于我。 这是关于 WCF 但发帖人在谈论 Web 参考或 asmx Web 服务以上是关于如何在不重新编译的情况下在 .NET 中动态切换 Web 服务地址?的主要内容,如果未能解决你的问题,请参考以下文章
如何在不通过 HTTP 加载图像的情况下在 HTML 中显示“重新加载”符号?
如何在不重新启动的情况下在 Express 上重新加载一个文件?