Asp Net Web API 2.1获取客户端IP地址

你好,我需要得到客户端的IP请求一些方法在Web API,我试图从这里使用这个代码,但它总是返回服务器本地IP,如何得到正确的方式?

HttpContext.Current.Request.UserHostAddress; 

从其他问题:

 public static class HttpRequestMessageExtensions { private const string HttpContext = "MS_HttpContext"; private const string RemoteEndpointMessage = "System.ServiceModel.Channels.RemoteEndpointMessageProperty"; public static string GetClientIpAddress(this HttpRequestMessage request) { if (request.Properties.ContainsKey(HttpContext)) { dynamic ctx = request.Properties[HttpContext]; if (ctx != null) { return ctx.Request.UserHostAddress; } } if (request.Properties.ContainsKey(RemoteEndpointMessage)) { dynamic remoteEndpoint = request.Properties[RemoteEndpointMessage]; if (remoteEndpoint != null) { return remoteEndpoint.Address; } } return null; } } 

以下链接可能会帮助你。 这是来自以下链接的代码。

参考: 获取客户端的IP通过ASPnetworkingnetworkingAPI

 using System.Net.Http; using System.ServiceModel.Channels; using System.Web; using System.Web.Http; namespace Trikks.Controllers.Api { public class IpController : ApiController { public string GetIp() { return GetClientIp(); } private string GetClientIp(HttpRequestMessage request = null) { request = request ?? Request; if (request.Properties.ContainsKey("MS_HttpContext")) { return ((HttpContextWrapper)request.Properties["MS_HttpContext"]).Request.UserHostAddress; } else if (request.Properties.ContainsKey(RemoteEndpointMessageProperty.Name)) { RemoteEndpointMessageProperty prop = (RemoteEndpointMessageProperty)request.Properties[RemoteEndpointMessageProperty.Name]; return prop.Address; } else if (HttpContext.Current != null) { return HttpContext.Current.Request.UserHostAddress; } else { return null; } } } } 

下面是另一种方法。

参考: 如何访问客户端的IP地址

对于网站托pipe版本

 string clientAddress = HttpContext.Current.Request.UserHostAddress; 

为自己主持

 object property; Request.Properties.TryGetValue(typeof(RemoteEndpointMessageProperty).FullName, out property); RemoteEndpointMessageProperty remoteProperty = property as RemoteEndpointMessageProperty; 

使用Web API 2.2: Request.GetOwinContext().Request.RemoteIpAddress

尝试使用IP

 ip = HttpContext.Current != null ? HttpContext.Current.Request.UserHostAddress : ""; 

如果您使用OWIN Self-host NuGet包自行托pipeAsp.Net 2.1,则可以使用以下代码:

  private string getClientIp(HttpRequestMessage request = null) { if (request == null) { return null; } if (request.Properties.ContainsKey("MS_OwinContext")) { return ((OwinContext) request.Properties["MS_OwinContext"]).Request.RemoteIpAddress; } return null; } 

最好把它转换成HttpContextBase ,这样你可以更容易地模拟和testing它

 public string GetUserIp(HttpRequestMessage request) { if (request.Properties.ContainsKey("MS_HttpContext")) { var ctx = request.Properties["MS_HttpContext"] as HttpContextBase; if (ctx != null) { return ctx.Request.UserHostAddress; } } return null; } 

我认为这是最明确的解决scheme,使用扩展方法:

 public static class HttpRequestMessageExtensions { private const string HttpContext = "MS_HttpContext"; private const string RemoteEndpointMessage = "System.ServiceModel.Channels.RemoteEndpointMessageProperty"; public static string GetClientIpAddress(this HttpRequestMessage request) { if (request.Properties.ContainsKey(HttpContext)) { dynamic ctx = request.Properties[HttpContext]; if (ctx != null) { return ctx.Request.UserHostAddress; } } if (request.Properties.ContainsKey(RemoteEndpointMessage)) { dynamic remoteEndpoint = request.Properties[RemoteEndpointMessage]; if (remoteEndpoint != null) { return remoteEndpoint.Address; } } return null; } } 

所以就像这样使用它:

 var ipAddress = request.GetClientIpAddress(); 

我们在我们的项目中使用这个。

源/参考: 在ASP.NET Web API中检索客户端的IP地址

我的解决scheme类似于user1587439的答案,但直接在控制器的实例上(而不是访问HttpContext.Current)。

在'Watch'窗口中,我看到this.RequestContext.WebRequest包含'UserHostAddress'属性,但由于它依赖于WebHostHttpRequestContexttypes(这是'System.Web.Http'程序集的内部) – 我不是能够直接访问它,所以我用reflection来直接访问它:

string hostAddress = ((System.Web.HttpRequestWrapper)this.RequestContext.GetType().Assembly.GetType("System.Web.Http.WebHost.WebHostHttpRequestContext").GetProperty("WebRequest").GetMethod.Invoke(this.RequestContext, null)).UserHostAddress;

我不是说这是最好的解决scheme。 使用reflection可能会导致在框架升级的情况下(由于名称变化)未来的问题,但为了我的需要,这是完美的