I have some code to send a url to a remote server. If I do not encode the url, it works perfectly. But if I encode the url, it does not work. So I am pretty sure something is not right with the way I encode the url query string.
Here is my code:
// URL TO BE SUBMITTED.
NSString *urlString =
#"http://www.mydomain.com/test.php?";
// NOW CREATE URL QUERY STRING
NSString *unencoded_query_string =
#"name=%#&user_id=%#&person_name=%#&person_email=%#&privacy=%#";
// PUT PREVIOUSLY SET VALUES INTO THE QUERY STRING
NSString *unencoded_url_with_params =
[NSString stringWithFormat:unencoded_query_string, business , user_id , name , email , privacy_string];
// ENCODE THE QUERY STRING
NSString *escapedString = (__bridge_transfer NSString *)CFURLCreateStringByAddingPercentEscapes(
NULL,
(__bridge CFStringRef)unencoded_url_with_params,
NULL,
(CFStringRef)#"!*'();:#&=+$,/?%#[]",
kCFStringEncodingUTF8);
// NOW APPEND URL TO QUERY STRING
NSString *full_encoded_url_string =
[urlString stringByAppendingString: escapedString];
and then I send this string to the server, and the server does have the correct request file invoked, but isn't able to read the parameters.
Would anyone know what I doing incorrectly here? I am using arc by the way.
Thanks!
I think you probably want to escape each param, not the entire request. Basically you want to escape ampersands, spaces etc that show up in your get variables. Your encoded URL probably looks like this:
http://www.mydomain.com/test.php?name%3DPeter%20Willsey%26user_id%3DUSERID%26person_name%3DPeter%20Willsey%26person_email%3Dpeter%40test.com%26privacy%3D1
and it should look like this:
http://www.mydomain.com/test.php?name=Peter%20Willsey&user_id=25&person_name=Peter%20Willsey&person_email=peter%40test.com&privacy=1
Related
I am trying to submit a request using NSURL to the following:
http://api.allsaints.com/v1/product/?category=Women's Knitwear
when putting this URL in a browser with the ' and the space int the category, the browser (chrome) is modifying the request to:
http://api.allsaints.com/v1/product/?category=Women%27s%20Knitwear which works.
However, I can not get the right encoding to work as part of a NSURL and NSDATA request on iOS. I tried various encoding using stringByAddingPercentEscapesUsingEncoding to normalise the URL but it keep on failing.
Can someone point me in the right direction to an encoding that not only swaps the space to a %20 but also swaps the ' to a %27?
Refer to NSString stringByAddingPercentEscapesUsingEncoding: you should use CFURLCreateStringByAddingPercentEscapes to custom which character you want to escape.
- (NSString *) urlencodeStr:(NSString *)str
{
return (NSString *)CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes(
NULL,
(__bridge CFStringRef) str,
NULL,
CFSTR("!*'();:#+$,/?%#[]"),
kCFStringEncodingUTF8));
}
CFSTR("!*'();:#+$,/?%#[]") contains the characters will be escaped.
I am having a link that i want to post the data.
I am using url encoding like,
http://admin:testsite#www.arabcircleonline.com/index.php?%#=%#",form_urlencode_rfc3986(#"do"),form_urlencode_rfc3986(#"/webservice/whisper/login_chauhankevalp#gmail.com/password_keval/action_whisper/whisperdata_{\"user_status\":\"last123\",\"privacy\":0,\"privacy_comment\":0}
This is giving the response intended when a record should be added, but the record is not getting added, when i execute this link on browser, it works fine.
Please help me out of this.. i am working on this last 2 days with no solution
form_urlencode_rfc3986 method i am using is,
NSString* form_urlencode_rfc3986(NSString* s) {
CFStringRef charactersToLeaveUnescaped = CFSTR(" ");
CFStringRef legalURLCharactersToBeEscaped = CFSTR("/%&=?$#+-~#<>|\\*,.()[]{}^!");
NSString *result = CFBridgingRelease(CFURLCreateStringByAddingPercentEscapes( kCFAllocatorDefault,(__bridge CFStringRef)s,charactersToLeaveUnescaped,legalURLCharactersToBeEscaped, kCFStringEncodingUTF8));
return [result stringByReplacingOccurrencesOfString:#" " withString:#"+"];
}
You are probably trying to do this:
You have a url with a query. The query component is separated by a "?" as illustrated below:
URL := scheme-authority-path "?" query
In your case "scheme-authority-path" is
http://admin:testsite#www.arabcircleonline.com/index.php,
and a "query" is a list of parameters, separated by a "&".
Your URL string without query (scheme, authority and path):
NSString* urlString = #"http://admin:testsite#www.arabcircleonline.com/index.php";
Compose a parameter (which is part of the query), e.g. in BNF
parameter := name "=" value
NOTE: name and value need to be encoded with the helper function.
which corresponds in code:
NSString* parameterString = [NSString stringWithFormat:#"%#=%#",
form_urlencode_rfc3986(#"do"),
form_urlencode_rfc3986(
#"/webservice/whisper/login_chauhankevalp#gmail.com/password_keval/action_whisper/whisperdata_{\"user_status\":\"last123\",\"privacy\":0,\"privacy_comment\":0")
];
A query string is composed by concatenating (encoded) parameters and separating them by a "&", e.g. in BNF:
query := parameter ["&" parameter]
You have only one parameter, thus our query string becomes just the parameter string:
NSString* queryString = parameterString;
Now, compose the complete url string (including the query) from the former urlString (scheme, authority and path) and the query, by concatenating urlString, a "?" and the query. For example:
NSString* urlStringWithQuery = [NSString stringWithFormat:#"%#?%#", urlString, queryString];
I need to form a POST NSURLRequest and I need to pass into the request this structure:
inspection (an array of NSDictionaries with string keys and values)
property (same structure as array1)
subcategories (an array of NSDictionaries where each dictionary can have an array of values for a certain key)
Here is how my requestString looks like after I concat everything:
?inspection[name]=inspection_name&inspection[address]=address_value&...&property[type]=property_type&....&subcategories[0][questions][0][title]=title_value&subcategories[0][questions][1][title]=title_value1&...&subcategories[1][questions][0][title]=title_valuen&...
For inspection and property array I've also tried inspection[][name]=inspection_name, property[][address]=property_address
While I'm forming that requestString I'm escaping each parameter using this method:
static NSString *escapeParam(NSString *param) {
param = [param stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
param = [param stringByReplacingOccurrencesOfString:#"&" withString:#"%26"];
param = [param stringByReplacingOccurrencesOfString:#"=" withString:#"%3D"];
param = [param stringByReplacingOccurrencesOfString:#"?" withString:#"%3F"];
return param;
}
There fore something like subcategories[0][questions][0][title]=title_value becomes subcategories%5B0%5D%5Bquestions%5D%5B0%5D%5Btitle%5D=title_value
Obviously I'm doing something wrong and don't know how to properly form this requestString because when I fire the request I get HTTP Error 400 Bad request in response.
Can someone point me in the right direction?
Thanks a bunch!
First of all &,=,? don't need to be encoded, these chars are supported.
Second of all, you don't need to add stringByAddingPercentEscapesUsingEncoding to the whole body, I think you don't need to add it at all because the server should support escaping chars. If the server doesn't support escaping chars, you should apply the stringByAddingPercentEscapesUsingEncoding only on the values, the keys should be as tehy are, something like
inspection[][name]=[inspection_name stringByAddingPercentEscapesUsingEncoding: NSUTF8StringEncoding];
This will handle eventual escaping chars from your values, but the keys should't have escaping characters since they are created to work on the server.
I have following strings. But I need to separate them by this "jsonp1343930692" and assign them NSString again. How could I that? I could able to separate them to NSArray but I don't know how to separate to NSString.
jsonp1343930692("snapshot":[{"timestamp":1349143800,"data":[{"label_id":10,"lat":29.7161,"lng":-95.3906,"attr":{"ozone_level":37,"exp":"IN","gridpoint":"29.72:-95.39"}},{"label_id":10,"lat":30.168456,"lng":-95.50448}]}]})
jsonp1343930692("snapshot":[{"timestamp":1349144700,"data":[{"label_id":10,"lat":29.7161,"lng":-95.3906,"attr":{"ozone_level":37,"exp":"IN","gridpoint":"29.72:-95.39"}},{"label_id":10,"lat":30.168456,"lng":-95.50448,"attr":{"ozone_level":57,"exp":"IN","gridpoint":"30.17:-95.5"}},{"label_id":10,"lat":29.036944,"lng":-95.438333}]}]})
The jsonp1343930692 prefix in your string is odd: I don't know where you string come from, but it really seems to be some JSON string with this strange prefix that has no reason to be there. The best shot here is probably to check if it is normal to have this prefix, for example if you get this string from a WebService it is probably the WebService fault to return this odd prefix.
Anyway, if you want to remove the jsonp1343930692 prefix of your string, you have multiple options:
Check that the prefix is existant, and if so, remove the right number of characters from the original string:
NSString* str = ... // your string with the "jsonp1343930692" prefix
static NSString* kStringToRemove = #"jsonp1343930692";
if ([str hasPrefix:kStringToRemove])
{
// rebuilt a string by only using the substring after the prefix
str = [str substringFromIndex:kStringToRemove.length];
}
Split your string in multiple parts, using the jsonp1343930692 string as a separator
NSString* str = ... // your string with the "jsonp1343930692" prefix
static NSString* kStringToRemove = #"jsonp1343930692";
NSArray* parts = [str componentsSeparatedByString:kStringToRemove];
str = [parts componentsJoinedByString:#""];
Replace every occurrences of jsonp1343930692 by the empty string.
NSString* str = ... // your string with the "jsonp1343930692" prefix
static NSString* kStringToRemove = #"jsonp1343930692";
str = [str stringByReplacingOccurrencesOfString:kStringToRemove withString:#""];
So in short you have many possibilities depending on what exactly you want to do :)
Of course, once you have removed your strange jsonp1343930692 prefix, you can deserialize your JSON string to obtain a JSON object (either using some third-party lib like SBJSON or using NSJSONSerializer on iOS5 and later, etc)
Have a look at the NSJSONSerialization class to turn this into a Cocoa collection that you can deal with.
I'm unable to open a URL into UIWebView so I've seached & found that I need to encode URL, so I tried to encode it but, I've facing problem in URL encoding : My URL is http://somedomain.com/data/Témp%20Page%20-%20Open.html (It's not real URL).
I'm concerned with %20 that I tried to replace using stringByReplacingOccuranceOfString:#"" withString:#"" , it give me the URL I wanted like http://somedomain.com/data/Témp Page - Open.html However its not opening in UIWebView but amazingly it opens in Safari & FireFox perfect. Even I open unencoded URL its automatically converts and open the page I'm looking for.
I've google for URL encoding & it points me to different results I already checked but no results help me out!! I tried different functions answers in different URL encoding question but it just changed all special characters and make my URL like, http%3A%2F%2Fsomedomain.com%2Fdata%2FT... which can't open in UIWebView and even in any browser.
It gives the following Error Log in UIWebView delegate
- (void)webView:(UIWebView *)webView didFailLoadWithError:(NSError *)error { }
Error Code : 101
& Description : Error Domain=WebKitErrorDomain Code=101 "The operation couldn’t be completed. (WebKitErrorDomain error 101.)" UserInfo=0x6e4cf60 {}
The answer #Dhaval Vaishnani provided is only partially correct. This method treats the ?, = and & characters as not to be encoded, since they're valid in an URL. Thus, to encode an arbitrary string to be safely used as a part of an URL, you can't use this method. Instead you have to fall back to using CoreFoundation and CFURLRef:
NSString *unsafeString = #"this &string= confuses ? the InTeRwEbZ";
CFStringRef safeString = CFURLCreateStringByAddingPercentEscapes (
NULL,
(CFStringRef)unsafeString,
NULL,
CFSTR("/%&=?$#+-~#<>|\\*,.()[]{}^!"),
kCFStringEncodingUTF8
);
Don't forget to dispose of the ownership of the resulting string using CFRelease(safeString);.
Also, it seems that despite the title, OP is looking for decoding and not encoding a string. CFURLRef has another, similar function call to be used for that:
NSString *escapedString = #"%32%65BCDEFGH";
CFStringRef unescapedString = CFURLCreateStringByReplacingPercentEscapesUsingEncoding (
NULL,
(CFStringRef)escapedString,
CFSTR(""),
kCFStringEncodingUTF8
);
Again, don't forget proper memory management.
I did some tests and I think the problem is not really with the UIWebView but instead that NSURL won't accept the URL because of the é in "Témp" is not encoded properly. This will cause +[NSURLRequest requestWithURL:] and -[NSURL URLWithString:] to return nil as the string contains a malformed URL. I guess that you then end up using a nil request with -[UIViewWeb loadRequest:] which is no good.
Example:
NSLog(#"URL with é: %#", [NSURL URLWithString:#"http://host/Témp"]);
NSLog(#"URL with encoded é: %#", [NSURL URLWithString:#"http://host/T%C3%A9mp"]);
Output:
2012-10-02 12:02:56.366 test[73164:c07] URL with é: (null)
2012-10-02 12:02:56.368 test[73164:c07] URL with encoded é: http://host/T%C3%A9mp
If you really really want to borrow the graceful handling of malformed URLs that WebKit has and don't want to implement it yourself you can do something like this but it is very ugly:
UIWebView *webView = [[[UIWebView alloc]
initWithFrame:self.view.frame]
autorelease];
NSString *url = #"http://www.httpdump.com/texis/browserinfo/Témp.html";
[webView loadHTMLString:[NSString stringWithFormat:
#"<script>window.location=%#;</script>",
[[[NSString alloc]
initWithData:[NSJSONSerialization
dataWithJSONObject:url
options:NSJSONReadingAllowFragments
error:NULL]
encoding:NSUTF8StringEncoding]
autorelease]]
baseURL:nil];
The most straightforward way is to use:
NSString *encodedString = [rawString stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];
iDhaval was close, but he was doing it the other way around (decoding instead of encoding).
Anand's way would work, but you'll most likely have to replace more characters than spaces and new lines. See the reference here:
http://en.wikipedia.org/wiki/Percent-encoding#Percent-encoding_reserved_characters
Hope that helps.
It's very simple to encode the URL in iPhone. It is as following
NSString* strURL = #"http://somedomain.com/data/Témp Page - Open.html";
NSURL* url = [NSURL URLWithString:[strURL stringByReplacingPercentEscapesUsingEncoding:NSUTF8StringEncoding]];
It's a perfect way to encode the URL, I am using it and it's perfectly work with me.
Hope it will help you!!!
This may useful to someone who's reach to this question for URL encoding, as my question likely different which has been solved and accepted, this is the way I used to do encoding,
-(NSString *)encodeURL:(NSString *)urlString
{
CFStringRef newString = CFURLCreateStringByAddingPercentEscapes(kCFAllocatorDefault, (CFStringRef)urlString, NULL, CFSTR("!*'();:#&=+#,/?#[]"), kCFStringEncodingUTF8);
return (NSString *)CFBridgingRelease(newString);
}
You can try this
NSString *url = #"http://www.abc.com/param=Hi how are you";
NSString* encodedUrl = [url stringByAddingPercentEscapesUsingEncoding:
NSASCIIStringEncoding];
I think this will work for you
[strUrl stringByAddingPercentEncodingWithAllowedCharacters:NSCharacterSet.URLQueryAllowedCharacterSet]
the Native method for URL Encoding.
Swift 4.x
let originalString = "https://www.somedomain.com/folder/some cool file.jpg"
let escapedString = originalString.addingPercentEncoding(withAllowedCharacters: .urlQueryAllowed)
print(escapedString!)
You probably need to break the URL down into it's constituent parts and then URL encode the host and path but not the scheme. Then put it back together again.
Create an NSURL with the string and then use the methods on it such as host, scheme, path, query, etc to pull it apart. Then use CFURLCreateStringByAddingPercentEscapes to encode the parts and then you can put them back together again into a new NSURL.
can you please Try this out.
//yourURL contains your Encoded URL
yourURL = [yourURL stringByReplacingOccurrencesOfString:#" " withString:#"%20"];
yourURL = [yourURL stringByReplacingOccurrencesOfString:#"\n" withString:#""];
NSLog(#"Keyword:%# is this",yourURL);
I am not sure,but I have solved using this in my case.
Hope this will solve yours.