如何获取设备的公共IP地址

时间:2021-01-09 07:09:28

I found this sample code to get all local IP addresses, but I don't find an easy solution to get the public IP.

我找到了这个示例代码来获取所有本地IP地址,但我找不到一个简单的解决方案来获取公共IP。

A legacy class from Apple allowed to do that ... but it's legacy ...

来自Apple的传统课程允许这样做...但它的遗产......

7 个解决方案

#1


8  

I have used ALSystemUtilities in the past. You basically have to make a call externally to find this out.

我过去使用过ALSystemUtilities。你基本上必须在外部打电话才能找到它。

+ (NSString *)externalIPAddress {
    // Check if we have an internet connection then try to get the External IP Address
    if (![self connectedViaWiFi] && ![self connectedVia3G]) {
        // Not connected to anything, return nil
        return nil;
    }

    // Get the external IP Address based on dynsns.org
    NSError *error = nil;
    NSString *theIpHtml = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"http://www.dyndns.org/cgi-bin/check_ip.cgi"]
                                                   encoding:NSUTF8StringEncoding
                                                      error:&error];
    if (!error) {
        NSUInteger  an_Integer;
        NSArray *ipItemsArray;
        NSString *externalIP;
        NSScanner *theScanner;
        NSString *text = nil;

        theScanner = [NSScanner scannerWithString:theIpHtml];

        while ([theScanner isAtEnd] == NO) {

            // find start of tag
            [theScanner scanUpToString:@"<" intoString:NULL] ;

            // find end of tag
            [theScanner scanUpToString:@">" intoString:&text] ;

            // replace the found tag with a space
            //(you can filter multi-spaces out later if you wish)
            theIpHtml = [theIpHtml stringByReplacingOccurrencesOfString:
                         [ NSString stringWithFormat:@"%@>", text]
                                                             withString:@" "] ;
            ipItemsArray = [theIpHtml  componentsSeparatedByString:@" "];
            an_Integer = [ipItemsArray indexOfObject:@"Address:"];
            externalIP =[ipItemsArray objectAtIndex:++an_Integer];
        }
        // Check that you get something back
        if (externalIP == nil || externalIP.length <= 0) {
            // Error, no address found
            return nil;
        }
        // Return External IP
        return externalIP;
    } else {
        // Error, no address found
        return nil;
    }
}

Source from ALSystemUtilities

来自ALSystemUtilities的资源

#2


14  

It's as simple as this:

这很简单:

NSString *publicIP = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"https://icanhazip.com/"] encoding:NSUTF8StringEncoding error:nil];
publicIP = [publicIP stringByTrimmingCharactersInSet:[NSCharacterSet newlineCharacterSet]]; // IP comes with a newline for some reason

#3


0  

You have to query an external server to find out the public IP. Either set up your own server (1 line of php code) or use one of the many available ones which return the IP as plain text or json upon http query. Like for example http://myipdoc.com/ip.php .

您必须查询外部服务器以找出公共IP。要么设置自己的服务器(1行php代码),要么使用许多可用的服务器中的一个,它们在http查询时将IP作为纯文本或json返回。例如http://myipdoc.com/ip.php。

#4


0  

For those of us using Swift, here's my translation of Andrei's answer with the addition of NSURLSession to run it in the background. To check the network, I use Reachability.swift. Also, remember to add dyndns.org to NSExceptionDomains for NSAppTransportSecurity in your info.plist.

对于我们这些使用Swift的人来说,这是我对Andrei的回答的翻译,添加了NSURLSession以在后台运行它。要检查网络,我使用Reachability.swift。另外,请记住在info.plist中将dyndns.org添加到NSExceptionDomains for NSAppTransportSecurity。

