POST request not being sent in Swift - swift

I would just like to ask. Why is my POST request below not being sent? The code seems perfectly sound, and Xcode shows no errors. I am using Swift 3. Could you please help me? Thanks! My code is below, my post URL is here. Thanks again!
#IBAction func onClick(_ sender: Any) {
let username = Username.text
let password = Password.text
let request = NSMutableURLRequest(url: url)
request.httpMethod = "POST"
let params = ["username": username, "password": password] as Dictionary<String, AnyObject>
do {
try request.httpBody = JSONSerialization.data(withJSONObject: params, options: .prettyPrinted)
} catch {
print("Error")
}
request.addValue("application/JSON", forHTTPHeaderField: "Content-Type")
URLSession.shared.getAllTasks { (openTasks: [URLSessionTask]) in
NSLog("open tasks: \(openTasks)")
}
}

You need to use:
let task = session.dataTaskWithRequest(urlRequest, completionHandler: { (data, response, error) in
// do stuff with response, data & error here
print(error)
print(response)
})
task.resume()
Get more info here

You have to use URLSession.shared.dataTask(with:completionHandler:). Also, don't use NSMutableRequest, but use the native Swift version, URLRequest.
#IBAction func onClick(_ sender: Any) {
let username = Username.text
let password = Password.text
var request = URLRequest(url: url)
request.httpMethod = "POST"
let params = ["username": username, "password": password] as Dictionary<String, AnyObject>
do {
try request.httpBody = JSONSerialization.data(withJSONObject: params, options: .prettyPrinted)
} catch {
print("Error")
}
request.addValue("application/JSON", forHTTPHeaderField: "Content-Type")
URLSession.shared.dataTask(with: request, completionHandler: { data,response, error in
if let existingError = error {
//handle error
}
//handle response and/or data
}).resume()
}

Related

http Post says its working but it isn't posting on localhost

I've been trying to do an HTTP post to my localhost using swift for a mobile app, it prints Result -> Optional(["user": larry]) which should mean it works but it isn't posting anything on my localhost. My code is:
func ReqUsers() -> Void {
let json = ["user":"larry"]
do {
let jsonData = try JSONSerialization.data(withJSONObject: json, options: .prettyPrinted)
let url = NSURL(string: "http://192.168.1.318:8080")! /*localhost*/
let request = NSMutableURLRequest(url: url as URL)
request.httpMethod = "POST"
request.setValue("application/json; charset=utf-8", forHTTPHeaderField: "Content-Type")
request.httpBody = jsonData
let task = URLSession.shared.dataTask(with: request as URLRequest){ data, response, error in
if error != nil{
print("Error -> \(String(describing: error))")
return
}
do {
let result = try JSONSerialization.jsonObject(with: /*data!*/ request.httpBody!, options: .allowFragments) as? [String:AnyObject]
print("Result -> \(String(describing: result))")
} catch {
print(response!)
print("Error -> \(error)")
print("that")
}
}
task.resume()
} catch {
print(error)
print("this")
}
print("called")
}
thanks for your time
for more info on the backend it's being written with goLang and here is the code:
package main
import (
"fmt"
//"os"
//"io/ioutil"
//"log"
"net/http"
)
func main() {
http.HandleFunc("/", HelloServer)
http.ListenAndServe(":8080", nil)
}
func HelloServer(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "Hello")
}
If you don't see logs in your server, may be caused by URLSession's cache policy.
Try to set the cachePolicy property of your URLRequest to .reloadIgnoringLocalAndRemoteCacheData or .reloadIgnoringCacheData and see if that works:
let url = URL(string: "http://192.168.1.318:8080")! /*localhost*/
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.setValue("application/json; charset=utf-8", forHTTPHeaderField: "Content-Type")
request.httpBody = jsonData
request.cachePolicy = .reloadIgnoringLocalAndRemoteCacheData
// or
request.cachePolicy = .reloadIgnoringCacheData

URL Session Post with form-data parameter in iOS Swift

