base64EncodedString returns undesired backslashes [duplicate] - ios

This question already has an answer here:
Alamofire 5 Escaping Forward Slashes
(1 answer)
Closed 4 years ago.
I am encoding a JPEG image to Base64 for sending to my app's backend using Alamofire.
When I inspect the sent string using Charles Proxy I find out that the encoded string escapes all slashes (/) with a backslash (becoming \/). For example, the string data:image/jpeg;base64, at the beginning becomes:
data:image\/jpeg;base64,
As all slashes in the Base64 encoded string, which renders the encoded string unusable.
Here is the code I use for encoding the image. The variable imageBase64 receives the string with the escaped slashes.
if let image = image {
let croppedImage = image.af_imageAspectScaled(toFill: CGSize(width: 500, height: 500))
if let imageData = UIImageJPEGRepresentation(croppedImage, 0.8) {
let imageBase64 = "data:image/jpeg;base64,\(imageData.base64EncodedString())"
base64dict["base64"] = imageBase64 as AnyObject
bodyParams["AVATAR"] = base64dict as AnyObject
} else {
base64dict["base64"] = "null" as AnyObject
bodyParams["AVATAR"] = base64dict as AnyObject
}
}
When I send the imageData string to the backend using Alamofire, the json sent in the request body becomes like this:
{
"AVATAR": {
"base64": "data:image\/jpeg;base64,\/9j\/4AAQSkZJRgABAQAAkACQAAD\/4QC..."
}
}
where all slashes were escaped.
The code I use for making the request is the following:
Alamofire.request(finalURL,
method: method,
parameters: bodyParams,
encoding: JSONEncoding.default,
headers: ["Content-Type": "application/json"])
.responseJSON { response in
// process response
}

I ended using the custom JSONEncoder posted by csim at this answer: Alamofire 5 Escaping Forward Slashes.
I had to create a new class, using the code provided by csim, and then the Alamofire request became:
Alamofire.request(finalURL,
method: method,
parameters: bodyParams,
encoding: JSONEncodingWithoutEscapingSlashes.default,
headers: ["Content-Type": "application/json"])
.responseJSON { response in
// process response
}

Related

Alamofire GET request with åäö (special characters), invalid url

