Dachmt
Dachmt

Reputation: 2099

Symfony 1.4.2 no content in PHP cURL PUT request

Using PHP cURL and Symfony 1.4.2

I'm trying to do a PUT request including data (JSON) to modify an object in my REST web services, but can't catch the data on the server side.

It seems that the content is attached successfully when checking at my logs:

PUT to http://localhost:8080/apiapp_test.php/v1/reports/498 with post body content=%7B%22report%22%3A%7B%22title%22%3A%22The+title+has+been+updated%22%7D%7D

I attached the data like this:

$curl_opts = array(
    CURLOPT_HTTPHEADER => $headers,
    CURLOPT_POSTFIELDS => http_build_query(array('content' => $post_data)),
);

And wanted to get the data using something like this

$payload = $request->getPostParameter('content');

It is not working and I've tried many ways to get this data in my actions file. I've tried the following solutions:

parse_str(file_get_contents("php://input"), $post_vars);
$payload = $post_vars['content'];
// or
$data = $request->getContent(); // $request => sfWebRequest
$payload = $data['content'];
// or
$payload = $request->getPostParameter('content');

// then I'd like to do that
$json_array = json_decode($payload, true);

I just don't know how to get this data in my actions and it's frustrating, I've read many topics here about it but none is working for me.

Additional informations:

I have these setup for my cURL request:

curl_setopt($curl_request, CURLOPT_CUSTOMREQUEST, $http_method);

if ($http_method === sfRequest::PUT) {
    curl_setopt($curl_request, CURLOPT_PUT, true);
    $content_length = array_key_exists(CURLOPT_POSTFIELDS, $curl_options) ? strlen($curl_options[CURLOPT_POSTFIELDS]) : 0;
    $curl_options[CURLOPT_HTTPHEADER][] = 'Content-Length: ' . $content_length;
}

curl_setopt($curl_request, CURLOPT_URL, $url);
curl_setopt($curl_request, CURLOPT_CONNECTTIMEOUT, 4);
curl_setopt($curl_request, CURLOPT_TIMEOUT, 4);
curl_setopt($curl_request, CURLOPT_DNS_CACHE_TIMEOUT, 0);
curl_setopt($curl_request, CURLOPT_NOSIGNAL, true);
curl_setopt($curl_request, CURLOPT_RETURNTRANSFER, true);

In sfWebRequest.php, I've seen this:

case 'PUT':
  $this->setMethod(self::PUT);
  if ('application/x-www-form-urlencoded' === $this->getContentType())
  {
    parse_str($this->getContent(), $postParameters);
  }
  break;

So I tried to set the header's Content-Type to it but it doesn't do anything.

If you have any idea, please help!

Upvotes: 1

Views: 2724

Answers (1)

j0k
j0k

Reputation: 22756

According to an other question/answer, I've tested this solution and I got the correct result:

$body = 'the RAW data string I want to send';

/** use a max of 256KB of RAM before going to disk */
$fp = fopen('php://temp/maxmemory:256000', 'w');
if (!$fp) {
    die('could not open temp memory data');
}
fwrite($fp, $body);
fseek($fp, 0);

$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_PUT, 1);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
curl_setopt($ch, CURLOPT_BINARYTRANSFER, true);
curl_setopt($ch, CURLOPT_INFILE, $fp); // file pointer
curl_setopt($ch, CURLOPT_INFILESIZE, strlen($body));

$output = curl_exec($ch);

echo $output;
die();

And on the other side, you can retrieve the content using:

$content = $request->getContent();

If you var_dump it, you will retrieve:

the RAW data string I want to send

Upvotes: 2

Related Questions