【问题标题】:How to send an asynchronous post request in iOS如何在 iOS 中发送异步 post 请求
【发布时间】:2015-08-23 00:40:01
【问题描述】:

我需要LoginViewController 的帮助。 基本上我有一个小应用程序,我需要向应用程序发布一些数据,而我是 POST 和 JSON 的新手。如果我能得到一些帮助和理解,我将不胜感激。以下是我正在处理的一些要求。我的 .m 文件被标记为 LoginViewController。这就是我目前所拥有的

-(void)setRequest {

#pragma mark NSURLConnection Delegate Methods

- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
    // A response has been received, this is where we initialize the instance var you created
    // so that we can append data to it in the didReceiveData method
    // Furthermore, this method is called each time there is a redirect so reinitializing it
    // also serves to clear it
    _responseData = [[NSMutableData alloc] init];
}

- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
    // Append the new data to the instance variable you declared
    [_responseData appendData:data];
}

- (NSCachedURLResponse *)connection:(NSURLConnection *)connection willCacheResponse:(NSCachedURLResponse*)cachedResponse {
    // Return nil to indicate not necessary to store a cached response for this connection
    return nil;
}

- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
    // The request is complete and data has been received
    // You can parse the stuff in your instance variable now
}

- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {
    // The request has failed for some reason!
    // Check the error var
}

-(void)PostRequest{
    // Create the request.
    NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://dev.apppartner.com/AppPartnerProgrammerTest/scripts/login.php"]];

    // Specify that it will be a POST request
    request.HTTPMethod = @"POST";

    // This is how we set header fields
    [request setValue:@"application/xml; charset=utf-8" forHTTPHeaderField:@"Content-Type"];

    // Convert your data and set your request's HTTPBody property
    NSString *stringData = @"some data";
    NSData *requestBodyData = [stringData dataUsingEncoding:NSUTF8StringEncoding];
    request.HTTPBody = requestBodyData;

    // Create url connection and fire request
    NSURLConnection *conn = [[NSURLConnection alloc] initWithRequest:request delegate:self];
}
}

我什至不知道我是否设置正确。我看到了很多 hTTP 帖子,但我仍然对如何编写此语法感到困惑,是否需要添加任何其他内容。

我需要:

  1. 向“某个 url”发送异步 POST 请求
  2. POST 请求必须包含参数“用户名”和“密码”
  3. 将收到带有“代码”和“消息”的 JSON 响应
  4. 在 UIAlert 中显示解析的代码和消息以及 api 调用所用的毫秒数
  5. 唯一有效的登录名是用户名:超级密码:qwerty
  6. 登录成功后,点击 UIAlert 上的“确定”应该会让我们回到 MainMenuViewController

【问题讨论】:

  • 请不要在标题中大喊大叫。
  • 我尝试格式化您的代码,但由于某种原因,您似乎在 setRequest 方法中包含所有这些方法。为什么?
  • 首先,您现在应该使用NSURLSession,而不是即将在即将发布的 iOS 9 中弃用的 NSURLConnection。其次,您在这里得到的非常接近,但是如何配置的详细信息该请求完全取决于您的 Web 服务是如何编写的,但如果您真的发送 application/xml 请求,我会感到非常惊讶。 application/x-www-form-urlencoded 更为常见。或text/json。但是,如果您不了解您所连接的 Web 服务,我们将无法帮助您编写 Objective-C 代码。这决定了客户端代码。
  • 您好,谢谢您的回复。我感到困惑的是,我是 ios 新手,所以我只需要正确放置代码。 Web 服务是 JSON。我不应该把 xml 请求解析部分。但是,如果有人可以帮助我构建它,我将运行它并查看它是否按照编写需求的方式工作。谢谢你

标签: ios objective-c json


【解决方案1】:

我假设方法中的方法是一个错字。

除非您有特定的理由来实现所有这些委托方法,否则您最好使用任何一种方法

