help with curl multipart from post

maximviper

BANNED
Joined
Oct 25, 2010
Messages
338
Reaction score
87
hello

i m trying to build a script that can post articles to my drupal based website on automation .but the porblem is the article postng form is multipart .and till now i havent figured out how to build header and postdata for multipart forms.

the header for the drupal form is like :

PHP:
http://mysite.com/drupal/?q=node%2Fadd%2Farticle&

POST /drupal/?q=node%2Fadd%2Farticle& HTTP/1.1
Host: mysite.com
User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:2.0b12) Gecko/20100101 Firefox/4.0b12
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip, deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 115
Connection: keep-alive
Referer: http://mysite.com/?q=node%2Fadd%2Farticle&
Cookie: Drupal.visitor.name=abcde; SESS0933c7f6c3b533f5a8c8b5e0739b8056=K6NQKbD8rItUPfuXxGpajYNGi5sh3A6IiSjYdDrIWLo; has_js=1
Content-Type: multipart/form-data; boundary=---------------------------7469163454380
Content-Length: 2836
-----------------------------7469163454380
Content-Disposition: form-data; name="title"

hello there
-----------------------------7469163454380
Content-Disposition: form-data; name="field_tags[und]"

hiiii
-----------------------------7469163454380
Content-Disposition: form-data; name="body[und][0][summary]"


-----------------------------7469163454380
Content-Disposition: form-data; name="body[und][0][value]"

hello everybody
-----------------------------7469163454380
Content-Disposition: form-data; name="body[und][0][format]"

filtered_html
-----------------------------7469163454380
Content-Disposition: form-data; name="files[field_image_und_0]"; filename=""
Content-Type: application/octet-stream


-----------------------------7469163454380
Content-Disposition: form-data; name="field_image[und][0][fid]"

0
-----------------------------7469163454380
Content-Disposition: form-data; name="field_image[und][0][display]"

1
-----------------------------7469163454380
Content-Disposition: form-data; name="changed"


-----------------------------7469163454380
Content-Disposition: form-data; name="form_build_id"

form-X6Kr86bnitVTegkkkTJ01ShYKnMTn2XBVH75BVIIIsA
-----------------------------7469163454380
Content-Disposition: form-data; name="form_token"

cUzbUH440gzTRSxjTj4n9I-omAQ2dByCl7DoVeMvmRE
-----------------------------7469163454380
Content-Disposition: form-data; name="form_id"

article_node_form
-----------------------------7469163454380
Content-Disposition: form-data; name="menu[link_title]"


-----------------------------7469163454380
Content-Disposition: form-data; name="menu[description]"


-----------------------------7469163454380
Content-Disposition: form-data; name="menu[parent]"

main-menu:0
-----------------------------7469163454380
Content-Disposition: form-data; name="menu[weight]"

0
-----------------------------7469163454380
Content-Disposition: form-data; name="log"


-----------------------------7469163454380
Content-Disposition: form-data; name="path[alias]"


-----------------------------7469163454380
Content-Disposition: form-data; name="comment"

2
-----------------------------7469163454380
Content-Disposition: form-data; name="name"

admin
-----------------------------7469163454380
Content-Disposition: form-data; name="date"


-----------------------------7469163454380
Content-Disposition: form-data; name="status"

1
-----------------------------7469163454380
Content-Disposition: form-data; name="promote"

1
-----------------------------7469163454380
Content-Disposition: form-data; name="additional_settings__active_tab"

edit-menu
-----------------------------7469163454380
Content-Disposition: form-data; name="op"

Save
-----------------------------7469163454380--
till now i came up with this script which obviously isnt correct

PHP:
<?php
$boundary = '-----------------------------7665267813202';

$header = array (
                            'Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
                            'Accept-Language: en-us,en;q=0.5',
                            'Accept-Encoding: gzip, deflate',
                            'Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7',
                            'Keep-Alive: 115',
                            'Connection: keep-alive',
                            'Referer: http://mysite.com/?q=node%2Fadd%2Farticle&',
                            'Content-Type: multipart/form-data; boundary=---------------------------7469163454380'
                            );