var ipAddress:String?
func getIPAddress() {

    if reachability!.isReachable() == false {
        return
    }

    guard let ipServiceURL = NSURL(string: "http://www.dyndns.org/cgi-bin/check_ip.cgi") else {
        return
    }

    let session = NSURLSession.sharedSession()

    let task = session.dataTaskWithURL(ipServiceURL, completionHandler: {(data, response, error) -> Void in
        if error != nil {
            print(error)
            return
        }

        let ipHTML = NSString(data: data!, encoding: NSUTF8StringEncoding) as? String

        self.ipAddress = self.scanForIPAddress(ipHTML)

    })

    task.resume()
}

func scanForIPAddress(var ipHTML:String?) -> String? {

    if ipHTML == nil {
        return nil
    }

    var externalIPAddress:String?
    var index:Int?
    var ipItems:[String]?
    var text:NSString?

    let scanner = NSScanner(string: ipHTML!)

    while scanner.atEnd == false {
        scanner.scanUpToString("<", intoString: nil)

        scanner.scanUpToString(">", intoString: &text)

        ipHTML = ipHTML!.stringByReplacingOccurrencesOfString(String(text!) + ">", withString: " ")

        ipItems = ipHTML!.componentsSeparatedByString(" ")

        index = ipItems!.indexOf("Address:")
        externalIPAddress = ipItems![++index!]

    }

    if let ip = externalIPAddress {
        print("External IP Address: \(ip)")
    }

    return externalIPAddress

}

#5


0  

You can call a public IP address lookup services to get this? I have set up http://ipof.in as a service that returns the device IP address as JSON / XML or plain text. You can find them here

您可以调用公共IP地址查找服务来获取此信息吗?我已将http://ipof.in设置为将设备IP地址作为JSON / XML或纯文本返回的服务。你可以在这里找到它们

For JSON with GeoIP data

对于带有GeoIP数据的JSON

http://ipof.in/json

https://ipof.in/json

For XML response

对于XML响应

http://ipof.in/xml

https://ipof.in/xml

For plain text IP address

对于纯文本IP地址

http://ipof.in/txt

https://ipof.in/txt

#6


0  

I find both Andrei and Tarek's answers helpful. Both are relying a web URL to query the "public IP" of the iOS/OS X device.

我发现Andrei和Tarek的答案都很有帮助。两者都依靠Web URL来查询iOS / OS X设备的“公共IP”。

However, there is an issue with this approach in some part of the world where URL such as "http://www.dyndns.org/cgi-bin/check_ip.cgi" is censored as in andrei's answer:

但是,在世界某些地方存在这种方法的问题,其中诸如“http://www.dyndns.org/cgi-bin/check_ip.cgi”之类的URL在andrei的答案中被审查:

NSString *theIpHtml = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"http://www.dyndns.org/cgi-bin/check_ip.cgi"]
encoding:NSUTF8StringEncoding
                                                  error:&error];

In this case, we will need to use an "uncensored" URL within the region such as http://1212.ip138.com/ic.asp

在这种情况下,我们需要在区域内使用“未经审查”的URL,例如http://1212.ip138.com/ic.asp

Note that the web URL could use a different HTML and encoding than what Andrei's answer could parse - in the URL above, some very gentle changes can fix it by using kCFStringEncodingGB_18030_2000 for http://1212.ip138.com/ic.asp

请注意,Web URL可以使用与Andrei的答案可以解析的不同的HTML和编码 - 在上面的URL中,一些非常温和的更改可以通过使用kCFStringEncodingGB_18030_2000来修复它http://1212.ip138.com/ic.asp

NSURL* externalIPCheckURL = [NSURL URLWithString: @"http://1212.ip138.com/ic.asp"];
encoding:NSUTF8StringEncoding error:nil];

NSStringEncoding encoding = CFStringConvertEncodingToNSStringEncoding(kCFStringEncodingGB_18030_2000);

NSString *theIpHtml = [NSString stringWithContentsOfURL: externalIPCheckURL
                                                   encoding: encoding
                                                      error: &error];

#7


0  

I use ipify and with no complaints.

我使用ipify并没有抱怨。

