How do I use JSON element with alamofire - json

I am using two textfields to pass login information to the PHP web service using Alamofire in the following way.
#IBAction func LoginButton(_ sender: Any) {
//getting the username and password
let parameters: Parameters=[
"Name":TextFieldUserName.text!,
"Pass":TextFieldPassword.text!
]
Alamofire.request(URL_USER_LOGIN, method: .post, parameters: parameters).responseJSON
{
response in
//printing response
print(response)
The following Json data is received on login.
[{"code":0,"message":"Check Username and Password....","userid":""}]
I want to use either "code" value (0 for false and 1 for true) or "message" value as String to put into an if - else statement for further steps. If Alamofire is not the best way to go about this, can someone please show another way. Thanks in advance for the help.

Do you need to deserialize the response from the server?
The easiest option is parsing response value as NSDictionary
if let JSON = response.result.value as? NSDictionary {
let code = JSON.value(forKey: "code") as? Int
let message = JSON.value(forKey: "message") as? String
}
You can also use the Codable protocol and the JSONDecoder to decode this response into your structure.
For example, declare struct:
struct LoginResponse: Codable {
var code: Int
var message: String
}
and decode response using JSONDecoder
let jsonDecoder = JSONDecoder()
let loginResponse = try? jsonDecoder.decode(LoginResponse.self, from: response.data)

Related

how to convert JSON dictionary to string value in swift 4

I'm new to Swift and I started working on a Swift 4 project with a PHP server.
I use Alamofire for requests, and print the data using print(). This is is what i'm getting:
{"error":false,"n":"Raghad"}
But when I want to convert it to String, it returns "" (empty) and
when I convert to boolean it returns the value correctly.
So, how can I fix it?
let wJSON : JSON = JSON(response.result.value!)
print(wJSON["n"].stringValue)
print(wJSON["error"].boolValue)
Simple solution using Decodable, define a Struct that conforms to the Decodable protocol for your dictionary
struct Reply: Decodable {
let error: Bool
let n: String
}
let data = response.data
do {
let result = try JSONDecoder().decode(Reply.self, from: data)
print("\(result.n) \(result.error)")
} catch {
print(error)
}
I change the responseString to responseJSON
Alamofire.request(Url!, method: .post, parameters: par).validate().responseJSON { response in if response.result.isSuccess { let wJSON : JSON = JSON(response.result.value!)
and it's work

Swift ObjectMapper: How to parse JSON with backslash

I have tried pretty much all the potential solutions on stackoverflow and so far no luck,
This is my json response:
[
"{\"id\":5,\"request_id\":\"rqst5c17fc752d44f1.15452158\",\"business_name\":\"611 Solutions\",\"business_email\":\"611thesolutions#gmail.com\",\"title\":\"123ABC - TESTING\",\"details\":\"Package is fragile, please haul with care\",\"load_description\":\"Royal Timber\",\"amount_offered\":\"2500\",\"pickup_address\":\"123 Colliumeal Dr, Fort Wayne, Indiana\",\"dropoff_address\":\"647 Airportway, Chicago, Illinois\",\"timestamp\":\"2018-12-17 19:43:49\"}"
]
Notice there are backslashes within the key and values of the json and my parsing is failing, this is how I am parse the json:
Alamofire.request(JOB_REQUEST_BASE_URL, method: .post, parameters: parameter, encoding: URLEncoding(), headers: nil).responseArray { (response: DataResponse<[JobResponseDataObject]>) in
log.debug("Fetching Job Requests...")
switch response.result {
case .success(let responseArray) :
log.debug(response.debugDescription)
log.debug("Sucessfully fetch job requests")
log.debug("Job request counts: \(responseArray.count)")
completionHandler(JobRequest.fetchJobRequest.Response(jobResponses: responseArray), nil)
case .failure(let error) :
log.debug("Fetching error: JobRequest")
log.debug(error.localizedDescription)
completionHandler(nil, .FailedToFetchEmptyJobRequests)
}
}
I have also tried fetching the pure string using .responseString and doing let json = response.result.value?.replacingOccurrences(of: "\\", with: "") and mapping it like so let jobs = Mapper<JobResponseDataObject>().map(JSONString: json!) so far no luck too. Please help
Thanks
You can try
if let str = responseArray.first as? String , let data = str.data(using:.utf8) {
do {
let decoder = JSONDecoder()
decoder.keyDecodingStrategy = .convertFromSnakeCase
let res = try decoder.decode(Root.self,from:data)
}
catch {
print(error)
}
}
struct Root: Codable {
let id: Int
let requestId, businessName, businessEmail, title: String
let details, loadDescription, amountOffered, pickupAddress: String
let dropoffAddress, timestamp: String
}
You don't need to remove backslashes - it's just serilized one more time, that means it needs to deserialize back.
Look at: Why json response includes backward slashes in web api response
Just make a Data object from the string item:
let data = stringItem.data(using: .utf8)
then decode normally using JSONDecoder.

Trouble parsing JSON data into Swift

i am trying to parse JSON data from web service into my Swift
JSON Output on my web browser:
[{"code":0,"message":"Check Username and Password....","userid":""}]
Swift Code:
Alamofire.request(URL_USER_LOGIN, method: .post, parameters: parameters).responseJSON
{
response in
//printing response
print(response)
if let userJSON = response.result.value
{
let userdata:Dictionary = userJSON as! Dictionary<String, Any>
let message:Dictionary = userdata["message"] as! Dictionary<String, Any>
print(message)
}
I want to use message element from the JSON for my code. However i get the following output and error:
(
{
code = 1;
message = "Login Successfull";
userid = 236;
}
)
Could not cast value of type '__NSSingleObjectArrayI' (0x10fd94b98) to 'NSDictionary' (0x10fd958b8).
2018-11-03 20:15:10.762929+0530 testDisplayTable[44610:2871941]
Could not cast value of type '__NSSingleObjectArrayI' (0x10fd94b98) to 'NSDictionary' (0x10fd958b8).
How do I successfully get the value of message and print? Can someone please show me the correct code for my case. Thanks in advance!
It's an array not dictionary
if let userdata = userJSON as? [[String:Any]] {
if let message = userdata[0]["message"] as? String {
print(message)
}
}

Invalid top-level type in JSON write Swift 4

I am trying to learn JSON parsing. I have written an API in Laravel, which returns status : 200 in response. What I did is this:
guard let url = URL(string: "http://localhost/workon-api/public/api/register") else { return }
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
let newUser = User.init(name: "Rob", email: "abc#gmail.com", password: "12345678")
do {
let jsonBody = try JSONEncoder().encode(newUser)
request.httpBody = jsonBody
} catch { }
URLSession.shared.dataTask(with: request) { (data, response, error) in
guard let data = data else { return }
do {
let json = try JSONSerialization.data(withJSONObject: data, options: .prettyPrinted)
print(json)
} catch {}
}.resume()
Now, I am getting this error: Invalid top-level type in JSON write and app's crashing. After searching, I used this:
let json = try JSONSerialization.jsonObject(with: data, options: [])
And, it works. Why the previous method is not working? And, I get a response like this if I try to return the collected userInfo.
status = "{\"name\":\"Rob\",\"email\":\"abc#gmail.com\",\"password\":\"12345678\"}";
Why are back-slashes there? Are these okay? And, what is Gzip data? I know I am asking a lot, but I need to understand this. Thanks in advance.
P.S. : Here is the User Model.
struct User: Encodable {
let name : String?
let email : String?
let password : String?
}
First of all the backslashes are virtual. The framework adds them to be able to print double quotes within a literal string.
Secondly dataTask returns serialized JSON Data so to get a dictionary or array from the data you have to call jsonObject(with.
let object = try JSONSerialization.jsonObject(with: data)
print(object)

Alamofire and SwiftyJSon get value outside request function

Hey I am new here and I am trying to get value from request outside the request function in VC, but I cant do that I get errors I tried few ways, but I keep getting different errors, now I get Type Any has no subscript members, could you help me how to get string from request and find an array and take a value from it.
I need to get value from Json strin in VC so I am trying this way:
let retur = Json()
retur.login(userName: userName.text!, password: password.text!) { (JSON) in
print(JSON)
let json = JSON
let name = json["ubus_rpc_session"].stringValue
print(name)
Response:
{"jsonrpc":"2.0","id":1,"result":[0,{"ubus_rpc_session":"70ea230f29057f54459814459b5a316e","timeout":300,"expires":300,"acls":{"access-group":{"superuser":["read","write"],"unauthenticated":["read"]},"ubus":{"":[""],"session":["access","login"]},"uci":{"*":["read","write"]}},"data":{"username":"root"}}]}
My request:
private func makeWebServiceCall (urlAddress: String, requestMethod: HTTPMethod, params:[String:Any], completion: #escaping (_ JSON : Any) -> ()) {
Alamofire.request(urlAddress, method: requestMethod, parameters: params, encoding: JSONEncoding.default).responseString { response in
switch response.result {
case .success:
if let jsonData = response.result.value {
completion(jsonData)
}
case .failure( _):
if let data = response.data {
let json = String(data: data, encoding: String.Encoding.utf8)
completion("Failure Response: \(json)")
}
Function which call request method:
public func login(userName: String, password: String, loginCompletion: #escaping (Any) -> ()) {
let loginrequest = JsonRequests.loginRequest(userName: userName, password: password)
makeWebServiceCall(urlAddress: URL, requestMethod: .post, params: loginrequest, completion: { (JSON : Any) in
loginCompletion(JSON)
})
Updated:
You can't subscript with Any and after you converting JSON to [String:Any] if you are trying .stringValue with subscripting Dictionary then Dictionary doesn't have any property stringValue you are mixing two things here SwiftyJSON and Swift native type. I will access your JSON response this way.
First get clear about how you get value of ubus_rpc_session from your JSON response. You can't directly get value of ubus_rpc_session from your JSON response because it is inside the 2nd object in your result array,so to get the ubus_rpc_session try like this way.
retur.login(userName: userName.text!, password: password.text!) { (json) in
print(json)
if let dic = json as? [String:Any], let result = dic["result"] as? [Any],
let subDic = result.last as? [String:Any],
let session = subDic["ubus_rpc_session"] as? String {
print(session)
}
}
If you want to work with SwiftyJSON then you can get value of ubus_rpc_session this way.
retur.login(userName: userName.text!, password: password.text!) { (json) in
print(json)
let jsonDic = JSON(json)
print(jsonDic["result"][1]["ubus_rpc_session"].stringValue)
}