NSURLSessionDataTask *task =
[[NSURLSession sharedSession] dataTaskWithRequest:request
                                completionHandler:^(NSData *data,
                                        NSURLResponse *response,
                                        NSError *error) {
    // Code to run when the response completes...
}];
[task resume];

如果您仍需要支持 iOS 6 及更早版本和/或 OS X v10.8 及更早版本,则使用 NSURLConnection 的 sendAsynchronousRequest:queue:completionHandler: 方法或等效方法。

但是您缺少的重要内容是请求正文的编码。为此,您可能需要使用 URL 编码并为其指定适当的 MIME 类型,如下所示:

https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/URLLoadingSystem/WorkingwithURLEncoding/WorkingwithURLEncoding.html

基本上,您以“user=ENCODEDUSERNAME&pass=ENCODEDPASSWORD”的形式通过字符串连接构造一个字符串,其中两个编码值的构造如下:

NSString *encodedString = (__bridge_transfer NSString *)CFURLCreateStringByAddingPercentEscapes(
    kCFAllocatorDefault,
    (__bridge NSString *)originalString,
    NULL,
    CFSTR(":/?#[]@!$&'()*+,;="),
    kCFStringEncodingUTF8);

不要试图使用 stringByAddingPercentEscapesUsingEncoding: 和朋友。如果您的字符串包含某些保留的 URL 字符,他们会做错事。

【讨论】:

    【解决方案2】:

    我建议您尝试使用 AFNetworking 库。
    您可以找到代码here
    还有一个很好的教程here

    【讨论】:

      【解决方案3】:

      你可以这样做。

          NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
         [request addValue:@"YourUsername" forHTTPHeaderField:@"Username"];
         [request addValue:@"YourPassword" forHTTPHeaderField:@"Password"];
      
          [NSURLConnection
           sendAsynchronousRequest:request
           queue:[NSOperationQueue mainQueue]
           completionHandler:^(NSURLResponse *response, NSData *data, NSError *connectionError) {
      
               // TODO: Handle/Manage your response ,Data & errors 
      
           }];
      

      【讨论】:

      • sendAsynchronousRequest 在 iOS 9 中已被弃用!
      • 使用 NSURLSession。 [[NSURLSession sharedSession] dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) { //A piece of code after response completes. }];
      【解决方案4】:
       -(IBAction)registerclick:(id)sender
      {
          if (_password.text==_repassword.text)
          {
              [_errorlbl setHidden:YES];
      
      
          NSString *requstUrl=[NSString stringWithFormat:@"http://irtech.com/fresery/index.php?route=api/fresery/registerCustomer"];
      
      
      
          NSString *postString=[NSString stringWithFormat:@"name=asd&email=sooraj&phonenumber=8111&password=soorajsnr&type=1&facebookid=&image_path="];
             // _name.text,_email.text,_mobile.text,_password.text
      
          NSData *returnData=[[NSData alloc]init];
      
          NSMutableURLRequest *request=[[NSMutableURLRequest alloc]initWithURL:[NSURL URLWithString:requstUrl]];
          [request setHTTPMethod:@"POST"];
          [request setValue:[NSString stringWithFormat:@"%lu", (unsigned long)[postString length]] forHTTPHeaderField:@"Content-length"];
          [request setHTTPBody:[postString dataUsingEncoding:NSUTF8StringEncoding]];
      
      
          returnData = [NSURLConnection sendSynchronousRequest:request returningResponse:nil error:nil];
          resp=[NSJSONSerialization JSONObjectWithData:returnData options:NSJSONReadingMutableContainers error:nil];
      
      
              c=[[resp valueForKey:@"status" ]objectAtIndex:0];
              b=[[resp valueForKey:@"message"]objectAtIndex:0];
      

      【讨论】:

      • 这如何回答这个问题?
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2016-06-09
      • 1970-01-01
      • 1970-01-01
      • 2012-07-04
      • 2022-01-22
      相关资源
      最近更新 更多