NSURL *url = [NSURL URLWithString:@"https://api.ipify.org/"];
NSString *ipAddress = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:nil];
NSLog(@"My public IP address is: %@", ipAddress);

#1


8  

I have used ALSystemUtilities in the past. You basically have to make a call externally to find this out.

我过去使用过ALSystemUtilities。你基本上必须在外部打电话才能找到它。

+ (NSString *)externalIPAddress {
    // Check if we have an internet connection then try to get the External IP Address
    if (![self connectedViaWiFi] && ![self connectedVia3G]) {
        // Not connected to anything, return nil
        return nil;
    }

    // Get the external IP Address based on dynsns.org
    NSError *error = nil;
    NSString *theIpHtml = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"http://www.dyndns.org/cgi-bin/check_ip.cgi"]
                                                   encoding:NSUTF8StringEncoding
                                                      error:&error];
    if (!error) {
        NSUInteger  an_Integer;
        NSArray *ipItemsArray;
        NSString *externalIP;
        NSScanner *theScanner;
        NSString *text = nil;

        theScanner = [NSScanner scannerWithString:theIpHtml];

        while ([theScanner isAtEnd] == NO) {

            // find start of tag
            [theScanner scanUpToString:@"<" intoString:NULL] ;

            // find end of tag
            [theScanner scanUpToString:@">" intoString:&text] ;

            // replace the found tag with a space
            //(you can filter multi-spaces out later if you wish)
            theIpHtml = [theIpHtml stringByReplacingOccurrencesOfString:
                         [ NSString stringWithFormat:@"%@>", text]
                                                             withString:@" "] ;
            ipItemsArray = [theIpHtml  componentsSeparatedByString:@" "];
            an_Integer = [ipItemsArray indexOfObject:@"Address:"];
            externalIP =[ipItemsArray objectAtIndex:++an_Integer];
        }
        // Check that you get something back
        if (externalIP == nil || externalIP.length <= 0) {
            // Error, no address found
            return nil;
        }
        // Return External IP
        return externalIP;
    } else {
        // Error, no address found
        return nil;
    }
}

Source from ALSystemUtilities

来自ALSystemUtilities的资源

#2


14  

It's as simple as this:

这很简单:

NSString *publicIP = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"https://icanhazip.com/"] encoding:NSUTF8StringEncoding error:nil];
publicIP = [publicIP stringByTrimmingCharactersInSet:[NSCharacterSet newlineCharacterSet]]; // IP comes with a newline for some reason

#3


0  

You have to query an external server to find out the public IP. Either set up your own server (1 line of php code) or use one of the many available ones which return the IP as plain text or json upon http query. Like for example http://myipdoc.com/ip.php .

您必须查询外部服务器以找出公共IP。要么设置自己的服务器(1行php代码),要么使用许多可用的服务器中的一个,它们在http查询时将IP作为纯文本或json返回。例如http://myipdoc.com/ip.php。

#4


0  

For those of us using Swift, here's my translation of Andrei's answer with the addition of NSURLSession to run it in the background. To check the network, I use Reachability.swift. Also, remember to add dyndns.org to NSExceptionDomains for NSAppTransportSecurity in your info.plist.

对于我们这些使用Swift的人来说,这是我对Andrei的回答的翻译,添加了NSURLSession以在后台运行它。要检查网络,我使用Reachability.swift。另外,请记住在info.plist中将dyndns.org添加到NSExceptionDomains for NSAppTransportSecurity。

var ipAddress:String?
func getIPAddress() {

    if reachability!.isReachable() == false {
        return
    }

    guard let ipServiceURL = NSURL(string: "http://www.dyndns.org/cgi-bin/check_ip.cgi") else {
        return
    }

    let session = NSURLSession.sharedSession()

    let task = session.dataTaskWithURL(ipServiceURL, completionHandler: {(data, response, error) -> Void in
        if error != nil {
            print(error)
            return
        }

        let ipHTML = NSString(data: data!, encoding: NSUTF8StringEncoding) as? String

        self.ipAddress = self.scanForIPAddress(ipHTML)

    })

    task.resume()
}

