How to print NSMutableURLRequest? - iphone

How to print NSMutableURLRequest using NSLog ?

.allHTTPHeaderFields returns a dictionary with the header content:
NSLog(#"%#", [request allHTTPHeaderFields]);
// {
// "Accept-Language" = "en;q=1";
// "Content-Length" = 190706;
// "Content-Type" = "multipart/form-data; boundary=Boundary+D90A259975186725";
// "User-Agent" = "...";
// }
Or for specific field:
NSString *field = #"Content-Type";
NSLog(#"%#",[request valueForHTTPHeaderField:field]);
// multipart/form-data; boundary=Boundary+D90A259975186725

Did you try with
NSLog(#" %#", myMutableURLRequest);

Related

Proper Encoding for chines character from NSData

Please help me i'm using below code to get file name.
Here i'm getting NSString from NSData where multipartData is NSMutableArray which contain NSData.
NSString* postInfo = [[NSString alloc] initWithBytes:[[multipartData objectAtIndex:1] bytes] length:[[multipartData objectAtIndex:1] length] encoding:NSUTF8StringEncoding];
I'm getting string like:
Printing description of postInfo:
Content-Disposition: form-data; name="file"; filename="??:??.PNG"
But It should be like:
Printing description of postInfo:
Content-Disposition: form-data; name="file"; filename="华语/華語.PNG"
Thanks in advance.
Obviously the server doesn't encode the response using UTF-8, but probably another Chinese-only encoding. You need to use the Content-Type header to detect which encoding it is, and then find the appropriate NSStringEncoding using the following code;
// set charset to the MIME charset you get from the server
CFStringConvertEncodingToNSStringEncoding(CFStringConvertIANACharSetNameToEncoding((__bridge CFStringRef)(charset)));
Here is a detailed answer:
// getting the Content-Type header (e.g. "application/json; charset=utf-8")
NSString* header = [[response allHeaderFields] objectForKey:#"Content-Type"];
// getting the MIME type
NSString* charset = nil;
NSArray* contentTypeParts = [header componentsSeparatedByString:#";"];
NSInteger i = 0;
for (NSString* part in contentTypeParts) {
// ignoring first loop (e.g. "application/json")
if (i > 0) {
NSArray* partComponents = [part componentsSeparatedByString:#"="];
if ([partComponents count] == 2 && [#"charset" isEqualToString:[[partComponents objectAtIndex:0] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]]]) {
charset = [[partComponents objectAtIndex:1] stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]];
break;
}
}
i++;
}
// converting the MIME type to NSStringEncoding
NSStringEncoding stringEncoding = NSUTF8StringEncoding; // default to UTF8
if (charset) {
stringEncoding = CFStringConvertEncodingToNSStringEncoding(CFStringConvertIANACharSetNameToEncoding((__bridge CFStringRef)(charset)));
}
// finally you can convert your string properly!
NSString* postInfo = [[NSString alloc] initWithBytes:[[multipartData objectAtIndex:1] bytes] length:[[multipartData objectAtIndex:1] length] encoding:stringEncoding];

Twitter search for hashtag

I'm trying to parse tweets using Twitter Framework, so I write the following code and it's working fine, but it's not Synchronous.
Now I'm trying to get all the tweets from #iOS.
I have used the following code to get the search result for iOS hashtag:
-(void)fetchResults
{
// Do a simple search, using the Twitter API
TWRequest *request = [[TWRequest alloc] initWithURL:[NSURL URLWithString:
#"http://search.twitter.com/search.json?q=iOS%20&rpp=20&with_twitter_user_id=true&result_type=recent"]
parameters:nil requestMethod:TWRequestMethodGET];
// Notice this is a block, it is the handler to process the response
[request performRequestWithHandler:^(NSData *responseData, NSHTTPURLResponse *urlResponse, NSError *error)
{
if ([urlResponse statusCode] == 200)
{
// The response from Twitter is in JSON format
// Move the response into a dictionary and print
NSError *error;
dict = [NSJSONSerialization JSONObjectWithData:responseData options:0 error:&error];
NSLog(#"Twitter response: %#", [dict description]);
[self filterTweets];
}
else
NSLog(#"Twitter error, HTTP response: %i", [urlResponse statusCode]);
}];
}
As a result I got this:
Twitter response: {
"completed_in" = "0.007";
"max_id" = 333837474914766848;
"max_id_str" = 333837474914766848;
page = 1;
query = quranRadios;
"refresh_url" = "?since_id=333837474914766848&q=quranRadios&result_type=recent";
results = (
{
"created_at" = "Mon, 13 May 2013 06:53:51 +0000";
"from_user" = YousefMutawe;
"from_user_id" = 324385406;
"from_user_id_str" = 324385406;
"from_user_name" = "Yousef N Mutawe \Uf8ff";
geo = "<null>";
id = 333837474914766848;
"id_str" = 333837474914766848;
"iso_language_code" = pt;
metadata = {
"result_type" = recent;
};
"profile_image_url" = "http://a0.twimg.com/profile_images/1533729607/20090719526_normal.jpg";
"profile_image_url_https" = "https://si0.twimg.com/profile_images/1533729607/20090719526_normal.jpg";
source = "<a href="http://twitter.com/download/iphone">Twitter for iPhone</a>";
text = "Testing #quranRadios #Mkalatrash";
},
{
"created_at" = "Sun, 12 May 2013 13:09:43 +0000";
"from_user" = YousefMutawe;
"from_user_id" = 324385406;
"from_user_id_str" = 324385406;
"from_user_name" = "Yousef N Mutawe \Uf8ff";
geo = "<null>";
id = 333569679484416000;
"id_str" = 333569679484416000;
"iso_language_code" = et;
metadata = {
"result_type" = recent;
};
"profile_image_url" = "http://a0.twimg.com/profile_images/1533729607/20090719526_normal.jpg";
"profile_image_url_https" = "https://si0.twimg.com/profile_images/1533729607/20090719526_normal.jpg";
source = "<a href="http://twitter.com/download/iphone">Twitter for iPhone</a>";
text = "#quranRadios :)";
}
);
"results_per_page" = 20;
"since_id" = 0;
"since_id_str" = 0;
}
So i use the following method to filter the result and to get the (Tweet,Username,and the User image):
-(void)filterTweets
{
NSArray *results = [dict objectForKey:#"results"];
//Loop through the results
int x =0;
for (NSDictionary *tweet in results)
{
// Get the tweet
NSString *twittext = [tweet objectForKey:#"text"];
NSString *twitPic = [tweet objectForKey:#"profile_image_url"];
NSString *userName = [tweet objectForKey:#"from_user"];
// Save the tweet to the twitterText array
[tweetsInfo addObject:(twittext)];
[tweetPics addObject:(twitPic)];
[imagesArray addObject:[UIImage imageWithData:[NSData dataWithContentsOfURL:[NSURL URLWithString:[tweetPics objectAtIndex:x]]]]];
[userNameTweet addObject:userName];
x++;
//NSLog(#"tweet ooooooo ======> %#",twitPic);
countMe++;
}
[tweetsTable reloadData];
}
I'm not sure if i'm doing the right thing,so what would you recommend me to do? and how can i make it synchronized?
am new to programming iOS, please advice.
Thanks.

Creating place on QuickBlox

I am using QuickBlox in my iOS app and trying to add data in Places table
QBLPlace *place = [QBLPlace place];
place.geoDataID = 34691;
place.photoID = 447;
place.title = [NSString stringWithFormat:#"%#",[aView.annotation title]];
place.address = #"London, Gadge st, 34";
place.placeDescription = #"My place description";
place.latitude = pinLocation.coordinate.latitude;
place.longitude = pinLocation.coordinate.longitude;
[QBLocation createPlace:place delegate:self];
but I am not able to add place. Below is the console log
RestRequest:
POST http://api.quickblox.com/places.xml
headers:{
"QB-SDK" = "iOS 1.3.1";
"Qb-Token" = c1191ff8ffbfdb79b11fba6bf2a4c054d2644de8;
"QuickBlox-REST-API-Version" = "0.1.1";
}
parameters:{
"place[address]" = "London, Gadge st, 34";
"place[description]" = "My place description";
"place[geo_data_id]" = 34691;
"place[photo_id]" = 447;
"place[title]" = "The Bridge Room";
}
raw body:place[address]=London%2C%20Gadge%20st%2C%2034&place[description]=My%20place%20description&place[geo_data_id]=34691&place[photo_id]=447&place[title]=The%20Bridge%20Room
2013-01-02 10:21:14.543 Chat.Points[10229:1d903] Query QBLPlaceCreateQuery DEALLOC
2013-01-02 10:21:14.551 Chat.Points[10229:1d903] Request finished, response:
RestResponse:
<QBASIHTTPRequest: 0xb40fc00>
headers:{
"Access-Control-Allow-Origin" = "*";
"Access-Control-Request-Method" = "*";
"Cache-Control" = "no-cache";
Connection = Close;
"Content-Length" = 116;
"Content-Type" = "application/xml; charset=utf-8";
Date = "Wed, 02 Jan 2013 04:51:14 GMT";
"QuickBlox-REST-API-Version" = "0.1.1";
Server = "nginx/1.0.15";
Status = "422 Unprocessable Entity";
"X-Rack-Cache" = "invalidate, pass";
"X-Request-Id" = 5ad6e7d628b4fbd931b7896058f012cd;
"X-Runtime" = "0.052140";
"X-UA-Compatible" = "IE=Edge,chrome=1";
}
body:<?xml version="1.0" encoding="UTF-8"?>
<errors type="array">
<error>No photo with such id found</error>
</errors>
The right way to create place is:
QBLPlace *place = [QBLPlace place];
place.geoDataID = 34691;
place.photoID = 447;
place.title = [NSString stringWithFormat:#"%#",[aView.annotation title]];
place.address = #"London, Gadge st, 34";
place.placeDescription = #"My place description";
[QBLocation createPlace:place delegate:self];
where:
geoDataID - ID of QBLGeoData object
photoID - ID of QBCBlob object
Your error says that you have to create file with photo and then connect it to place.
To upload file please use this code:
NSData *file = [NSData dataWithContentsOfFile:[[NSBundle mainBundle] pathForResource:#"Hotel47" ofType:#"png"]];
[QBContent TUploadFile:file fileName:#"Hotel47 Image" contentType:#"image/png" isPublic:YES delegate:self];
#pragma mark -
#pragma mark QBActionStatusDelegate
- (void)completedWithResult:(Result *)result{
// Upload file result
if(result.success && [result isKindOfClass:[QBCFileUploadTaskResult class]]){
// File uploaded, do something
QBCBlob *uploadedFile = ((QBCFileUploadTaskResult *)result).uploadedBlob;
NSUInteger photoID = uploadedFile.ID; // use this as photo IS for place
}else{
NSLog("errors=%#", result.errors);
}
}
To create GeoData please use next code:
QBLGeoData *geodata = [QBLGeoData geoData];
geodata.latitude = 23.2344;
geodata.longitude = -12.23523;
geodata.status = #"Hello, world";
[QBLocation createGeoData:geodata delegate:self];
#pragma mark -
#pragma mark QBActionStatusDelegate
- (void)completedWithResult:(Result *)result{
// Check-in result
if(result.success && [result isKindOfClass:QBLGeoDataResult.class]){
QBLGeoDataResult *checkinResult = (QBLGeoDataResult *)result;
NSUInteger geoDataID = checkinResult.geoData.ID; // your geo data ID
}else{
NSLog(#"errors=%#", result.errors);
}
}

AFNetwork and GoogleAPI returning NULL

After being very disappointed with CLGeocoder, I decided to use the GoogleMaps API instead.
I have designed the call as following, using AFNetwork :
AFHTTPClient *new = [[AFHTTPClient alloc] initWithBaseURL:[NSURL URLWithString:#"http://maps.googleapis.com/"]];
NSDictionary *dict = [[NSDictionary alloc] initWithObjects:[NSArray arrayWithObjects:#"thorsgade",#"true", nil] forKeys:[NSArray arrayWithObjects:#"address",#"sensor", nil]];
NSMutableURLRequest *req = [new requestWithMethod:#"GET" path:#"maps/api/geocode/json" parameters:dict];
AFJSONRequestOperation *call = [AFJSONRequestOperation JSONRequestOperationWithRequest:req success:^(NSURLRequest *request, NSHTTPURLResponse *response, id JSON) {
NSArray *geos = [JSON objectForKey:#"results"];
DLog(#"Got result : '%#' %# from %# %# %#",JSON,geos,[NSHTTPURLResponse localizedStringForStatusCode:response.statusCode],response.allHeaderFields,request.URL.description);
} failure:^(NSURLRequest *request, NSHTTPURLResponse *response, NSError *error, id JSON) {
DLog(#"Failed %# %#",error.localizedDescription,request.URL.description);
}];
[call start];
I get this feedback:
Got result : '(null)' (null) from no error {
"Cache-Control" = "public, max-age=86400";
"Content-Encoding" = gzip;
"Content-Length" = 1603;
"Content-Type" = "application/json; charset=UTF-8";
Date = "Fri, 07 Dec 2012 08:51:58 GMT";
Expires = "Sat, 08 Dec 2012 08:51:58 GMT";
Server = mafe;
Vary = "Accept-Language";
"X-Frame-Options" = SAMEORIGIN;
"X-XSS-Protection" = "1; mode=block"; } http://maps.googleapis.com/maps/api/geocode/json?sensor=true&address=thorsgade
Null result, but no errors. The content is recognized in the headers as JSON, but the raw JSON is null.
The annoying thing is that if I open http://maps.googleapis.com/maps/api/geocode/json?sensor=true&address=thorsgade in a browser, i get plenty of results.
So far i have tried:
Flicking the sensor booleon true/false.
Faking the user-agent to be regular safari.
Use POST instead of GET.
With no luck...
If the problem persists, I would recommend using MKNetworkKit instead
Here is my solution -
GoogleGeocodeApi.h
//GoogleGeocodeApi.h
#import <Foundation/Foundation.h>
#import "MKNetworkEngine.h"
typedef void (^JsonResponseBlock)(NSDictionary *);
typedef void (^ErrorBlock)(NSError* error);
#interface GoogleGeocodeApi : MKNetworkEngine
-(MKNetworkOperation*) geocodeWithAddress: (NSString *) address
onCompletion:(JsonResponseBlock) completionBlock
onError:(ErrorBlock) errorBlock;
#end
GoogleGeocodeApi.m
//GoogleGeocodeApi.m
#import "GoogleGeocodeApi.h"
#implementation GoogleGeocodeApi
-(id)init
{
if (self = [super initWithHostName:#"maps.googleapis.com" apiPath:#"maps/api/geocode" customHeaderFields:nil]) {
}
return self;
}
-(MKNetworkOperation*) geocodeWithAddress: (NSString *) address
onCompletion:(JsonResponseBlock) completionBlock
onError:(ErrorBlock) errorBlock;
{
MKNetworkOperation *op = [self operationWithPath:[NSString stringWithFormat:#"json?sensor=true&address=%#", address] params:nil httpMethod:#"GET"];
[op onCompletion:^(MKNetworkOperation *completedOperation) {
NSDictionary *responseJSON = [completedOperation responseJSON];
if (responseJSON && [[responseJSON objectForKey:#"status"] isEqualToString:#"OK"]) {
completionBlock(responseJSON);
} else {
NSDictionary* errorDictionary = #{NSLocalizedDescriptionKey :#"Google geocode failed!"};
NSError *error = [NSError errorWithDomain:#"Failed response" code:100 userInfo:errorDictionary];
errorBlock(error);
}
} onError:^(NSError* error) {
errorBlock(error);
}];
[self enqueueOperation:op];
return op;
}
Somewhere in code
GoogleGeocodeApi *gma = [[GoogleGeocodeApi alloc] init];
[gma geocodeWithAddress:#"thorsgade"
onCompletion:^(NSDictionary *responseJSON) {
NSLog(#"Geocode succeeded: %#", responseJSON);
} onError:^(NSError *error) {
NSLog(#"Geocode failed with error: %#", [error localizedDescription]);
}];

HTTP status code = 0 (iPhone) (objective c)

I want to ask about the iPhone application objective C problem.
I wrote a program to store the cookies and pass to another URL to retrieve the cookies.
However, I found that one of the return status code is 0. The content of the html is empty.
Can any one help me?
The following is my code.
// create a new mutable url
NSMutableURLRequest *request_get2 = [[[NSMutableURLRequest alloc] init] autorelease];
[request_get2 setURL:[NSURL URLWithString:#"http://www.example.com"]];
[request_get2 setHTTPMethod:#"GET"];
[request_get2 setValue:#"text/html; charset=UTF-8" forHTTPHeaderField:#"Content-Type"];
[request_get2 setValue:#"http://www.example.com" forHTTPHeaderField:#"Referer"];
[request_get2 setHTTPShouldHandleCookies:YES];
// cookiesString is a string, the format is "cookieName=cookieValue;"
[request_get2 setValue: (NSString *) cookiesString forHTTPHeaderField:#"Cookie"];
// doGet - response
NSHTTPURLResponse *response_get2 = nil;
NSError *error_get2 = nil;
NSData *responseData_get2 = [NSURLConnection sendSynchronousRequest:request_get2 returningResponse:&response_get2 error:&error_get2];
NSString *data_get2 = [[NSString alloc]initWithData:responseData_get2 encoding:NSUTF8StringEncoding];
NSString *responseURL_get2 = [[response_get2 URL] absoluteString]; // null value
NSString *responseTextEncodingName_get2 = [response_get2 textEncodingName]; // null value
NSString *responseMIMEType_get2 = [response_get2 MIMEType]; // null value
NSUInteger *responseStatusCode_get2 = [response_get2 statusCode]; //[responseStatusCode intValue]; // the status code is 0
Thank you very much
If you get a 0 for a response code, the response response_get2 probably was never initialized, which might point to a problem with the request unrelated to your web server.
You set error_get2, so check its value after the request is placed:
if (!error_get2) {
NSString *responseURL_get2 = [[response_get2 URL] absoluteString]; // null value
NSString *responseTextEncodingName_get2 = [response_get2 textEncodingName]; // null value
NSString *responseMIMEType_get2 = [response_get2 MIMEType]; // null value
NSUInteger *responseStatusCode_get2 = [response_get2 statusCode]; //[responseStatusCode intValue]; // the status code is 0
}
else {
NSLog(#"something went wrong: %#", [error_get2 userInfo]);
}