application/x-www-form-urlencoded или multipart/form-data?
В HTTP има два начина за изпращане на данни: application/x-www-form-urlencoded
и multipart/form-data
. Разбирам, че повечето браузъри могат да качват файлове само ако се използва multipart/form-data
. Има ли някакви допълнителни указания кога да се използва един от типовете кодиране в контекста на API (без участието на браузър)? Това може да се основава например на:
- размер на данните
- наличие на не-ASCII символи
- наличие на (некодирани) двоични данни
- необходимост от прехвърляне на допълнителни данни (като име на файл)
Досега не съм открил официални указания в интернет относно използването на различните типове съдържание.
1262
3
TL;DR
Обобщение; ако трябва да предадете двоични (неалфанумерични) данни (или значителен по размер полезен товар), използвайте
multipart/form-data
. В противен случай използвайтеapplication/x-www-form-urlencoded
.Споменатите от вас MIME типове са двата хедъра
Content-Type
за HTTP POST заявки, които потребителските агенти (браузърите) трябва да поддържат. Целта и на двата типа заявки е да се изпрати списък от двойки име/стойност към сървъра. В зависимост от вида и обема на предаваните данни единият от методите ще бъде по-ефективен от другия. За да разберете защо, трябва да разгледате какво прави всеки от тях под капака.При
application/x-www-form-urlencoded
тялото на HTTP съобщението, изпратено до сървъра, е по същество един огромен низ от заявки - двойките име/стойност са разделени с амперсанд (&
), а имената са отделени от стойностите със символа за равенство (=
). Пример за това е:MyVariableOne=СтойностOne&MyVariableTwo=СтойностTwo
Според спецификацията:
Това означава, че за всеки небуквен байт, който съществува в една от нашите стойности, ще са необходими три байта, за да бъде представен. За големи двоични файлове утрояването на полезния товар ще бъде крайно неефективно.
Ето къде се появява
multipart/form-data
. При този метод за предаване на двойки име/стойност всяка двойка се представя като "part" в MIME съобщение (както е описано в други отговори). Частите се разделят с определен граничен низ (избран специално така, че този граничен низ да не се среща в нито един от полезните товари на "стойността"). Всяка част има свой собствен набор от MIME заглавия катоContent-Type
и особеноContent-Disposition
, които могат да дадат на всяка част нейното "име." Стойностната част на всяка двойка име/стойност е полезният товар на всяка част от MIME съобщението. Спецификацията на MIME ни дава повече възможности при представянето на полезния товар на стойността - можем да изберем по-ефективно кодиране на двоичните данни, за да спестим честотна лента (напр. база 64 или дори сурова двоица).Защо да не използвате
multipart/form-data
през цялото време? За кратки буквено-цифрови стойности (като повечето уеб формуляри) режийните разходи за добавяне на всички заглавия на MIME ще надхвърлят значително спестяванията от по-ефективно двоично кодиране.Не мисля, че HTTP се ограничава до POST в мултипарт или x-www-form-urlencoded. Заглавието [Content-Type Header][1] е ортогонално на метода HTTP POST (можете да попълните MIME типа, който ви е подходящ). Такъв е случаят и с типичните уеб приложения, базирани на HTML представяне (напр. json payload стана много популярен за предаване на полезен товар за ajax заявки).
Що се отнася до Restful API по HTTP, най-популярните типове съдържание, с които съм се сблъсквал, са application/xml и application/json.
application/xml:
Съгласен съм с много от казаното от Мануел. Всъщност коментарите му се отнасят до тази URL...
http://www.w3.org/TR/html401/interact/forms.html#h-17.13.4
... в който се казва:
За мен обаче въпросът се свежда до поддръжката на инструменти/рамки.
Ако имате ясна представа за потребителите си и за това как те ще използват вашия API, това ще ви помогне да вземете решение. Ако затруднявате качването на файлове за потребителите на API, те ще се отдръпнат, а вие ще изразходвате много време, за да ги поддържате.
Второстепенно значение за това ще има поддръжката на инструментите, с които разполагате за писане на вашия API, и колко лесно е за вас да приспособите един механизъм за качване на файлове към друг.