我有一个saas服务,它有多个站点组(每个组属于不同的客户端)在一个IIS站点中运行,具有不同的iis绑定/主机名,这就是计划。
问题是我有网站的WCF服务以及它们在.net3.5上运行我不能有多个使用相同协议的基地址。我可以升级到.net4和enable this,但我更愿意只启动我必须的服务,目前每组一个站点,也不必提前升级。
我一直试图通过在代码中创建服务来做到这一点(下面两次尝试)。这使我可以完全控制服务的创建时间和位置(以及从web.config中删除几乎不会更改wcf配置的块)。
原创尝试:
using System;
using System.ServiceModel;
using System.ServiceModel.Activation;
using System.Web;
[ServiceContract(Namespace = "WcfInIis")]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class Tiny
{
[OperationContract]
public bool IsTiny()
{
return true;
}
}
public class Global : System.Web.HttpApplication
{
protected void Application_Start(object sender, EventArgs e)
{
Uri requestUri = HttpContext.Current.Request.Url;
//some logic to decide if this context is allowed to run the wcf service requested
ServiceHost host = new ServiceHost(typeof(Tiny), new Uri(requestUri.OriginalString.Replace(requestUri.LocalPath, string.Empty)));
WSHttpBinding binding = new WSHttpBinding(SecurityMode.None);
host.AddServiceEndpoint(typeof(Tiny), binding, "_service/tiny");
host.Open();
}
}
我对代码的问题是,当它运行时,我得到了
AddressAccessDeniedException: HTTP could not register URL http://+:56134/. Your process does not have access rights to this namespace (see http://go.microsoft.com/fwlink/?LinkId=70353 for details).]
。显然,这是在Cassini中运行但在IIS中运行时我收到相同的消息。
当我按照链接并执行命令时,它建议netsh http add urlacl url=http://+:56134/ user=domain\username
我得到一个空白屏幕,因为没有asp.net执行,并且该服务在目标网址上不可用。
总之,问题是:
修改后的尝试
使用@Nick Nieslanik的建议我构建了以下
using System;
using System.ServiceModel;
using System.ServiceModel.Activation;
using System.Web;
using System.Web.Routing;
[ServiceContract(Namespace = "WcfInIis")]
[AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
public class Tiny
{
[OperationContract]
public bool IsTiny()
{
return true;
}
}
public class ffServiceHandler : IRouteHandler, IHttpHandler
{
#region IRouteHandler Members
public System.Web.IHttpHandler GetHttpHandler(RequestContext requestContext)
{
return this;
}
#endregion
#region IHttpHandler Members
public bool IsReusable
{
get { return false; }
}
public void ProcessRequest(HttpContext context)
{
Uri requestUri = context.Request.Url;
//some logic to decide if this context is allowed to run the wcf service requested
ServiceHost host = new ServiceHost(typeof(Tiny), new Uri(requestUri.OriginalString.Replace(requestUri.LocalPath, string.Empty)));
WSHttpBinding binding = new WSHttpBinding(SecurityMode.None);
host.AddServiceEndpoint(typeof(Tiny), binding, "_services/tiny");
host.Open(); // throws AddressAlreadyInUseException
}
#endregion
}
public class Global : System.Web.HttpApplication
{
protected void Application_Start(object sender, EventArgs e)
{
RouteTable.Routes.Add(new Route
(
"_services/tiny",
new ffServiceHandler()
));
}
}
此修订后的尝试存在以下问题:
[AddressAlreadyInUseException: HTTP could not register URL http://+:56134/ because TCP port 56134 is being used by another application.]
。这是因为服务尝试在网站运行的同一端口上启动wcf服务。 摘要
任何人都可以帮助我让其中一个工作:
我认为另一种解决方案可能是创建动态.svc文件,如here所述。我会给你一个去发布我的结果。看起来这就是asp.net在请求它们时如何处理.svc文件,因为你怎么能避免使用AddressAlreadyInUseException呢?
由于
基思
答案 0 :(得分:0)
实现此目的的一种方法是使用ASP.NET UrlRouting并实现一个IRouteHandler对象,该对象将启动WCF服务主机......
http://msdn.microsoft.com/en-us/library/system.web.routing.iroutehandler.gethttphandler.aspx
http://msdn.microsoft.com/en-us/library/cc668201.aspx
我在过去设置WCF数据服务时已经这样做了,我不明白为什么它也不能在这里工作。