php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Request #76847 support headers in individual parameters in "Multipart/form-data" requests
Submitted: 2018-09-06 10:53 UTC Modified: -
From: divinity76+spam at gmail dot com Assigned:
Status: Open Package: cURL related
PHP Version: Next Minor Version OS:
Private report: No CVE-ID: None
 [2018-09-06 10:53 UTC] divinity76+spam at gmail dot com
Description:
------------
the `multipart/form-data` format and libcurl allows for headers for individual parameters in the `multipart/form-data` body (look at the "Expected Result" section to see an example of what it looks like), but php's libcurl wrapper, the curl_* api does not (except 1 notable exception thanks to the CURLFile class, which allows specifying the "Content-Type" and "filename" headers)

this limitation makes it difficult to answer this question https://stackoverflow.com/questions/52182551/linux-curl-f-to-php-curl-contact-everyone-api/52191778 
and to port the following curl invocation to php: 


curl -F "json={whatever:123};headers=\"Content-Type: application/json\";headers=\"X-Api-Key: jsonapikey\"" -F "xml=.<xml>whatever</xml>;headers=\"Content-Type: application/xml\";headers=\"X-Api-Key: xmlapikey\"" dumpinput.ratma.net

currently you'll have to craft the multipart/form-data body manually and give it to CURLOPT_POSTFIELDS as a string or something.

so for php userland, i propose a CURLMultiPart class taking a value and a array of strings of headers just like the existing CURLOPT_HTTPHEADER, and otherwise work much like the existing CURLFile class. at the same time i propose upgrading the CURLFile class to add a new optional array parameter of custom headers.

as for the libcurl integration, the example code generated by curl's `--libcurl` parameter may be of help: http://paste.debian.net/1040960/

Test script:
---------------
<?php
$ch = curl_init ();
curl_setopt_array ( $ch, array (
		CURLOPT_URL => "http://dumpinput.ratma.net",
		CURLOPT_POST => 1,
		CURLOPT_POSTFIELDS => array (
				'json' => new CURLMultiPart ( json_encode ( array (
						'whatever' => 123 
				) ), array (
						'Content-Type: application/json',
						'X-Api-Key: jsonapikey' 
				) ),
				'xml' => new CURLMultiPart ( '.<xml>whatever</xml>', array (
						'Content-Type: application/xml',
						'X-Api-Key: xmlapikey' 
				) ) 
		) 
) );
curl_exec ( $ch );


Expected result:
----------------
POST / HTTP/1.1
Host: dumpinput.ratma.net
User-Agent: curl/7.59.0
Accept: */*
Content-Length: 373
Content-Type: multipart/form-data; boundary=------------------------43d95126c0bbf31e

--------------------------43d95126c0bbf31e
Content-Disposition: form-data; name="json"
Content-Type: application/json
X-Api-Key: jsonapikey

{whatever:123}
--------------------------43d95126c0bbf31e
Content-Disposition: form-data; name="xml"
Content-Type: application/xml
X-Api-Key: xmlapikey

.<xml>whatever</xml>
--------------------------43d95126c0bbf31e--

Actual result:
--------------
PHP Fatal error:  Uncaught Error: Class 'CURLMultiPart' not found

Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2018-09-07 09:05 UTC] divinity76 at gmail dot com
for a userland implementation, as well as an example of the amount of shit one has to do to work around this limitation, see the: "edit: if you absolutely must have the header, then you cannot use PHP's curl_ api's multipart/form-data generator, you must roll your own"-part of this post: https://stackoverflow.com/a/52191778/1067003
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Nov 21 11:01:29 2024 UTC