0

I'm trying to set up sending data to a PHP server but I'm having no luck at all.

Here is my PHP code.

<?php
require_once "../config/config.php";
var_dump($_POST);
var_dump($_REQUEST);
// Read request parameters
if(isset($_REQUEST)){
    $username = $db->escape($_REQUEST["username"]);
    $email = $db->escape($_REQUEST["email"]);
    $password = $db->escape($_REQUEST["password"]);
    $id = MD5($email);
    echo $username;
    //$db->query("INSERT INTO user ('id','username','email','password') VALUES ('$id','$username','$email',PASSWORD('$password'))");
    $returnValue = $id;
}else{
    $returnValue = "No data received";
}
// Send back request in JSON format
echo json_encode($returnValue); 
?>

Here is my Swift Code

    let request = NSMutableURLRequest(URL: NSURL(string: "http://***************/register.php")!)

    let session = NSURLSession.sharedSession()

    request.HTTPMethod = "POST"

    let data = "username=JoeBloggs&email=joe@bloggs.com&password=12345"

    request.HTTPBody = (data as NSString).dataUsingEncoding(NSUTF8StringEncoding)
    request.addValue("application/json", forHTTPHeaderField: "Content-Type")
    request.addValue("application/json", forHTTPHeaderField: "Accept")

    let task = session.dataTaskWithRequest(request) { (data, response, error) -> Void in
        print(response)
        let strData = NSString(data: data!, encoding: NSUTF8StringEncoding)
        print(strData)
        print(error)

    }
    task.resume()

I'm not concerned about getting a result back yet (I have that working fine). I just can't get any data to the server.

Here is the result from the above script.

Optional(<NSHTTPURLResponse: 0x7ff9b3d6ea90> { URL: http://iep.almartin.co.uk/register.php } { status code: 200, headers {
"Cache-Control" = "no-store, no-cache, must-revalidate, post-check=0, pre-check=0";
Connection = close;
"Content-Type" = "text/html; charset=UTF-8";
Date = "Tue, 01 Sep 2015 09:02:46 GMT";
Expires = "Thu, 19 Nov 1981 08:52:00 GMT";
Pragma = "no-cache";
Server = nginx;
"Set-Cookie" = "PHPSESSID=8j2d7oobg9plvdik1dcbqtoq70; path=/";
"Transfer-Encoding" = Identity;
} })
Optional(array(0) {
 }
 array(0) {
 }
 <br />
 <b>Notice</b>:  Undefined index: username in <b>/home/linweb34/i/iep.almartin.co.uk/user/htdocs/register.php</b> on line <b>7</b><br />
 <br />
 <b>Notice</b>:  Undefined index: email in <b>/home/linweb34/i/iep.almartin.co.uk/user/htdocs/register.php</b> on line <b>8</b><br />
 <br />
 <b>Notice</b>:  Undefined index: password in <b>/home/linweb34/i/iep.almartin.co.uk/user/htdocs/register.php</b> on line <b>9</b><br />
 "d41d8cd98f00b204e9800998ecf8427e")
 nil

As you can see both $_REQUEST and $_POST are returning empty arrays.

What am I doing wrong?

Al Martin
  • 179
  • 3
  • 15

4 Answers4

0

The error clearly says that there is problem with your MySQL usage. Following are the working code template. It uses PDO for DB connection.

function __construct() {
    $this->conn = new PDO('mysql:host=<your hostnam>;dbname=<dbname>', '<user>', '<pass>');
    // Generate stack trace on failure.
    $this->conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
}

/*
 * Write a function and pass your variables
 */
function get_data_from_db($id,$username,$password,$email) {
    $stmt = $this->conn->prepare("INSERT INTO `user`(`id`,`username`,`email`,`password`) VALUES (:id,:username,:email,PASSWORD(:password))");
    $stmt->execute(array(':id' => $id, ':username' => $username, ':email' => $email, ':password' => $password));
    $data = $stmt->fetchAll(PDO::FETCH_ASSOC);
    $stmt->closeCursor();

    return $data;
}

Now in your code, just add a function call and you are done:

if(isset($_REQUEST)){
    $username = $db->escape($_REQUEST["username"]);
    $email = $db->escape($_REQUEST["email"]);
    $password = $db->escape($_REQUEST["password"]);
    $id = MD5($email);

    $result = get_result_from_db($id,$username,$password,$email);

    echo json_encode($result);
}

Note : Not tested, but it should work.

Nagaraja Thangavelu
  • 1,168
  • 1
  • 15
  • 31
  • 1
    You're way off in this. The error in the MySQL isn't the issue. If you look in the response the first error is that $_REQUEST["username"] is an undefined index. In other words it doesn't exist which it should. For some reason the POST from my app isn't reaching the server. That is the issue, not the MySQL. – Al Martin Sep 01 '15 at 08:57
  • Yes, ur right. I thought the problem was with MySQL issue of getting the proper associative index. Also, thought that data is coming to PHP by seeing the var_dump and ISSET conditions. – Nagaraja Thangavelu Sep 01 '15 at 09:02
  • Yes, the var_dump is returning empty arrays. I've followed several examples online on how to do this but I can't see why it doesn't work for me. – Al Martin Sep 01 '15 at 09:07
  • Have you checked this post http://stackoverflow.com/questions/24714566/how-to-send-post-parameters-in-swift – Nagaraja Thangavelu Sep 01 '15 at 09:16
0

Found the problem.

It seems these lines are the culprit in my app.

request.addValue("application/json", forHTTPHeaderField: "Content-Type")
request.addValue("application/json", forHTTPHeaderField: "Accept")

It worked fine when I removed them.

Which brings up another question, how do I set up PHP to accept header type "application/json" ?

Al Martin
  • 179
  • 3
  • 15
  • the server accepts json, but you're sending html/text. You have to serialize the text with NSJSONSerialization – vadian Sep 01 '15 at 09:21
0

To send JSON to a server with POST you have to put the data to be sent into a dictionary and serialize the dictionary with NSJSONSerialization

let request = NSMutableURLRequest(URL: NSURL(string: "http://***************/register.php")!)

let session = NSURLSession.sharedSession()
let postData = ["username" : "JoeBloggs", "email" : "joe@bloggs.com", "password" : "12345"]

do {
  let jsonData = try NSJSONSerialization.dataWithJSONObject(postData, options: NSJSONWritingOptions())
  request.HTTPMethod = "POST"
  request.setValue("\(jsonData.length)", forHTTPHeaderField:"Content-Length")
  request.setValue("application/json", forHTTPHeaderField:"Accept")
  request.setValue("application/json", forHTTPHeaderField:"Content-Type")
  request.HTTPBody = jsonData

  let task = session.dataTaskWithRequest(request) { (data, response, error) -> Void in
    print(response)
    let strData = NSString(data: data!, encoding: NSUTF8StringEncoding)
    print(strData)
    print(error)

  }
  task.resume()
} catch let error as NSError {
  print(error)
}
vadian
  • 274,689
  • 30
  • 353
  • 361
  • Thanks for your answer. I had this originally but I was getting the same problem although I didn't have jsonData.length. I'll try this again tonight and see if it works. – Al Martin Sep 01 '15 at 10:03
  • So I tried this and it still doesn't work. Interestingly if I print(jsonData) I get this---- <7b0a2020 22656d61 696c2220 3a20226a 6f654062 6c6f6767 732e636f 6d222c0a 20202270 61737377 6f726422 203a2022 31323334 35222c0a 20202275 7365726e 616d6522 203a2022 4a6f6542 6c6f6767 73220a7d>. I thought Json data was supposed to be readable? – Al Martin Sep 01 '15 at 15:20
  • no, `jsonData` is an `NSData` object like the result of `dataUsingEncoding:` – vadian Sep 01 '15 at 15:38
0

So I followed @vadian answer which didn't work initially. I did some research into why PHP wasn't accepting application/json.

I got it to work by using $HTTP_RAW_POST_DATA instead of $_POST or $_REQUEST in the php file.

However! $HTTP_RAW_POST_DATA is now depreciated but the following code works

$json = file_get_contents('php://input'); 
$obj = json_decode($json);

Seems like a PHP hack to me but at least it works.

Al Martin
  • 179
  • 3
  • 15