$payload = array 
( 
        'Content-Disposition: form-data; name="title"' => "hellooo here",
        'Content-Disposition: form-data; name="field_tags[und]"' => "test",
        'Content-Disposition: form-data; name="body[und][0][summary]"' => "",
        'Content-Disposition: form-data; name="body[und][0][value]"' => "hello everybody",
        'Content-Disposition: form-data; name="body[und][0][format]"' => "filtered_html", 
        'Content-Disposition: form-data; name="files[field_image_und_0]"; filename=""\nContent-Type: application/octet-stream' => "", 
        'Content-Disposition: form-data; name="field_image[und][0][fid]"' => "0", 
        'Content-Disposition: form-data; name="field_image[und][0][display]"' => "1",
        'Content-Disposition: form-data; name="changed"' => "",
        'Content-Disposition: form-data; name="form_build_id"' => "form-X6Kr86bnitVTegkkkTJ01ShYKnMTn2XBVH75BVIIIsA",
        'Content-Disposition: form-data; name="form_token"' => "cUzbUH440gzTRSxjTj4n9I-omAQ2dByCl7DoVeMvmRE",
        'Content-Disposition: form-data; name="form_id"' => "article_node_form",
        'Content-Disposition: form-data; name="menu[link_title]"' => "",
        'Content-Disposition: form-data; name="menu[description]"' => "",
        'Content-Disposition: form-data; name="menu[parent]"' => "main-menu:0",
        'Content-Disposition: form-data; name="menu[weight]' => "0",
        'Content-Disposition: form-data; name="log"' => "",
        'Content-Disposition: form-data; name="path[alias]"' => "",
        'Content-Disposition: form-data; name="comment"' => "2",
        'Content-Disposition: form-data; name="name"' => "admin",
        'Content-Disposition: form-data; name="date"' => "",
        'Content-Disposition: form-data; name="status"' => "1",
        'Content-Disposition: form-data; name="promote"' => "1",
        'Content-Disposition: form-data; name="additional_settings__active_tab"' => "edit-menu",
        'Content-Disposition: form-data; name="op"' => "Save"
    
);
 
  //$output .= "$boundary\r\n";
// foreach ($payload as $key => $value){
//    $output .= $value."$boundary\r\n";
  
  //  }
 
 echo " <BR><BR><BR><BR>Payload is:<BR>$output";
 $posturl="";
 $ch = curl_init($posturl);
 curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "Content-Type: multipart/form-data; boundary=--$srand");
 curl_setopt($ch, CURLOPT_POST      ,1);
 curl_setopt($ch, CURLOPT_POSTFIELDS    ,$postdata);
 curl_setopt($ch, CURLOPT_TIMEOUT, $timeout);
 curl_setopt($ch, CURLOPT_FOLLOWLOCATION  ,0);
 curl_setopt($ch, CURLOPT_COOKIE,  $mycookies);
 
curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
 curl_setopt($ch, CURLOPT_RETURNTRANSFER  ,1);  // RETURN THE CONTENTS OF THE CALL
 $return = curl_exec($ch);
 curl_close($ch);
?>
can somebody please guide me how to deal with multipart. i looked google but i am not able to find out any good example.

Fisrt i m not able to figure out how to frame the boundry
then i dont understans how to build the postdata.

my skype is :sourabh_swarnkar
 
Last edited:
the problem is i dont know to to build that kind of array. currently i m just trying to mimic what i m getting from livehttpheader. but i dont think this is the right way to do.
If only i can find any good example about how to deal with such kind of form...
 
array would be like

PHP:
$postdata = array(
"title" => "hellooo here",
"body" => "hellooo here"
);

 
array would be like

PHP:
$postdata = array(
"title" => "hellooo here",
"body" => "hellooo here"
);



oh.. i get it now. atleast this part :) thankyou

still i m unable to figure out how to inculde boundary value to the post data.
trying to include this line throws an error

curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "Content-Type: multipart/form-data; boundary=$boundary");
 
Yep it's like zelma says. Unlike a regular form POST, with a multipart form you don't have to concatenate your post data array into one string; you just send it to the contents of CURLOPT_POSTFIELDS and curl will automagically realize that it's a multipart form and take care of the boundaries for you. 99% of the time you don't need to provide complicated headers either - just keep it simple.

PHP:
$postdata['title'] = "hellooo here";
$postdata['field_tags[und]'] = "test";
// etc etc

$ch = curl_init();
curl_setopt($ch, CURLOPT_URL, $posturl);
curl_setopt($ch, CURLOPT_POST, 1);
curl_setopt($ch, CURLOPT_POSTFIELDS, $postdata);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$return = curl_exec($ch);
curl_close($ch);


If you want to upload a file (eg. an image) with a multi part form, you just use:

PHP:
$postdata['image_filename_field'] = "@/path/to/your/image.jpg";
 
i see... your explaination cleared things a bit. trying to modify my now.
thanks a lot :)
 
