街道地址验证

时间:2012-03-02 05:25:16

标签: objective-c ios xcode xmlhttprequest nsurlrequest

我的用户输入收件人地址(街道地址不是电子邮件)。我需要用USPS验证它,所以我知道它实际上是一个地址。

我现在正在挖掘他们的API,我想我明白了,但我不确定如何用objective-c来解决它。

所以它的工作原理如下:

  1. 我必须创建一个包含收件人姓名,地址和邮政编码的XML请求。
  2. 我必须将其发布到他们的服务器
  3. 他们以XML响应回复
  4. 以下是其构建的XML请求之一的示例:

    http://SERVERNAME/ShippingAPITest.dll?API=Verify&XML=<AddressValidateRequest% 20USERID="xxxxxxx"><Address ID="0"><Address1></Address1>
    <Address2>6406 Ivy Lane</Address2><City>Greenbelt</City><State>MD</State> <Zip5></Zip5><Zip4></Zip4></Address></AddressValidateRequest>
    

    有点乱码但是坏了:

    http://SERVERNAME/ShippingAPITest.dll?API=Verify&XML=
    <AddressValidateRequest% 20USERID="xxxxxxx">
      <Address ID="0">
        <Address1></Address1>
         <Address2>6406 Ivy Lane</Address2>
         <City>Greenbelt</City>
         <State>MD</State>
         <Zip5></Zip5>
         <Zip4></Zip4>
      </Address>
    </AddressValidateRequest>
    

    我的第一个想法似乎很明显,但也许有更好的方法可以解决它。由于XML feed很短,我应该通过简单的做法来进行构建:

    NSString * request = [NSString stringWithFormat:@“......”]

    在上面张贴的行中填写并格式化的地方。

    第二个问题是如何正确地将其发送到服务器?

    我只是创建一个NSURL请求并将URL作为构造的XML字符串?

    这就是我所拥有的,但我一直认为URL构造错误:

    - (void)verifyAddress:(Recipient*)_recipient {
    
        NSURL *_url = [NSURL URLWithString:@"http://testing.shippingapis.com/ShippingAPITest.dll?API=Verify&XML=<AddressValidateRequest%20USERID=\"********\"><Address ID=\"0\"><Address1></Address1><Address2>6406 Ivy Lane</Address2><City>Greenbelt</City><State>MD</State><Zip5></Zip5><Zip4></Zip4></Address></AddressValidateRequest>"];
    
        // Create the request.
        NSURLRequest *theRequest=[NSURLRequest requestWithURL:_url
                                                  cachePolicy:NSURLRequestUseProtocolCachePolicy
                                              timeoutInterval:60.0];
        // create the connection with the request
        // and start loading the data
        NSURLConnection *theConnection=[[NSURLConnection alloc] initWithRequest:theRequest delegate:self];
        if (theConnection) {
            // Create the NSMutableData to hold the received data.
            // receivedData is an instance variable declared elsewhere.
            receivedData = [NSMutableData data];
            NSString* newStr = [[NSString alloc] initWithData:receivedData
                                                     encoding:NSUTF8StringEncoding];
            NSLog(@"the response '%@'", newStr);
        } else {
            // Inform the user that the connection failed.
            NSLog(@"error");
        }
    
    }
    
    - (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response
    {
        // This method is called when the server has determined that it
        // has enough information to create the NSURLResponse.
    
        // It can be called multiple times, for example in the case of a
        // redirect, so each time we reset the data.
    
        // receivedData is an instance variable declared elsewhere.
        [receivedData setLength:0];
    }
    
    - (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data
    {
    
    
        // Append the new data to receivedData.
        // receivedData is an instance variable declared elsewhere.
        [receivedData appendData:data];
    }
    
    - (void)connection:(NSURLConnection *)connection
      didFailWithError:(NSError *)error
    {
    
        // inform the user
        NSLog(@"Connection failed! Error - %@ %@",
              [error localizedDescription],
              [[error userInfo] objectForKey:NSURLErrorFailingURLStringErrorKey]);
    }
    - (void)connectionDidFinishLoading:(NSURLConnection *)connection
    {
        NSString* newStr = [[NSString alloc] initWithData:receivedData
                                                 encoding:NSUTF8StringEncoding];
        NSLog(@"the response '%@'", newStr);
        // do something with the data
        // receivedData is declared as a method instance elsewhere
        NSLog(@"Succeeded! Received %d bytes of data",[receivedData length]);
    }
    

    我收到以下错误:

    Connection failed! Error - bad URL (null)
    

    我现在唯一的问题是,就NSURLConnection而言,我做的一切都好吗?我可以使用URL,我只是想确保我的实现是正确的,所以我不是在圈子里跑来跑去。 :P

2 个答案:

答案 0 :(得分:1)

您的网址中有% 20。它应该是%20(没有空格)。

可能还有其他问题,但这很容易被发现。如果您收到错误消息,则需要编辑问题并粘贴 exact 错误消息。

此外,您可以考虑使用Apple的NSURLRequestNSURLConnection课程,因为更多人可能会熟悉它们,因此您可能更容易找到帮助。

答案 1 :(得分:1)

Cory,我在地址验证行业工作(SmartyStreets,你正在尝试做的事情就是我们的专长)并且已经看到了很多与你类似的问题。

我们实际上曾经为我们的地址验证API(LiveAddress)支持XML端点。去年我们弃用它并部署了一种新的JSON格式,因为XML使用起来很笨,并且当它实际上只是一个简单的任务(对你,开发人员)来说有很多问题。

所以要记住一些事情......虽然Rob的答案在程序上是全面的,但这些也很重要:

  • USPS是美国的官方地址来源,但其核心域提供API服务。特别是最近的财务问题,我怀疑API的支持和维护会随着时间的推移而减弱。

  • 您使用的API的License Agreement限制性很强。例如:

      

    用户同意仅使用USPS网站,API和USPS数据来促进USPS运输交易。 [2012年1月27日]

    意思是,如果您使用他们的API通过USPS发送邮件或包裹,那很好,但是出于任何其他目的,它是不允许的,它违反了服务条款。

  • 我看到你正在为iOS开发。有一个名为TouchJSON伟大的 JSON库,在我看来,它比Objective-C中的XML格式更容易使用。

虽然USPS服务确实有效,但他们通过CASS认证私人实体以更好的价值提供数据(更多专业,经验,功能等)。

这些和其他疾病可以通过第三方供应商的服务来补救。更多细节和原因是documented here。您选择哪个提供商取决于您,但我很乐意亲自回答任何其他与地址验证相关的问题。