sebasthug sebasthug - 1 year ago 102
Swift Question

POST with swift and API

I've a problem when I try to send a POST request to my API on my server, I've followed many many different tutorials but it still doesn't work.
I know than my problem is with the POST request but I can't solve it !
So this is my code in Swift and my API in php : (and yes I've replaced the xxxx by the real IDs in my code)

To sum up server receive the request and for example if I manually enter a pseudo it works, It's really the POST method who doesn't work.. The server doesn't receive the POST parameter

Swift code :

var request = NSMutableURLRequest(URL: NSURL(string: "http://localhost:8888/academy/test.php")!)
var session = NSURLSession.sharedSession()
request.HTTPMethod = "POST"

var params = ["pseudo":"test"] as Dictionary<String, String>

var err: NSError?
request.HTTPBody = NSJSONSerialization.dataWithJSONObject(params, options: nil, error: &err)
request.addValue("application/json", forHTTPHeaderField: "Content-Type")
request.addValue("application/json", forHTTPHeaderField: "Accept")

var task = session.dataTaskWithRequest(request, completionHandler: {data, response, error -> Void in
println("Response: \(response)")
var strData = NSString(data: data, encoding: NSUTF8StringEncoding)
println("Body: \(strData)")
var err: NSError?
var json = NSJSONSerialization.JSONObjectWithData(data, options: .MutableLeaves, error: &err) as? NSDictionary

// Did the JSONObjectWithData constructor return an error? If so, log the error to the console
if(err != nil) {
let jsonStr = NSString(data: data, encoding: NSUTF8StringEncoding)
println("Error could not parse JSON: '\(jsonStr)'")
else {
// The JSONObjectWithData constructor didn't return an error. But, we should still
// check and make sure that json has a value using optional binding.
if let parseJSON = json {
// Okay, the parsedJSON is here, let's get the value for 'success' out of it
var success = parseJSON["success"] as? Int
println("Succes: \(success)")
else {
// Woa, okay the json object was nil, something went worng. Maybe the server isn't running?
let jsonStr = NSString(data: data, encoding: NSUTF8StringEncoding)
println("Error could not parse JSON: \(jsonStr)")

PHP Code :

$BDD_hote = 'xxxxx';
$BDD_bd = 'xxxxx';
$BDD_utilisateur = 'xxxxx';
$BDD_mot_passe = 'xxxxx';

$bdd = new PDO('mysql:host='.$BDD_hote.';dbname='.$BDD_bd, $BDD_utilisateur, $BDD_mot_passe);
$bdd->exec("SET CHARACTER SET utf8");

catch(PDOException $e){
echo 'Erreur : '.$e->getMessage();
echo 'N° : '.$e->getCode();
$pseudo = addslashes($_POST["pseudo"]);
$req = $bdd->query("SELECT * from users WHERE pseudo='$pseudo'");
$resultArray = array();
$donnees = $req->fetch();
echo json_encode($donnees);

Thanks by advance :)

Answer Source

Try this:

 let myURL = NSURL(string: "http://localhost:8888/academy/test.php")! 
 let request = NSMutableURLRequest(URL: myURL)
 request.HTTPMethod = "POST"
 request.setValue("application/x-www-form-urlencoded", forHTTPHeaderField: "Content-Type")
 request.setValue("application/json", forHTTPHeaderField: "Accept")
 let bodyStr:String = "pseudo=test"
 request.HTTPBody = bodyStr.dataUsingEncoding(NSUTF8StringEncoding) 
 let task = NSURLSession.sharedSession().dataTaskWithRequest(request) {
      data, response, error in

      // Your completion handler code here

You have to encode your data using UTF8 string encoding. If you need to set more than one field&value pairs for request body, you can change the body string, for example, "pseudo=test&language=swift". In fact, I usually create an extension for NSMutableURLRequest and add a method which takes a dictionary as parameter and sets the content of this map(dictionary) as HTTPBody using correct encoding. This may work for you:

 extension NSMutableURLRequest {
      func setBodyContent(contentMap: Dictionary<String, String>) {
           var firstOneAdded = false
           let contentKeys:Array<String> = Array(contentMap.keys)
           for contentKey in contentKeys {
                if(!firstOneAdded) {
                     contentBodyAsString += contentKey + "=" + contentMap[contentKey]!
                     firstOneAdded = true
                else {
                     contentBodyAsString += "&" + contentKey + "=" + contentMap[contentKey]! 
           contentBodyAsString = contentBodyAsString.stringByAddingPercentEscapesUsingEncoding(NSUTF8StringEncoding)!
           self.HTTPBody = contentBodyAsString.dataUsingEncoding(NSUTF8StringEncoding)

And you can use this as:


I hope this helps you!