Reputation: 179
I am trying to send an array of dictionaries to server and before that I am converting to json format
NOTE:- the server is working well my friend in android is getting the response and data for successful post method
below is my code of post method:-
NSError *error;
NSMutableDictionary *tvarns = [[NSMutableDictionary alloc] init];
tvarns[@"order_cart"]=_order_cart;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:tvarns
options:NSJSONWritingPrettyPrinted error:&error];
NSLog(@"%@",jsonData);
NSString* order_cart;
order_cart = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
NSLog(@"%@",order_cart);
NSString *post = [NSString stringWithFormat:@"%@",order_cart];
NSData *postData = [post dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES];
// Next up, we read the postData's length, so we can pass it along in the request.
NSString *postLength = [NSString stringWithFormat:@"%lu", (unsigned long)[postData length]];
// Now that we have what we'd like to post, we can create an NSMutableURLRequest, and include our postData
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:@"http://test.kre8tives.com/barebon/add_cartapi.php"]];
[request setHTTPMethod:@"POST"];
[request setValue:postLength forHTTPHeaderField:@"Content-Length"];
[request setHTTPBody:postData];
NSLog(@"the data Details is %@", post);
// And finally, we can send our request, and read the reply by creating a new NSURLSession:
NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
[[session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
NSString *requestReply = [[NSString alloc] initWithData:data encoding:NSASCIIStringEncoding]; // this is json string
NSLog(@"Reply = %@", requestReply);
// NSError *error;
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:data options:0 error:&error]; // you need to convert to dictionary object
NSLog(@"requestReply: %@", jsonDict);
}] resume];
[self presentViewController:alertController animated:YES completion:nil];
}
The value which the server wants is
{"order_cart":[{"customer_id":"114","item_id":14,"_id":"591d3822f55e2270202d8ff1","item_name":"Bira White","item_quantity":"2","price":"180.0","qr_code":"table21","phone":"7008841769","customer_name":"Samanthaa"},{"customer_id":"114","item_id":15,"_id":"591d3822f55e2270202d8ff0","item_name":"Bira Blonde","item_quantity":"2","price":"200.0","qr_code":"table21","phone":"7008841769","customer_name":"Samanthaa"}]}
My nslog is
2017-06-28 16:16:41.334 Barebones[3139:211622] the data Details is {
"order_cart" : [
{
"phone" : "9047038606",
"item_quantity" : "7",
"qr_code" : "table21",
"item_name" : "Bottled Water",
"price" : "175",
"customer_id" : "116",
"customer_name" : "Akshay"
},
{
"phone" : "9047038606",
"item_quantity" : "2",
"qr_code" : "table21",
"item_name" : "Fresh Lime Soda(Sweet, Salt, Plain)",
"price" : "158",
"customer_id" : "116",
"customer_name" : "Akshay"
},
{
"phone" : "9047038606",
"item_quantity" : "2",
"qr_code" : "table21",
"item_name" : "Bottled Water",
"price" : "50",
"customer_id" : "116",
"customer_name" : "Akshay"
},
{
"phone" : "9047038606",
"item_quantity" : "2",
"_id" : "591d3822f55e2270202d8ff0",
"item_name" : "Bira Blonde",
"price" : "86",
"qr_code" : "table21",
"customer_id" : "116",
"item_id" : "3971",
"customer_name" : "Akshay"
},
{
"phone" : "9047038606",
"item_quantity" : "1",
"qr_code" : "table21",
"item_name" : "Bottled Water",
"price" : "25",
"customer_id" : "116",
"customer_name" : "Akshay"
}
]
}
2017-06-28 16:16:41.485 Barebones[3139:211669] Reply = {"order_id":3961,"success":1}
<script type='text/javascript' src='https://cdnjs.cloudflare.com/ajax/libs/jquery/3.2.1/jquery.min.js'>. </script>
<script>
var data_array='{"source":{"name":"Kre8Tives","id":"SJQ6kyA1","order_id":"3961"},"customer":{"firstname":"","mobile":""},"tabType":"table","tabId":"591d3790498782970be66302","tableNumber":"1","items":null}';
alert(data_array);
var settings = {
'async': true,
'crossDomain': true,
'url': 'http://posistapi.com/api/v1/table_order/push?customer_key=8c982f5e9ef091e9d5c8fb142311b49a68049b102de5e0987ebce29755c454227fbc7573c7da4199f126524a3ac7a39a&tabtype=table',
'method': 'POST',
'headers': {
'postman-token': 'e200ae19-d083-a98a-6db3-53fc2f8bd73f',
'cache-control': 'no-cache',
'authorization': 'Basic [removed]',
'content-type': 'application/json'
},
'processData': false,
'data': data_array,
'acceptUrl':'http://test.kre8tives.com/barebon/order_confirm.php',
'rejectUrl':'http://test.kre8tives.com/barebon/order_confirm.php',
'billPrintUrl':'http://test.kre8tives.com/barebon/order_confirm.php'
}
$.ajax(settings).done(function (response) {
console.log(response);
});
</script>
2017-06-28 16:16:41.486 Barebones[3139:211669] requestReply: (null)
I have converted to desired son format but still I am getting no reply from server
Even if I send return the data what I send from server I get null!!why is that ???thanks in advance !!:)
This is my PHP code
<?php
include('order-function.php');
if($_SERVER["REQUEST_METHOD"] == "POST")
{
$order_cart=$_POST['order_cart'];
$items=json_decode($order_cart,true);
include('dbconfig.php');
$response = array();
try
{
$total_item_price=0;
foreach ($items['order_cart'] as $item) { //['order_cart']
$customer_id=$item['customer_id'];
$customer_name=$item['customer_name'];
$phone=$item['phone'];
$_id=$item['_id'];
$item_name=$item['item_name'];
$item_quantity=$item['item_quantity'];
$price=$item['price'];
$qr_code=$item['qr_code'];
$products[]=array(
"_id"=>"$_id",
"item_name"=> $item_name,
"item_price"=> $price,
"item_quantity"=> $item_quantity
);
$price_new+=$price;
$item_push[]=array(
"id"=>"$_id",
"rate"=> $price,
"quantity"=> $item_quantity
);
}
$product_details=json_encode($products);
$add_to_cart = "INSERT INTO order_cart (customer_id,product_details,order_amount,qr_code) VALUES ('$customer_id','$product_details','$price_new','$qr_code')";
$result = mysqli_query($conn,$add_to_cart);
$order_id=mysqli_insert_id($conn);
if ($result) {
$data['source']=array("name"=>"Kre8Tives",
"id"=>"SJQ6kyA1",
"order_id"=>"$order_id"
);
$data['customer']=array(
"firstname"=>"$customer_name",
"mobile"=>"$phone"
);
$data['tabType']= "table";
$data['tabId']= "591d3790498782970be66302";
$data['tableNumber']= "1";
//items
$data_one=json_encode($item_push,JSON_NUMERIC_CHECK);
$data_new=json_decode($data_one);
$data['items']=$data_new;
$data_item=json_encode($data);
$response["order_id"] = $order_id;
$response["success"] = 1;
// print_r(json_encode($data));die;
} else {
$response["success"] = 0;
}
echo json_encode($response);
push_order($data_item);
}
catch(Exception $e)
{
$response["success"] = 0;
$response["message"] = "error occured";
}
}
?>
Upvotes: 2
Views: 1883
Reputation: 437582
Frankly, looking at your NSLog
results, it looks like the server code is erroneously returning some extra HTML (starting at the <script>
line) after the JSON result. Looking at the body of the $response
, it's reporting success, but it looks like some extra text is included in the response, either as a result of push_order
, or some HTML after after the %>
, or some web service error that is inserting some extra HTML.
Focusing on your client request code, it should set the Content-Type
and Accept
headers, though that’s not critical. But well designed requests should do that. The key issue is that the PHP should be outputting nothing else before or after the outputting of the JSON.
For what it's worth, if your web service was expecting a true JSON request, I would suggest a series of simplifications to your client code (in addition to setting those two additional headers). For example, just send the output of NSJSONSerialization
as the httpBody
; don't take that NSData
, convert it to a NSString
and then convert it back to a NSData
. Just send jsonData
as httpBody
:
NSDictionary *tvarns = @{@"order_cart": _order_cart};
NSError *error;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:tvarns
options:0
error:&error];
// if you want to see the JSON, you can do this, but this is not needed
//
// NSString *order_cart = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
// NSLog(@"%@",order_cart);
// none of this stuff is needed; at worst, it can introduce encoding problems; at best, it's inefficient to do all that stuff
//
// NSString *post = [NSString stringWithFormat:@"%@",order_cart];
// NSLog(@"the data Details is %@", post);
// NSData *postData = [post dataUsingEncoding:NSASCIIStringEncoding allowLossyConversion:YES];
// // Next up, we read the postData's length, so we can pass it along in the request.
// NSString *postLength = [NSString stringWithFormat:@"%lu", (unsigned long)[postData length]];
// Now that we have what we'd like to post, we can create an NSMutableURLRequest, and include our jsonData
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:@"http://test.kre8tives.com/barebon/add_cartapi.php"]];
[request setHTTPMethod:@"POST"];
// you don't need this, because NSURLSession sets the length for you
//
// [request setValue:postLength forHTTPHeaderField:@"Content-Length"];
// use the original jsonData here
[request setHTTPBody:jsonData];
// you should, if you're a good web-service citizen, set the header; it's not always needed, but it's advisable
// tell the server that you're sending JSON request
[request setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
// tell the server that you're expecting JSON response
[request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
// Unless you need a new session for some reason, it's better to use the shared session
NSURLSession *session = [NSURLSession sharedSession];
[[session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
if (error) {
NSLog(@"error: %@", error);
}
if (!data) {
return;
}
NSError *parseError;
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:data options:0 error:&parseError]; // you need to convert to dictionary object
if (jsonDict) {
NSLog(@"requestReply: %@", jsonDict);
} else {
NSLog(@"parseError: %@", parseError);
NSLog(@"response: %@", response); // when you have failure, it's sometimes useful to see what this says
NSString *requestReply = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; // this is json string
NSLog(@"requestReply: %@", requestReply);
}
}] resume];
Again, having suggested these simplifications, I really suspect that there's a bug in the server code, including all that junk after the <script>...
. I bet your Android code is ignoring all of this erroneous data at the end of the response, whereas NSJSONSerialization
is correctly pointing out that the response is not, technically, well-formed JSON. (By the way, my code above will correctly log the JSON error.)
Looking at your PHP code that you've added to your revised question, it's grabbing $order_cart=$_POST['order_cart'];
, which means that your web service is expecting a x-www-form-urlencoded
request. The PHP code then proceeds to define $items
as json_decode($order_cart,true)
and then iterate with foreach
through $items['order_cart']
. That means that the web service is expecting x-www-form-urlencoded
request whose value associated with order_cart
key is, itself, a JSON dictionary keyed by order_cart
(again), i.e., the request body will look like order_cart={"order_cart":[...]}
.
That's not a very elegant design, but if you're stuck with that, you're going to have to create x-www-form-urlencoded
request whose key is order_cart
and whose value is a percent-encoded representation of a JSON dictionary of the form {"content-type":[...]}
.
NSDictionary *tvarns = @{@"order_cart": _order_cart};
NSError *error;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:tvarns
options:0
error:&error];
NSString *jsonString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
NSString *bodyString = [NSString stringWithFormat:@"order_cart=%@", [jsonString stringByAddingPercentEncodingQueryValue]];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:[NSURL URLWithString:@"http://test.kre8tives.com/barebon/add_cartapi.php"]];
[request setHTTPMethod:@"POST"];
[request setHTTPBody:[bodyString dataUsingEncoding:NSUTF8StringEncoding]];
[request setValue:@"application/x-www-form-urlencoded" forHTTPHeaderField:@"Content-Type"];
[request setValue:@"application/json" forHTTPHeaderField:@"Accept"];
// Unless you need a new session for some reason, it's better to use the shared session
NSURLSession *session = [NSURLSession sharedSession];
[[session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
if (error) {
NSLog(@"error: %@", error);
}
if (!data) {
return;
}
NSError *parseError;
NSDictionary *jsonDict = [NSJSONSerialization JSONObjectWithData:data options:0 error:&parseError]; // you need to convert to dictionary object
if (jsonDict) {
NSLog(@"requestReply: %@", jsonDict);
} else {
NSLog(@"parseError: %@", parseError);
NSLog(@"response: %@", response); // when you have failure, it's sometimes useful to see what this says
NSString *requestReply = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding]; // this is json string
NSLog(@"requestReply: %@", requestReply);
}
}] resume];
Where:
@interface NSCharacterSet (URLQueryValue)
/**
Character set of characters allowed within value (or a key) in a application/x-www-form-urlencode key/value pair.
@return NSCharacterSet of allowed characters.
*/
+ (NSCharacterSet *) URLQueryValueAllowedCharacterSet;
@end
@implementation NSCharacterSet (URLQueryValue)
+ (NSCharacterSet *) URLQueryValueAllowedCharacterSet {
static NSString * const generalDelimitersToEncode = @":#[]@"; // does not include "?" or "/" due to RFC 3986 - Section 3.4
static NSString * const subDelimitersToEncode = @"!$&'()*+,;=";
NSString * const characterToEncode = [generalDelimitersToEncode stringByAppendingString:subDelimitersToEncode];
NSMutableCharacterSet *cs = [[NSCharacterSet URLQueryAllowedCharacterSet] mutableCopy];
[cs removeCharactersInString:characterToEncode];
return cs;
}
@end
And
@interface NSString (URLQueryValue)
/**
String percent encoding for key or value in key/value pair within an application/x-www-form-urlencoded request.
@return Percent encoded string.
*/
- (NSString *)stringByAddingPercentEncodingQueryValue;
@end
@implementation NSString (URLQueryValue)
- (NSString *)stringByAddingPercentEncodingQueryValue {
return [self stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet URLQueryAllowedCharacterSet]];
}
@end
Frankly, I'd suggest changing the web service to process a true JSON request, not JSON within a x-www-form-urlencoded
request. If you did that, the client code would look more like my original answer above. But for your existing web service code, you'd create something like my second code sample.
Upvotes: 1
Reputation: 681
NSDictionary *dict = @{@"order_cart": _order_cart};
NSLog(@"dict = %@", dict);
NSError *error;
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:dict options:0 error:&error];
// For debug
NSString *postString = [[NSString alloc] initWithData:jsonData encoding:NSUTF8StringEncoding];
NSLog(@"postString = %@", postString);
//
NSString *postLength = [NSString stringWithFormat:@"%lu", (unsigned long)[jsonData length]];
NSURL *url = [NSURL URLWithString:@"http://test.kre8tives.com/barebon/add_cartapi.php"];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:url];
[request setHTTPMethod:@"POST"];
[request setValue:postLength forHTTPHeaderField:@"Content-Length"];
[request setValue:@"application/json; charset=utf-8" forHTTPHeaderField:@"Content-Type"];
[request setHTTPBody:jsonData];
NSURLSession *session = [NSURLSession sessionWithConfiguration:[NSURLSessionConfiguration defaultSessionConfiguration]];
NSURLSessionDataTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {
if (!error) {
id jsonDict = [NSJSONSerialization JSONObjectWithData:data options:0 error:&error];
NSLog(@"jsonDict = %@", jsonDict);
if (!error) {
}
else {
}
}
else {
}
}];
[task resume];
Upvotes: 1
Reputation: 1355
Your array is correct just convert to json string
Here is func for that
public func jsonString(prettify: Bool = false) -> String? {
guard JSONSerialization.isValidJSONObject(self) else {
return nil
}
Use it this way
self.arrOrderCart.jsonString()
Upvotes: 0
Reputation: 8351
You have to pass directly NSData to HttpBody like below :
NSDictionary *headers = @{ @"content-type": @"application/json",
@"cache-control": @"no-cache"
};
NSData *jsonData = [NSJSONSerialization dataWithJSONObject:tvarns
options:NSJSONWritingPrettyPrinted error:&error];
NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:@"http://test.kre8tives.com/barebon/add_cartapi.php"]
cachePolicy:NSURLRequestUseProtocolCachePolicy
timeoutInterval:10.0];
[request setHTTPMethod:@"POST"];
[request setAllHTTPHeaderFields:headers];
[request setHTTPBody:postData];
NSURLSession *session = [NSURLSession sharedSession];
NSURLSessionDataTask *dataTask = [session dataTaskWithRequest:request
completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
if (error) {
NSLog(@"%@", error);
} else {
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *) response;
NSLog(@"%@", httpResponse);
}
}];
[dataTask resume];
Hope this will helps to get your data request success!
Upvotes: 0
Reputation: 539
Try below code
NSMutableDictionary *parametersDictionary = [[NSMutableDictionary alloc]init];
[parametersDictionary setValue:@"114" forKey:@"customer_id"];
[parametersDictionary setValue:@"14" forKey:@"item_id"];
[parametersDictionary setValue:@"591d3822f55e2270202d8ff1" forKey:@"_id"];
[parametersDictionary setValue:@"Bira White" forKey:@"item_name"];
[parametersDictionary setValue:@"2" forKey:@"item_quantity"];
[parametersDictionary setValue:@"180.0" forKey:@"price"];
[parametersDictionary setValue:@"table21" forKey:@"qr_code"];
[parametersDictionary setValue:@"7008841769" forKey:@"phone"];
[parametersDictionary setValue:@"Samanthaa" forKey:@"customer_name"];
NSMutableDictionary *requestParametersDic=[[NSMutableDictionary alloc] initWithObjectsAndKeys:parametersDictionary,@"order_cart", nil];
NSData * postData=[NSJSONSerialization dataWithJSONObject:requestParametersDic options:NSJSONWritingPrettyPrinted error:nil];
NSString *postLength = [NSString stringWithFormat:@"%lu",(unsigned long)[postData length]];
NSMutableURLRequest *request = [[NSMutableURLRequest alloc] init];
[request setURL:[NSURL URLWithString:[NSString stringWithFormat:@"%@%@",KWebservicesBaseURL,kiPestConfirmOrder]]];
[request setHTTPMethod:@"POST"];
[request setValue:postLength forHTTPHeaderField:@"Content-Length"];
[request setHTTPBody:postData];
NSURLSessionConfiguration *configuration = [NSURLSessionConfiguration defaultSessionConfiguration];
NSURLSession *session = [NSURLSession sessionWithConfiguration:configuration delegate:nil delegateQueue:nil];
NSURLSessionDataTask *postDataTask = [session dataTaskWithRequest:request completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *) response;
NSString *responseString=[[NSString alloc]init];
if(data!=nil && httpResponse.statusCode==200)
{
responseString=[[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
// NSLog(@"i deliver add order reponse str %@",responseString);
}
else
{
}
}];
[postDataTask resume];
Upvotes: 0