Qual è il modo giusto di POST multipart / form-data usando curl?


164

Ho usato questa sintassi per pubblicare un file insieme ad alcuni parametri:

curl -v -include --form "key1=value1" --form upload=localfilename URL

Il file ha una dimensione di circa 500 KB. Innanzitutto, vedo che la lunghezza del contenuto è 254 sul lato di trasmissione. Successivamente la lunghezza del contenuto della risposta del server è 0. Dove sbaglio?

Ecco la traccia completa del comando.

* Couldn't find host xxx.xxx.xxx.xxx in the _netrc file; using defaults
* About to connect() to xxx.xxx.xxx.xxx port yyyy (#0)
*   Trying xxx.xxx.xxx.xxx...
* Adding handle: conn: 0x4b96a0
* Adding handle: send: 0
* Adding handle: recv: 0
* Curl_addHandleToPipeline: length: 1
* - Conn 0 (0x4b96a0) send_pipe: 1, recv_pipe: 0
* Connected to xxx.xxx.xxx.xxx (xxx.xxx.xxx.xxx) port yyyy (#0)
* POST /zzzzzz/UploadFile HTTP/1.1
* User-Agent: curl/7.32.0
* Host: xxx.xxx.xxx.xxx:yyyy
* Accept: */*
* Content-Length: 254
* Expect: 100-continue
* Content-Type: multipart/form-data; boundary=------------------------948a6137eef50079
*
* HTTP/1.1 100 Continue
* HTTP/1.1 100 Continue

* HTTP/1.1 200 OK
* HTTP/1.1 200 OK
* Server Apache-Coyote/1.1 is not blacklisted
* Server: Apache-Coyote/1.1
* Server: Apache-Coyote/1.1
* Added cookie JSESSIONID="C1D7DD042E250211D9DEA82688876F88" for domain xxx.xxx.xxx.xxx, path /zzzzz/, expire 0
* Set-Cookie: JSESSIONID=C1D7DD042E250211D9DEA82688876F88; Path=/zzzzzz/;
* HttpOnly
* Set-Cookie: JSESSIONID=C1D7DD042E250211D9DEA82688876F88; Path=/zzzzzz/; HttpOnly
* Content-Type: text/html;charset=ISO-8859-1
Content-Type: text/html;charset=ISO-8859-1
* Content-Length: 0
* Content-Length: 0
* Date: Tue, 01 Oct 2013 11:54:24 GMT
* Date: Tue, 01 Oct 2013 11:54:24 GMT
* Connection #0 to host xxx.xxx.xxx.xxx left intact

Risposte:


254

La sintassi seguente lo risolve per te:

curl -v -F key1=value1 -F upload=@localfilename URL

che dire di Windows e curl.exe?
Piotr

1
che dire di più allegati?
hellboy,

8
Funziona esattamente allo stesso modo su Windows e supporta più "allegati" / file: basta aggiungere più istanze -F!
Daniel Stenberg

Questa risposta ha un buon esempio di caricamento di più file. stackoverflow.com/questions/11599957/...
bmoran

Questo funziona sul ricciolo non abbiamo bisogno di aggiungere qualcosa di simile:-H 'content-type: multipart/form-data; boundary=----WebKitFormBoundary7MA4YWxkTrZu0gW'
Emily

19

per caricare un file usando curl in Windows ho scoperto che il percorso richiede doppie virgolette di escape

per esempio

curl -v -F 'upload=@\"C:/myfile.txt\"' URL

1
Questa risposta mi ha aiutato molto. Anche se nel mio caso non dovrei scappare ", nel mio caso su Mac dovrei inviarlo come curl -X POST -F key1=value1 -F 'image=@"/Users/ivkremer/Downloads/file name.jpg"';
Ivkremer,

nel mio caso - ho avuto un trasferimento riuscito senza virgolette: curl -v -F file=@/Users/path/to/file/testq.jpg 192.168.0.101:8080/upload-image
chatlanin

Nel mio caso in Windows, non ho potuto usare le virgolette singole e ho dovuto usare virgolette doppie in questo modocurl -F "filename=@\"C:\temp\file.jpg\"" https://someurl.com
Beems

5

Questo è ciò che ha funzionato per me

curl -F file=@filename URL

1

Ho avuto difficoltà a inviare una richiesta PUT HTTP multipart con curlun back-end Java. Ho semplicemente provato

curl -X PUT URL \
   --header 'Content-Type: multipart/form-data; boundary=---------BOUNDARY' \
   --data-binary @file

e il contenuto del file era

-----------BOUNDARY
Content-Disposition: form-data; name="name1"
Content-Type: application/xml;version=1.0;charset=UTF-8

<xml>content</xml>
-----------BOUNDARY
Content-Disposition: form-data; name="name2"
Content-Type: text/plain

content
-----------BOUNDARY--

ma ho sempre avuto un errore che il confine era errato. Dopo un po 'di debug del backend Java, ho scoperto che l'implementazione Java stava aggiungendo \r\n--un prefisso al limite, quindi dopo aver cambiato il mio file di input in

                          <-- here's the CRLF
-------------BOUNDARY       <-- added '--' at the beginning
...
-------------BOUNDARY       <-- added '--' at the beginning
...
-------------BOUNDARY--     <-- added '--' at the beginning

tutto funziona bene!

tl; dr

Aggiungi una nuova riga (CRLF \r\n) all'inizio del contenuto di confine multipart e-- all'inizio dei confini e riprova.

Forse stai inviando una richiesta a un back-end Java che necessita di queste modifiche al confine.


Durante la copia dei dati POST con la console Web di Firefox, ho anche notato che stava usando \ninvece di \r\n. Anche mitmproxy copia come stava usando cURL, \nquindi ho dovuto copiare la richiesta non elaborata con mitmproxy. Ho visto con hexdump che stava usando il codice esadecimale 0Ainvece di 0D 0A.
Baptx

la \r\nè richiesto. Guarda tools.ietf.org/html/rfc2046#section-5.1.1 pagina 19.
Adam Zahran

0

Su Windows 10, arricciare 7.28.1 all'interno di PowerShell, ho trovato quanto segue per me:

$filePath = "c:\temp\dir with spaces\myfile.wav"
$curlPath = ("myfilename=@" + $filePath)
curl -v -F $curlPath URL
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.