func scanForIPAddress(var ipHTML:String?) -> String? {

    if ipHTML == nil {
        return nil
    }

    var externalIPAddress:String?
    var index:Int?
    var ipItems:[String]?
    var text:NSString?

    let scanner = NSScanner(string: ipHTML!)

    while scanner.atEnd == false {
        scanner.scanUpToString("<", intoString: nil)

        scanner.scanUpToString(">", intoString: &text)

        ipHTML = ipHTML!.stringByReplacingOccurrencesOfString(String(text!) + ">", withString: " ")

        ipItems = ipHTML!.componentsSeparatedByString(" ")

        index = ipItems!.indexOf("Address:")
        externalIPAddress = ipItems![++index!]

    }

    if let ip = externalIPAddress {
        print("External IP Address: \(ip)")
    }

    return externalIPAddress

}

#5


0  

You can call a public IP address lookup services to get this? I have set up http://ipof.in as a service that returns the device IP address as JSON / XML or plain text. You can find them here

您可以调用公共IP地址查找服务来获取此信息吗?我已将http://ipof.in设置为将设备IP地址作为JSON / XML或纯文本返回的服务。你可以在这里找到它们

For JSON with GeoIP data

对于带有GeoIP数据的JSON

http://ipof.in/json

https://ipof.in/json

For XML response

对于XML响应

http://ipof.in/xml

https://ipof.in/xml

For plain text IP address

对于纯文本IP地址

http://ipof.in/txt

https://ipof.in/txt

#6


0  

I find both Andrei and Tarek's answers helpful. Both are relying a web URL to query the "public IP" of the iOS/OS X device.

我发现Andrei和Tarek的答案都很有帮助。两者都依靠Web URL来查询iOS / OS X设备的“公共IP”。

However, there is an issue with this approach in some part of the world where URL such as "http://www.dyndns.org/cgi-bin/check_ip.cgi" is censored as in andrei's answer:

但是,在世界某些地方存在这种方法的问题,其中诸如“http://www.dyndns.org/cgi-bin/check_ip.cgi”之类的URL在andrei的答案中被审查:

NSString *theIpHtml = [NSString stringWithContentsOfURL:[NSURL URLWithString:@"http://www.dyndns.org/cgi-bin/check_ip.cgi"]
encoding:NSUTF8StringEncoding
                                                  error:&error];

In this case, we will need to use an "uncensored" URL within the region such as http://1212.ip138.com/ic.asp

在这种情况下,我们需要在区域内使用“未经审查”的URL,例如http://1212.ip138.com/ic.asp

Note that the web URL could use a different HTML and encoding than what Andrei's answer could parse - in the URL above, some very gentle changes can fix it by using kCFStringEncodingGB_18030_2000 for http://1212.ip138.com/ic.asp

请注意,Web URL可以使用与Andrei的答案可以解析的不同的HTML和编码 - 在上面的URL中,一些非常温和的更改可以通过使用kCFStringEncodingGB_18030_2000来修复它http://1212.ip138.com/ic.asp

NSURL* externalIPCheckURL = [NSURL URLWithString: @"http://1212.ip138.com/ic.asp"];
encoding:NSUTF8StringEncoding error:nil];

NSStringEncoding encoding = CFStringConvertEncodingToNSStringEncoding(kCFStringEncodingGB_18030_2000);

NSString *theIpHtml = [NSString stringWithContentsOfURL: externalIPCheckURL
                                                   encoding: encoding
                                                      error: &error];

#7


0  

I use ipify and with no complaints.

我使用ipify并没有抱怨。

NSURL *url = [NSURL URLWithString:@"https://api.ipify.org/"];
NSString *ipAddress = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:nil];
NSLog(@"My public IP address is: %@", ipAddress);