curl_formadd(3) | Library Functions Manual | curl_formadd(3) |
curl_formadd - add a section to a multipart form POST
#include <curl/curl.h> CURLFORMcode curl_formadd(struct curl_httppost **firstitem,
struct curl_httppost **lastitem, ...);
This function is deprecated. Use curl_mime_init(3) instead.
curl_formadd() is used to append sections when building a multipart form post. Append one section at a time until you have added all the sections you want included and then you pass the firstitem pointer as parameter to CURLOPT_HTTPPOST(3). lastitem is set after each curl_formadd(3) call and on repeated invokes it should be left as set to allow repeated invokes to find the end of the list faster.
After the lastitem pointer follow the real arguments.
The pointers firstitem and lastitem should both be pointing to NULL in the first call to this function. All list-data is allocated by the function itself. You must call curl_formfree(3) on the firstitem after the form post has been done to free the resources.
Using POST with HTTP 1.1 implies the use of a "Expect: 100-continue" header. You can disable this header with CURLOPT_HTTPHEADER(3) as usual.
First, there are some basics you need to understand about multipart form posts. Each part consists of at least a NAME and a CONTENTS part. If the part is made for file upload, there are also a stored CONTENT-TYPE and a FILENAME. Below, we discuss what options you use to set these properties in the parts you want to add to your post.
The options listed first are for making normal parts. The options from CURLFORM_FILE through CURLFORM_BUFFERLENGTH are for file upload parts.
If you pass a 0 (zero) for this option, libcurl calls strlen() on the contents to figure out the size. If you really want to send a zero byte content then you must make sure strlen() on the data pointer returns zero.
(Option added in 7.46.0)
followed by a long giving the length of the contents. Note that for CURLFORM_STREAM contents, this option is mandatory.
If you pass a 0 (zero) for this option, libcurl calls strlen() on the contents to figure out the size. If you really want to send a zero byte content then you must make sure strlen() on the data pointer returns zero.
The specified file needs to kept around until the associated transfer is done.
The given upload file has to exist in its full in the file system already when the upload starts, as libcurl needs to read the correct file size beforehand.
The specified file needs to kept around until the associated transfer is done.
When you have passed the struct curl_httppost pointer to curl_easy_setopt(3) (using the CURLOPT_HTTPPOST(3) option), you must not free the list until after you have called curl_easy_cleanup(3) for the curl handle.
See example below.
#include <string.h> /* for strlen */ static const char record[]="data in a buffer"; int main(void) {
CURL *curl = curl_easy_init();
if(curl) {
struct curl_httppost *post = NULL;
struct curl_httppost *last = NULL;
char namebuffer[] = "name buffer";
long namelength = strlen(namebuffer);
char buffer[] = "test buffer";
char htmlbuffer[] = "<HTML>test buffer</HTML>";
long htmlbufferlength = strlen(htmlbuffer);
struct curl_forms forms[3];
char file1[] = "my-face.jpg";
char file2[] = "your-face.jpg";
/* add null character into htmlbuffer, to demonstrate that
transfers of buffers containing null characters actually work
*/
htmlbuffer[8] = '\0';
/* Add simple name/content section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "name",
CURLFORM_COPYCONTENTS, "content", CURLFORM_END);
/* Add simple name/content/contenttype section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "htmlcode",
CURLFORM_COPYCONTENTS, "<HTML></HTML>",
CURLFORM_CONTENTTYPE, "text/html", CURLFORM_END);
/* Add name/ptrcontent section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "name_for_ptrcontent",
CURLFORM_PTRCONTENTS, buffer, CURLFORM_END);
/* Add ptrname/ptrcontent section */
curl_formadd(&post, &last, CURLFORM_PTRNAME, namebuffer,
CURLFORM_PTRCONTENTS, buffer, CURLFORM_NAMELENGTH,
namelength, CURLFORM_END);
/* Add name/ptrcontent/contenttype section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "html_code_with_hole",
CURLFORM_PTRCONTENTS, htmlbuffer,
CURLFORM_CONTENTSLENGTH, htmlbufferlength,
CURLFORM_CONTENTTYPE, "text/html", CURLFORM_END);
/* Add simple file section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "picture",
CURLFORM_FILE, "my-face.jpg", CURLFORM_END);
/* Add file/contenttype section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "picture",
CURLFORM_FILE, "my-face.jpg",
CURLFORM_CONTENTTYPE, "image/jpeg", CURLFORM_END);
/* Add two file section */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "pictures",
CURLFORM_FILE, "my-face.jpg",
CURLFORM_FILE, "your-face.jpg", CURLFORM_END);
/* Add two file section using CURLFORM_ARRAY */
forms[0].option = CURLFORM_FILE;
forms[0].value = file1;
forms[1].option = CURLFORM_FILE;
forms[1].value = file2;
forms[2].option = CURLFORM_END;
/* Add a buffer to upload */
curl_formadd(&post, &last,
CURLFORM_COPYNAME, "name",
CURLFORM_BUFFER, "data",
CURLFORM_BUFFERPTR, record,
CURLFORM_BUFFERLENGTH, sizeof(record),
CURLFORM_END);
/* no option needed for the end marker */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "pictures",
CURLFORM_ARRAY, forms, CURLFORM_END);
/* Add the content of a file as a normal post text value */
curl_formadd(&post, &last, CURLFORM_COPYNAME, "filecontent",
CURLFORM_FILECONTENT, ".bashrc", CURLFORM_END);
/* Set the form info */
curl_easy_setopt(curl, CURLOPT_HTTPPOST, post);
curl_easy_perform(curl);
curl_easy_cleanup(curl);
curl_formfree(post);
} }
Deprecated in 7.56.0. Before this release, field names were allowed to contain zero-valued bytes. The pseudo-filename "-" to read stdin is discouraged although still supported, but data is not read before being actually sent: the effective data size can then not be automatically determined, resulting in a chunked encoding transfer. Backslashes and double quotes in field and file names are now escaped before transmission.
0 means everything was OK, non-zero means an error occurred corresponding to a CURL_FORMADD_* constant defined in <curl/curl.h>
curl_easy_setopt(3), curl_formfree(3), curl_mime_init(3)
November 4, 2020 | libcurl 7.77.0 |