I'm trying to send an API get request with alamofire, but when i use the following url: https://stuntmans.evosale.se/admin/api/dräkt , the special character in "dräkt" is returning an invalid url as response. How would i go about using special characters with alamofire?
Thanks in advance!
Here is a part of the code:
let headers: HTTPHeaders = [
.authorization(username: "Username", password: "Password"),
.accept("application/json")]
AF.request(https://stuntmans.evosale.se/admin/api/dräkt, headers: headers).validate().responseJSON { response in
You could percent encode the URL with URLComponents
var components = URLComponents(string: "https://stuntmans.evosale.se")!
components.path = "/admin/api/dräkt"
guard let url = components.url else { return }
AF.request(url, headers: headers).validate().responseJSON { response in
Solved this by replacing the characters "åäö" with the corresponding characters they're supposed to represent in url, below is the code:
var result = Url
zip(["å", "ä", "ö"],["%C3%A5", "%C3%A4", "%C3%B6"]).forEach {
result = result.replacingOccurrences(of: $0, with: $1, options: .literal)
}
print (result) // the result

-1103 Error Domain=NSURLErrorDomain Code=-1103 "resource exceeds maximum size" iOS 13

We are facing the following networking error when the response is somehow large(14kb) on iOS 13.
[-1103] Error Domain=NSURLErrorDomain Code=-1103 "resource exceeds maximum size"
As we are using Alamofire, this problem is treated as error result which breaks our treatments of the results.
The strange thing is that if we use NSURLSession directly, though this error is still seen from logging, we don't actually receive it in the callback of
session.dataTask(with: request) { value, response, error in ... }
So the result can treated correctly.
This problem is never seen before. Anyone has got some idea on that ?
With the help of the Slack community, we find the answer is that
on iOS13, it is not allowed to add a body in GET request. To make it work again, we can either switch to a POST/PUT request or add body value via url parameters of the GET request.
Pass query parameters in GET request like the following:
let parameters: Parameters = [
"param": value
]
Alamofire.request(urlString, method: .get, parameters: parameters, encoding: URLEncoding.queryString)
I have face same issue and find out the solution.
You can't pass parameter in body while using GET.
Either use POST method if API support or pass it in URL like below.
AnyURL?Parameter=Value&Parameter=Value
Finally found the answer. For GET services I was trying to add an httpBody. Something like this:
do {
request.httpBody = try JSONSerialization.data(withJSONObject: parameters, options: .prettyPrinted)
} catch let error {
errorCompletion(error)
return
}
The solution was just to add an if to avoid that chunk of code if httpMethod is a GET. Seems like an iOS 13 new behavior and the error message given by Swift definitely not helps at all
Alamofire: You should try this!
Alamofire.request(urlString, method: .get, parameters: parameters, encoding: URLEncoding.queryString)
Just avoid the httpBody for the GET API request.
if requestType != .get{
request.httpBody = data
}
#OR
For GET request append parameter into URL instead of the HTTP body
Use the below extension to create a query parameter from the dictionary.
extension NSObject {
func buildQueryString(fromDictionary parameters: [String:String]) -> String {
var urlVars = [String]()
for (var k, var v) in parameters {
let characters = (CharacterSet.urlQueryAllowed as NSCharacterSet).mutableCopy() as! NSMutableCharacterSet
characters.removeCharacters(in: "&")
v = v.addingPercentEncoding(withAllowedCharacters: characters as CharacterSet)!
k = k.addingPercentEncoding(withAllowedCharacters: characters as CharacterSet)!
urlVars += [k + "=" + "\(v)"]
}
return (!urlVars.isEmpty ? "?" : "") + urlVars.joined(separator: "&")
}
}
I used default url encoding instead of default json encoding and it's worked for me.
Alamofire.request(url, method: .get, parameters: param, encoding: URLEncoding.default)
OR
If you using URLRequestConvertible
enum NetworkRouter: URLRequestConvertible {
case someCase(lang:String)
var method: HTTPMethod {
return .get
}
var parameters: Parameters? {
switch self {
case .someCase(let param):
return ["lang": param.lang]
default:
return nil
}
}
var url: URL {
switch self {
case .someCase(let param):
return URL(string: Constants.baseURL + Constants.endPoint)!
default:
return URL(string: Constants.baseURL)!
}
}
var encoding: ParameterEncoding {
return URLEncoding.default
}
func asURLRequest() throws -> URLRequest {
var urlRequest = URLRequest(url: url)
urlRequest.httpMethod = method.rawValue
return try encoding.encode(urlRequest, with: parameters)
}
}
I got that issue because i pass empty parameters in Alamofire when send get request. So, instead of sending empty parameters i simply replace it for nil.
My fix is I only set .parameters to nil, then everything works fine. Because in Swift it still initialize the value of .parameters.
self.request.parameters = nil
Here you might have missing the method of the URL request that you are passing to data task. You have to add POST/PUT/DELETE to the URL request method parameter like below.
var request: URLRequest = URLRequest(url: SOME_VALID_URL)
request.body = SOME_VALID_DATA_IN_BYTES
request.method = "post" --> You are missing this.
I only see this issue when I build with Xcode 11. If I revert back to Xcode 10.3 I do not have the same issue anymore. While not a forever fix, if you're needing to push out code you can revert until you have time to fix it.

Pass JSON object in GET request: iOS

I want to add the JSON object in GET request with URL. Please refer below URL.
https://testdata.com/xyz/&form={"id":"12", "data": "3"}
I am getting nil while converting String to URL
let serviceUrl = URL(string: url)
Thanks in advance.
I was already tried below solution but unfortunately no luck.
JSONSerialization.data
converting to string with utf8
removed whitespaces if any
addingPercentEncoding with URL host allowed
It's not recommended, to send a request body with GET request. GET request means to fetch all the resources/content that this URL has to offer. If they are parsing the GET body on server side, it's against the semantics. But if you really need to do it. Use Almofire. Here's a Sample Code.
let parameters : [String : Any] = [
"id":"12",
"data":"3"
]
func getContent(parameters: [String: Any]) {
Alamofire.request("http://18.218.235.193:3000/user/securedtoken", method:
.get, parameters: parameters, encoding: JSONEncoding.default)
.responseObject {(response:
DataResponse<YOUR RESPONSE MODEL HERE>) in
let response = response.result.value
//Do Something (Success)
}
}
I recommend you to use Alamofire library. You can do what you want using following code snippet
Alamofire.request(.GET, "http://httpbin.org/get", parameters: ["form": ["id": 12, "data": 3]])
.response { request, response, data, error in
print(request)
print(response)
print(error)
}

servlet request.parameter() function returns null when i post post request using swift 4 and alamofire4

I was trying to do a post request from ios swift4 using alamofire4.And my server side is a servelet file.
The Swift4 code is as follows
var datasDicts = [String: Any]()
datasDicts["phoneNumber"] = phoneNumber
datasDicts["tokenId"] = fcmDeviceToken
let parameters: Parameters = ["UploadData": datasDicts]
Alamofire.request(DDGeneralData.globalDatas.url+"/Sample", method: .post, parameters: Parameters, encoding:
JSONEncoding.default).responseJSON
{ (response:DataResponse) in
print("response result \(response.result)")
}
}
The request is successfully called the servlet but when i call request.getparameter(); it returns null. the servlet code is asfollows
String json_data = request.getParameter("UploadData");
System.out.println(config.getLogTime()+" DdbLogin json
parsed"+json_data);
how can i solve. when i read the request using request.reader i am able to get the string but request.getParameter() returns null

IOS Swift Alamofire JSON Request

I am trying to make a JSON Request with Alamofire but the response is in Greek and Swift returns:
Response
{
id = 4;
name = "\U0395\U03bb\U03b1\U03b9\U03cc\U03bb\U03b1\U03b4\U03bf"
url = "http://www.gaiaskarpos.com/app/images/categories/olive.png";
}
The problem is at name field.
//Swift Alamofire Request
Alamofire.request(.GET, "http://gaiaskarpos.com/applegetCategores.php",
encoding:.JSON).validate().responseJSON{(response)->
Void in print("Response Json : \(response.result.value)")
I had a same issue in Arabic/Persian chars and It's my solution:
json variable :
{
message = "\U062f\U0633\U062a\U06af\U0627\U0647 \U0645\U0639\U062a\U0628\U0631 \U0646\U06cc\U0633\U062a";
status = 0;
}
So I casted json to [String: AnyObject] :
var test = json as? [String : AnyObject]
print(test)
It's fixed. You should give it a try.
Why is your encoding .JSON? You send .GET-request and you don't need to specify the type of encoding in your request.
Alamofire documentation say:
Alamofire.request(.GET, "https://httpbin.org/get", parameters: ["foo": "bar"])
.responseJSON { response in
print(response.request) // original URL request
print(response.response) // URL response
print(response.data) // server data
print(response.result) // result of response serialization
if let JSON = response.result.value {
print("JSON: \(JSON)")
}
}
So use it. Links -> http://cocoadocs.org/docsets/Alamofire/1.1.3/ and https://github.com/Alamofire/Alamofire
You must specify the type of encoding when you pass parameters in the body of your request. It is for .POST and .PUT requests.
Try to print 'name' to Debug area. Maybe you'll get name in normal encoding... Xcode has the disadvantage: it shows not-UTF8 data in response like '\U0395\U03bb ... ... ... \U03b1\U03b9\' when there is some level of nested data in response.
Try to use NSUTF8StringEncoding with alamofire response
encoding: NSUTF8StringEncoding
Try to serialize the JSON with below code this might help you
let dict = NSJSONSerialization.JSONObjectWithData(jsonString.dataUsingEncoding(NSUTF8StringEncoding)!,
options: nil, error: nil) as [String : String]

Resources