mirror of
https://github.com/denoland/deno.git
synced 2024-11-25 15:29:32 -05:00
fix(fetch): implement newline normalization and escapes in the multipart/form-data serializer (#10832)
This commit is contained in:
parent
55e962b688
commit
03184aeabb
2 changed files with 36 additions and 13 deletions
|
@ -323,11 +323,13 @@
|
|||
filename,
|
||||
type,
|
||||
) {
|
||||
const escapedField = this.#headerEscape(field);
|
||||
const escapedFilename = this.#headerEscape(filename, true);
|
||||
/** @type {[string, string][]} */
|
||||
const headers = [
|
||||
[
|
||||
"Content-Disposition",
|
||||
`form-data; name="${field}"; filename="${filename}"`,
|
||||
`form-data; name="${escapedField}"; filename="${escapedFilename}"`,
|
||||
],
|
||||
["Content-Type", type || "application/octet-stream"],
|
||||
];
|
||||
|
@ -340,7 +342,10 @@
|
|||
*/
|
||||
#writeFieldHeaders(field) {
|
||||
/** @type {[string, string][]} */
|
||||
const headers = [["Content-Disposition", `form-data; name="${field}"`]];
|
||||
const headers = [[
|
||||
"Content-Disposition",
|
||||
`form-data; name="${this.#headerEscape(field)}"`,
|
||||
]];
|
||||
return this.#writeHeaders(headers);
|
||||
}
|
||||
|
||||
|
@ -351,7 +356,7 @@
|
|||
*/
|
||||
#writeField(field, value) {
|
||||
this.#writeFieldHeaders(field);
|
||||
this.chunks.push(encoder.encode(value));
|
||||
this.chunks.push(encoder.encode(this.#normalizeNewlines(value)));
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -363,6 +368,32 @@
|
|||
this.#writeFileHeaders(field, value.name, value.type);
|
||||
this.chunks.push(value[_byteSequence]);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param {string} string
|
||||
* @returns {string}
|
||||
*/
|
||||
#normalizeNewlines(string) {
|
||||
return string.replace(/\r(?!\n)|(?<!\r)\n/g, "\r\n");
|
||||
}
|
||||
|
||||
/**
|
||||
* Performs the percent-escaping and the normalization required for field
|
||||
* names and filenames in Content-Disposition headers.
|
||||
* @param {string} name
|
||||
* @param {boolean} isFilename Whether we are encoding a filename. This
|
||||
* skips the newline normalization that takes place for field names.
|
||||
* @returns {string}
|
||||
*/
|
||||
#headerEscape(name, isFilename = false) {
|
||||
if (!isFilename) {
|
||||
name = this.#normalizeNewlines(name);
|
||||
}
|
||||
return name
|
||||
.replaceAll("\n", "%0A")
|
||||
.replaceAll("\r", "%0D")
|
||||
.replaceAll('"', "%22");
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -990,16 +990,8 @@
|
|||
},
|
||||
"file": {
|
||||
"File-constructor.any.html": true,
|
||||
"send-file-formdata-controls.any.html": [
|
||||
"Upload file-for-upload-in-form-LF-[\n].txt (ASCII) in fetch with FormData",
|
||||
"Upload file-for-upload-in-form-LF-CR-[\n\r].txt (ASCII) in fetch with FormData",
|
||||
"Upload file-for-upload-in-form-CR-[\r].txt (ASCII) in fetch with FormData",
|
||||
"Upload file-for-upload-in-form-CR-LF-[\r\n].txt (ASCII) in fetch with FormData"
|
||||
],
|
||||
"send-file-formdata-punctuation.any.html": [
|
||||
"Upload file-for-upload-in-form-QUOTATION-MARK-[\"].txt (ASCII) in fetch with FormData",
|
||||
"Upload \"file-for-upload-in-form-double-quoted.txt\" (ASCII) in fetch with FormData"
|
||||
],
|
||||
"send-file-formdata-controls.any.html": true,
|
||||
"send-file-formdata-punctuation.any.html": true,
|
||||
"send-file-formdata-utf-8.any.html": true,
|
||||
"send-file-formdata.any.html": true
|
||||
},
|
||||
|
|
Loading…
Reference in a new issue