I am trying to POST a parameter using form-data in swift.
I want to pass a mobile number with url session in form-data format. but I can't able to send data properly . please help me to pass data on form-data format in url session.
code I have Tried:
func registerService(){
print("register tapped")
let parameters: [String: Any] = [
"mobile" : mobileNumber
]
let url = URL(string: "http://54.251.198.30/api/user/login")
var req = URLRequest(url: url!)
req.httpMethod = "POST"
let boundary = "Boundary-\(UUID().uuidString)"
req.addValue("multipart/form-data : \(boundary)", forHTTPHeaderField: "Contet-Type")
req.addValue("multipart/form-data", forHTTPHeaderField: "Accept")
req.httpBody = NSKeyedArchiver.archivedData(withRootObject: parameters)
guard let httpBody = try? JSONSerialization.data(withJSONObject: parameters, options: .prettyPrinted) else {return}
req.httpBody = httpBody
let session = URLSession.shared
session.dataTask(with: req, completionHandler: {(data, response, error) in
if response != nil {
print(response)
}
if let jsonResponse = try? JSONDecoder().decode(LoginBase.self, from: data!) {
print(jsonResponse)
}else{
print("error")
}
}).resume()
}
I have added an image which parameter I want to pass. you Can see Here
thanks for your response
I have modified your function parameter as well as request-body in the correct syntax. Now you can use as follows:-
func Register(){
print("register tapped")
let parameters: [String: Any] = ["mobile" : mobileNumber] as Dictionary<String, Any>
var request = URLRequest(url: URL(string: "http://54.251.198.30/api/user/login")!)
request.httpMethod = "POST"
request.httpBody = try? JSONSerialization.data(withJSONObject: parameters, options: [])
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
let session = URLSession.shared
let task = session.dataTask(with: request, completionHandler: { data, response, error -> Void in
print(response!)
do {
let json = try JSONSerialization.jsonObject(with: data!) as! Dictionary<String, AnyObject>
print(json)
} catch {
print("error")
}
})
task.resume()
}

Swift - Multiple URL Request - Code To Refactor and To Reuse