:( feeling like crying now .....

PHP:
function curl_post2($site,$token){


$boundary = '-----------------------------7665267813202';

$header = array (
                            'Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
                            'Accept-Language: en-us,en;q=0.5',
                            'Accept-Encoding: gzip, deflate',
                            'Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7',
                            'Keep-Alive: 115',
                            'Connection: keep-alive',
                       
                              );
//print_r($header);                            

$payload = array 
( 
        'title' => "hellooo here",
        'field_tags[und]' => "test",
        'body[und][0][summary]' => "",
        'body[und][0][value]' => "hello everybody",
        'body[und][0][format]' => "filtered_html", 
        'files[field_image_und_0]' => "", 
        'field_image[und][0][fid]' => "0", 
        'field_image[und][0][display]' => "1",
        'changed' => "",
        'form_build_id' => $token[3],
        'form_token' => $token[4],
        'form_id' => "article_node_form",
        'menu[link_title]' => "",
        'menu[description]' => "",
        'menu[parent]' => "main-menu:0",
        'menu[weight]' => "0",
        'log' => "",
        'path[alias]' => "",
        'comment' => "2",
        'name' => "admin",
        'date' => "",
        'status' => "1",
        'promote' => "1",
        'additional_settings__active_tab' => "edit-menu",
        'op' => "Save"
    
);
//print_r($payload);

$curl_opt = array(
    CURLOPT_RETURNTRANSFER => true, 
    CURLOPT_HEADER => 0,
    CURLOPT_USERAGENT => "Mozilla/5.0 (Windows NT 5.1; rv:2.0b11) Gecko/20100101 Firefox/4.0b11",
    CURLOPT_FOLLOWLOCATION => 1,
    CURLOPT_AUTOREFERER => 1,
    CURLOPT_RETURNTRANSFER => 1,
    CURLOPT_CONNECTTIMEOUT => 5,
    CURLOPT_TIMEOUT => 20,
    CURLOPT_VERBOSE => 0,
    CURLOPT_SSL_VERIFYHOST => 0,
    CURLOPT_SSL_VERIFYPEER => 0,
    CURLOPT_COOKIEJAR => "cookie.txt",
    CURLOPT_COOKIEFILE => "cookie.txt"
    );  
    
  
    $ch = curl_init();
    curl_setopt_array($ch, $curl_opt);
    curl_setopt($ch, CURLOPT_URL, $site);
    curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "Content-Type: multipart/form-data; boundary=$boundary");
    curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
    curl_setopt($ch, CURLOPT_POSTFIELDS,$payload);
    curl_setopt($ch, CURLOPT_POST, TRUE);
    echo curl_exec ($ch);
    $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
 
print "Code: ".$http_code."<br>";
    //return $response;
}
keep the header unattended wont help .it is simply echoing the article form in browser.
but when i try to include this

PHP:
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "Content-Type: multipart/form-data; boundary=$boundary");
all i m getting is 400 bad request.

ANy suggestion ? please .....
 
Last edited:
That belongs into the header:
"Content-Type: multipart/form-data; boundary=$boundary"

And something else:
From LiveHTTPHeaders you posted:
Content-Type: multipart/form-data; boundary=---------------------------7469163454380
27 hyphens

your $boundary:
-----------------------------7665267813202
29 hyphens

I'm not sure thats the reason, but a had some issues with my Youtube Bot & multipart/form data too and i think i missed a hyphen somewhere and then it worked
 
Last edited:
Don't include any boundary information. Curl will handle that automatically handle that for you if you feed an array rather than a string into CURLOPT_POSTFIELDS. You shouldn't need CURLOPT_CUSTOMREQUEST.

Also try not including any extra header information except for the user agent. It's not necessary in 99% of situations.

Also try setting the values in $payload using = not => eg.
$payload['title'] = 'hello there';

Set CURLOPT_VERBOSE to 1 and echo the returned content in <pre> tags to get a better idea of what's going on.
 
here is as far i have got

