How can I get the exactly ip address which used to connect in iOS?

ε祈祈猫儿з 提交于 2019-12-06 01:51:44

问题


I created a request using a domain name, e.g., http://www.google.com. But how could I get the exactly ip address which the framework used to connect to the server?

I knew that the gethostbyname method or the nslookup method could give us the address, but since the ip address is dynamic allocated, maybe the ip address I request that time is different with these methods returned.

So is there a way for me to get the real requested ip address? (I wanted to get the ip programmatically, rather than using tcpdump, etc.)


回答1:


When you say "which the framework used" here, I assume you mean NSURLSession, NSURLConnection, UIWebView, or WKWebView. Each of those is a slightly different situation, but in all of them, the answer is that it's not possible directly (but see below; it's possible indirectly). You have no access to the underlying sockets that any of them use. All of them use connection pooling, which complicates things slightly even if you could get "the socket." And in the case of UIWebView and WKWebView, a single request to www.google.com may generate several independent connections, each of which could potentially interact with a different IP address.

(I'm a bit fascinated about what you're trying to do. Due to load balancing, a single IP address doesn't mean a single server, so IP addresses are only marginally more identifying than CNAMEs. Mixing in reverse proxies....)

If you need this kind of access, you have to manage the socket yourself. That's generally possible with all of the systems except WKWebView. I'll assume that you know already (or can easily study) how to create a socket and perform HTTP using CFSocket and CFHTTPMessage. This is extensively covered in the CFNetwork Programming Guide. If you've created the socket, you can use CFSocketCopyPeerAddress to check what host you really connected to. That's the piece you wanted.

Given you are able to create this kind of socket and manage it yourself, you can hook that into the major URL loaders (except WKWebView) using an NSURLProtocol. See Drop-in Offline Caching for UIWebView (and NSURLProtocol) for a quick introduction and some sample code. You just need to take the request and make it yourself with CFSocket, giving you the chance to see the exact port you're connected to.




回答2:


Your browser or whatever other tool you use to make a HTTP request will look up the address at the time of doing the request. On any reasonable system, they will use the same method for looking up the address as gethostbyname does, except that there might be local caching in the browser (which you can usually turn off or clear).

The request might get a redirection response to make the same request to a different location. These are often used for load balancing, etc. The only straightforward way I can see that you would be able to find out the 'ultimate destination' behind these, would be to make the request programmatically and record the details of any redirections, Of course, it is the nature of load balancing that you might redirected to a slightly different server each time.

This has nothing to do with 'dynamic allocation of IP addresses' by the way. If the IP address of www.google.com changes, it is likely to be not because the same server has been allocated a different IP address, but because requests are being directed to a different machine.




回答3:


In case you are using NSURLSession to obtain a URLSessionStreamTask, you can capture the underlying streams using -captureStreams. This will invoke the -URLSession:streamTask:didBecomeInputStream:outputStream: delegate method, giving you a NSInputStream and a NSOutputStream. NSInputStream is toll-free bridged to CFReadStreamRef and using CFReadStreamCopyProperty() and the constant kCFStreamPropertySocketNativeHandle provides you with the native socket handle, which you can pass into getpeername(). For Upload-, Download- and DataTasks, no such possibility seems to exist.



来源:https://stackoverflow.com/questions/31508871/how-can-i-get-the-exactly-ip-address-which-used-to-connect-in-ios

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!