I'm new to Swift and I am trying to refactor my URL Post requests. I have multiple URL POST requests inside the same View Controller like this. Everything works fine but it seems to me that there is a lot of repetitive code that could be reused. Particularly, I don't know how to pass/handle different Data Models that should be used in parseRequest1 and parseRequest2. I also read that there should be only one session used for URL requests within the same project. Any help would be greatly appreciate it!
func request1() {
let parameters = [...//some parameters to send]
guard let url = URL(string: "https//www.....") else {return}
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
guard let parametersToSend = try? JSONSerialization.data(withJSONObject: parameters, options: [])
else {
print("Error")
return
}
request.httpBody = parametersToSend
let session = URLSession.shared
session.dataTask(with: request) { (data, response, error) in
if let safeData = data {
self.parseRequest1(data: safeData)
}
}.resume()
}
func parseRequest1(data: Data){
let decoder = JSONDecoder()
do{
let decodedData = try decoder.decode(DataModelForRequest1.self, from: data)
DispatchQueue.main.async {
self.performAction1(request1Result)
}
} catch {
print(error)
}
}
Then I have another URL request request2 which is almost identical except the parameters, and model to be used for decoding and action inside parseRequest2.
func request2() {
let parameters = [...//some parameters to send]
guard let url = URL(string: "https//www.....") else {return}
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
guard let parametersToSend = try? JSONSerialization.data(withJSONObject: parameters, options: [])
else {
print("Error")
return
}
request.httpBody = parametersToSend
let session = URLSession.shared
session.dataTask(with: request) { (data, response, error) in
if let safeData = data {
self.parseRequest2(data: safeData)
}
}.resume()
}
func parseRequest2(data: Data){
let decoder = JSONDecoder()
do{
let decodedData = try decoder.decode(DataModelForRequest2.self, from: data)
DispatchQueue.main.async {
self.performAction2(request2Result)
}
} catch {
print(error)
}
}
The only differences seem to be:
request parameters
type of model returned
the action you do after the response is received
This means that we can write this as one single method taking the above three values as parameters:
func request<T: Codable>(modelType: T.Type, parameters: [String: Any], completion: (T) -> Void) {
func parseResponse(data: Data){
let decoder = JSONDecoder()
do{
let decodedData = try decoder.decode(T.self, from: data)
DispatchQueue.main.async {
completion(decodedData)
}
} catch {
print(error)
}
}
guard let url = URL(string: "https//www.....") else {return}
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
guard let parametersToSend = try? JSONSerialization.data(withJSONObject: parameters, options: [])
else {
print("Error")
return
}
request.httpBody = parametersToSend
let session = URLSession.shared
session.dataTask(with: request) { (data, response, error) in
if let safeData = data {
parseResponse(data: safeData)
}
}.resume()
}
You can then call this method with the appropriate parameters as per your needs.

Swift parsing a http request returns domain error

okay, so Im trying to make a post request but when I try to parse the data, I always get a error domain code= 3840.
https://www.codepunker.com/tools/http-requests/64243-brrjq9t
In this example it shows what the request response looks like.
and this is my code:
let parameters = ["txt": "כאב גרון","usr": "","pass": "" ,"ktivmale": false] as [String : Any]
guard let url = URL(string: "http://www.nakdan.com/GetResult.aspx") else { return }
var request = URLRequest(url: url)
request.httpMethod = "POST"
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
request.addValue("text/xml; charset=utf-8", forHTTPHeaderField: "Content-Type")
guard let httpBody = try? JSONSerialization.data(withJSONObject: parameters, options: []) else { return }
request.httpBody = httpBody
let task = URLSession.shared.dataTask(with: request as URLRequest){
data,response, error in
print(response!)
if error != nil{
print("error")
return
}
do {
let json = try JSONSerialization.jsonObject(with: data!, options: [])
DispatchQueue.main.async(execute: { () -> Void in
print(json)
SVProgressHUD.dismiss()
})
} catch {
print(error)
SVProgressHUD.dismiss()
SVProgressHUD.showError(withStatus: "Connection Failed.")
}
}
task.resume()

Call Rest API from Swift3

I trying to send a POST request in swift for example :
url = "http://localhost:9080/mfp/api/az/v1/token"
Headers :
Authorization = "Basic UGlua0NhclBhc3NlbmdlcjoxMjM0"
Content-Type = "application/x-www-form-urlencoded"
Body :
grant_type = client_credentials
scope = RegisteredClient messages.write push.application.com.XXX
What's simple way to do it ?
I've tried by use IBMMobileFirstPlatformFoundation SDK, it's return error "Can't not connect to server",but i'm sure that the connect still good... Here's my code :
let urlString = "http://localhost:9080/mfp/api/az/v1/token"
let url1 = URL(string: urlString)
let request1 = WLResourceRequest(url: url1! as URL, method: WLHttpMethodPost)!
request1.addHeaderValue("Basic UGlua0NhclBhc3NlbmdlcjoxMjM0" as NSObject, forName: "Authorization")
request1.addHeaderValue("application/x-www-form-urlencoded" as NSObject, forName: "Content-Type")
request1.send(withBody: "{\"grant_type\":\"client_credentials\",\"scope\":\"RegisteredClient messages.write push.application.com.XXX\"}", completionHandler: { (response, error) in
if error == nil {
print("Response : ")
print(response)
} else {
print("Error : ")
print(error)
}
})
You can use Alamofire as ZassX suggested or you can use URLSession.
I have some code as an example:
func postRequest(toUrl url: String, accessKey: String?, completion: #escaping(Data?, HTTPURLResponse?, Error?, AnyObject?) -> Void){
let requestUrl = NSURL(string: url)
let request = NSMutableURLRequest(url: requestUrl! as URL)
if accessKey != nil {
request.setValue("\(accessKey!)", forHTTPHeaderField: "Authorization")
}
request.addValue("application/x-www-form-urlencoded", forHTTPHeaderField: "Content-Type")
request.httpMethod = "POST"
request.httpBody = yourBody
URLSession.shared.dataTask(with: request as URLRequest, completionHandler: { (data,response,error) in
if let content = data{
do{
let myJSON = try JSONSerialization.jsonObject(with: content, options: JSONSerialization.ReadingOptions.mutableContainers) as AnyObject
completion(data as Data?, response as? HTTPURLResponse, error, myJSON)
}
catch{
print("JSON ERROR")
}
}else{
completion(data as Data?, response as? HTTPURLResponse, error, nil)
}
}).resume()
}
First, you don't manually manage the security token when you're using the MobileFirst SDK, it's handled automatically.
Next, WLResourceRequest() takes a URL that is relative to the MobileFirst server URL (http://localhost:9080/mfp, in your case). You can see that "base" URL in your mfpclient.plist file.
Your code will then look something like
let request = WLResourceRequest(
URL: NSURL(string: "/adapters/MyAdapter/myResource"),
method: WLHttpMethodGet
)
See https://mobilefirstplatform.ibmcloud.com/tutorials/en/foundation/8.0/application-development/resource-request/ios/