PHP:
<?php
function curl_post2($site,$token){


$boundary = '---------------------------7469163454380';

$header = array (
                            'Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
                            'Accept-Language: en-us,en;q=0.5',
                            'Accept-Encoding: gzip, deflate',
                            'Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7',
                            'Keep-Alive: 115',
                            'Connection: keep-alive',
                            'Referer: http://mysite.com/?q=node%2Fadd%2Farticle&',
                            'Content-Type: multipart/form-data; boundary='.$boundary
                            
                              );
print_r($header);                            


$payload['title'] = "hellooooo there";
$payload['field_tags[und]'] = "hiiii";
$payload['body[und][0][summary]'] = "";
$payload['body[und][0][value]'] = "hello everybody";
$payload['body[und][0][format]'] = "filtered_html";
$payload['files[field_image_und_0]'] = "";
$payload['field_image[und][0][fid]'] = "0";
$payload['field_image[und][0][display]'] = "1";
$payload['changed'] = "";
$payload['form_build_id'] = $token[3];
$payload['form_token'] = $token[4];
$payload['form_id'] = "article_node_form";
$payload['menu[link_title]'] = "";
$payload['menu[description]'] = "";
$payload['menu[parent]'] = "main-menu:0";
$payload['menu[weight]'] = "0";
$payload['log'] = "";
$payload['path[alias]'] = "";
$payload['comment'] = "1";
$payload['name'] = "admin";
$payload['date'] = "";
$payload['status'] = "1";
$payload['promote'] = "1";
$payload['additional_settings__active_tab'] = "edit-menu";
$payload['op'] = "Save";

//print_r($data);

$curl_opt = array(
    CURLOPT_RETURNTRANSFER => true, 
    CURLOPT_HEADER => 1,
    CURLOPT_USERAGENT => "Mozilla/5.0 (Windows NT 5.1; rv:2.0b11) Gecko/20100101 Firefox/4.0b11",
    CURLOPT_FOLLOWLOCATION => 1,
    CURLOPT_AUTOREFERER => 1,
    CURLOPT_RETURNTRANSFER => 1,
    CURLOPT_CONNECTTIMEOUT => 5,
    CURLOPT_TIMEOUT => 20,
    CURLOPT_VERBOSE => 1,
    CURLOPT_SSL_VERIFYHOST => 0,
    CURLOPT_SSL_VERIFYPEER => 0,
    CURLOPT_COOKIEJAR => "cookie.txt",
    CURLOPT_COOKIEFILE => "cookie.txt"
    );  
    
  
 
    $ch = curl_init();
    curl_setopt_array($ch, $curl_opt);
    curl_setopt($ch, CURLOPT_URL, $site);
    //curl_setopt($ch, CURLOPT_HTTPHEADER, Array('Content-Type: multipart/form-data; boundary=---------------------------7469163454380' ));
    curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
    //curl_setopt($ch,CURLOPT_HTTPHEADER,array('Content-Type: multipart/form-data'));
    curl_setopt($ch, CURLOPT_POSTFIELDS,$payload);
    curl_setopt($ch, CURLINFO_HEADER_OUT, true);
    curl_setopt($ch, CURLOPT_POST, TRUE);
    
    $response = curl_exec ($ch);
    //print_r(curl_getinfo($ch));
   
    var_dump(curl_getinfo($ch,CURLINFO_HEADER_OUT));
    $http_code = curl_getinfo($ch, CURLINFO_HTTP_CODE);
    
    print "Code: ".$http_code."<br>";
    curl_close($ch);
    return $response;
    //return $response;
}

Still it is not working.

i check what header i am sending
and with var_dump(curl_getinfo($ch,CURLINFO_HEADER_OUT));
i m getting this otput

Code:
Array
(
    [0] => Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
    [1] => Accept-Language: en-us,en;q=0.5
    [2] => Accept-Encoding: gzip, deflate
    [3] => Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
    [4] => Keep-Alive: 115
    [5] => Connection: keep-alive
    [6] => Referer: http://mysite.com?q=node%2Fadd%2Farticle&
    [7] => Content-Type: multipart/form-data; boundary=---------------------------7469163454380
)
string(662) "POST /drupal/?q=node%2Fadd%2Farticle HTTP/1.1
User-Agent: Mozilla/5.0 (Windows NT 5.1; rv:2.0b11) Gecko/20100101 Firefox/4.0b11
Host: thinkbigtest.getbuzz.info
Cookie: SESS0933c7f6c3b533f5a8c8b5e0739b8056=UCE728Xn8-2cVaGgbZ1gdqgqCJ8C8Fgt6W7WydbMejM
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-us,en;q=0.5
Accept-Encoding: gzip, deflate
Accept-Charset: ISO-8859-1,utf-8;q=0.7,*;q=0.7
Keep-Alive: 115
Connection: keep-alive
Referer: http://mysite.com?q=node%2Fadd%2Farticle&
Content-Type: multipart/form-data; boundary=---------------------------7469163454380
Content-Length: 0

"
Code: 200<br>HTTP/1.1 200 OK
Date: Sun, 13 Mar 2011 07:48:53 GMT
Server: Apache
X-Powered-By: PHP/5.2.9
Expires: Sun, 19 Nov 1978 05:00:00 GMT
Cache-Control: no-cache, must-revalidate, post-check=0, pre-check=0
ETag: "1300002533"
X-Generator: Drupal 7 (http://drupal.org)
Last-Modified: Sun, 13 Mar 2011 07:48:53 GMT
Keep-Alive: timeout=2, max=100
Connection: Keep-Alive
Transfer-Encoding: chunked

i guess the problem is this
Content-Length: 0

why my content length is zero. i dont understand .is there any other way to send the array to postfield ?
 
found the solution i was framing the postdata wrong.
thankyou everyone :)
 
Back
Top