objective-c HTTP POST 以表单形式发送请求

Posted

技术标签:

【中文标题】objective-c HTTP POST 以表单形式发送请求【英文标题】:objective-c HTTP POST send request as form 【发布时间】:2017-08-24 09:12:25 【问题描述】:

我已经使用 POST 方法在我的应用程序中调用带有标头值和参数的 API。 服务器只接受格式为

的表单
"form": 
        "action" : "login",
        "user" : "311"
,

当我们使用代码时

NSString *urlString = [NSString stringWithFormat:@"%@", url_string];

NSURL *url = [NSURL URLWithString:urlString];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
NSError *error;

NSDictionary *parameters = @@"action": @"login", @"user": @"311";
NSString *params = [self makeParamtersString:parameters withEncoding:NSUTF8StringEncoding];
NSData *jsonData2 = [params dataUsingEncoding:NSUTF8StringEncoding];

[request setHTTPMethod:@"POST"];
        [request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
[request setHTTPBody: jsonData2];
        [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:ourBlock];

我的表单是这样的

form = 
        action = login;
        user = 311;
;

你能产生你想要的结果吗? 你能帮我解决这个问题吗?

【问题讨论】:

【参考方案1】:

试试

NSString *urlString = [NSString stringWithFormat:@"%@", url_string];

NSURL *url = [NSURL URLWithString:urlString];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
NSError *error;

NSDictionary *parameters = @@"action": @"login", @"user": @"311";
NSData *jsonData = [NSJSONSerialization dataWithJSONObject: parameters options:0 error:&error];

[request setHTTPMethod:@"POST"];
        [request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
[request setHTTPBody: jsonData];
        [NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:ourBlock];

【讨论】:

【参考方案2】:

这样改参数怎么样。

NSDictionary *parameters = @@"form":@@"action": @"login", @"user": @"311";
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:parameters options:NSJSONWritingPrettyPrinted error:nil];
[request setHTTPMethod:@"POST"];
[request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[request addValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
[request setHTTPBody: jsonData];
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:ourBlock];

【讨论】:

然后我有错误异常:-[__NSDictionaryI stringValue]: unrecognized selector sent to instance 您的服务器似乎需要json格式的正文。如果是这样,请尝试更新的答案。【参考方案3】:

如果你需要 base64 编码试试这个

NSMutableDictionary *param = [@@"form":@@"action": @"login", @"user": @"311" mutableCopy];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:serviceURL];
NSString *strEncoded = [self encodeParameters:param];
NSData *requestData = [strEncoded dataUsingEncoding:NSUTF8StringEncoding];
[request setHTTPBody:requestData];
[request setValue:[NSString stringWithFormat:@"%lu",(unsigned long)requestData.length] forHTTPHeaderField:@"Content-Length"];

[request setHTTPMethod:@"POST"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
[request setValue:@"application/json" forHTTPHeaderField:@"Accept"];


// Function encodeParameters 

+(NSString *)encodeParameters:(NSDictionary *)dictEncode

// Encode character set as per BASE64
NSCharacterSet *URLBase64CharacterSet = [[NSCharacterSet characterSetWithCharactersInString:@"/+=\n"] invertedSet];

NSMutableString *stringEncode = [[NSMutableString alloc] init];
NSArray *allKeys = [dictEncode allKeys];
for (int i = 0;i < allKeys.count; i++) 
    NSString *key = [allKeys objectAtIndex:i];
    if([dictEncode valueForKey:key])
    
        [stringEncode appendFormat:@"%@=%@",key,[[dictEncode valueForKey:key] stringByAddingPercentEncodingWithAllowedCharacters:URLBase64CharacterSet]];
    

    if([allKeys count] > i+1)
    
        [stringEncode appendString:@"&"];
    


return stringEncode;

【讨论】:

【参考方案4】:

试试这个

NSURL * url = [NSURL URLWithString:@"%@",url_string];

NSURLSessionConfiguration * config = [NSURLSessionConfiguration defaultSessionConfiguration];

NSURLSession * session = [NSURLSession sessionWithConfiguration:config];

NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:url];

request.HTTPMethod = @"POST";

NSDictionary * paramters = [NSDictionary dictionaryWithObjectsAndKeys:@"login",@"action",@"311",@"user", nil]; // [NSDictionary dictionaryWithObjectsAndKeys:@"value",@"key", nil];


NSDictionary *params = @@"form": paramters;
NSError *err = nil;
NSData *jsonData2 = [NSJSONSerialization dataWithJSONObject:params options:0 error:&err];

【讨论】:

然后我的请求:form = "\"action\":\"login\",\"user\":\"311\"" = ""; ; @Albert ,我已经更新了答案。请检查并告诉我。 现在请求是:form = "\"form\":\"action\":\"login\",\"user\":\"311\"" = ""; ; 你试过这个吗?你能告诉我你的更新代码吗?【参考方案5】:

试试这个,

NSString *parameters = @"\"form\":\"action\" : \"login\", \"user\" : \"311\"";
NSData *jsonData2 = [parameters dataUsingEncoding:NSUTF8StringEncoding];

[request setHTTPMethod:@"POST"];
[request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
[request setHTTPBody: jsonData2];
[NSURLConnection sendAsynchronousRequest:request queue:[NSOperationQueue mainQueue] completionHandler:ourBlock];

【讨论】:

【参考方案6】:
 NSError *error;
 NSDictionary *parameters = @@"form": @@"action": @"login", @"user": @"311";
 NSData *jsonData = [NSJSONSerialization dataWithJSONObject:parameters 
      options:NSJSONWritingPrettyPrinted error:&error];
 request.HTTPBody = jsonData

 //Using NSURLSession is better option than using NSURLConnection
 NSURLSession *session = [NSURLSession sharedSession];
 NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) 
  NSHTTPURLResponse* respHttp = (NSHTTPURLResponse*) response;

  if (!error && respHttp.statusCode == 200) 

    NSDictionary* respondData = [NSJSONSerialization JSONObjectWithData:data options:NSJSONReadingAllowFragments error:&error];
    NSLog(@"%@", respondData);

   else
    NSLog(@"%@", error);
  
];

[dataTask resume];

【讨论】:

我的结果表单 = "\n \"action\" : \"login\",\n \"user\" : \"311\"\n" = ""; ;【参考方案7】:

试试AFNetwoking

   NSString *urlString = [NSString stringWithFormat:@"URL"];
   NSDictionary *para=  @@"action": @"login", @"user": @"311";
   AFHTTPRequestOperationManager *manager = [AFHTTPRequestOperationManager manager];
   manager.responseSerializer = [AFJSONResponseSerializer serializer];
   manager.responseSerializer.acceptableContentTypes = [NSSet setWithObject:@"text/html"];

   [manager POST:urlString parameters:para success:^(AFHTTPRequestOperation *operation, id responseObject) 
                       NSLog(@"JSON: %@", responseObject);

     failure:^(AFHTTPRequestOperation *operation, NSError *error) 
        NSLog(@"Error: %@", error);

    ];

【讨论】:

以上是关于objective-c HTTP POST 以表单形式发送请求的主要内容,如果未能解决你的问题,请参考以下文章

使用 Objective-C 发布多部分/表单数据

如何以编程方式重复表单 POST 请求

通过POST方法以objective-c的文件格式将语音和图像与文本数据一起上传到服务器的最简单方法是啥?

HTTP 的幂等性 分析 POST 表单重复提交

Objective-C如何使用标题中的嵌套字典将数据发送到Http Post请求

在 Objective-c 中使用 AFNetworking 对字典进行 URL 编码