-
Notifications
You must be signed in to change notification settings - Fork 545
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fetch
fails on ByteString
header with non-ASCII chars
#1317
Comments
The online link for a quick look:
But headers are not UTF-8 characters.
It's correct. UPD: Oops, these links requires an account). import {fetch as undiciFetch} from "undici";
import nodeFetch from "node-fetch";
// const headers = {
// "cookie": "..." // It's required
// };
const url = "https://xenforo.com/community/attachments/¡«£»ÿ-png.266785/";
const nodeFetchCdHeader = (await nodeFetch(url, {headers})).headers.get("content-disposition");
const undiciFetchCdHeader = (await undiciFetch(url, {headers})).headers.get("content-disposition");
const toString = bStr => Buffer.from(bStr, "binary").toString("utf8");
console.log(nodeFetchCdHeader.length); // OK (86)
console.log(nodeFetchCdHeader); // OK (..."¡«£»ÿ.png"...)
console.log(toString(nodeFetchCdHeader)); // OK (..."¡«£»ÿ.png"...)
console.log(undiciFetchCdHeader.length); // Not OK (81)
console.log(undiciFetchCdHeader); // Not OK (..."¡«£»ÿ.png"...)
console.log(toString(undiciFetchCdHeader)); // Not OK (..."�����.png"...)
const url2 = "https://xenforo.com/community/attachments/rock-roll-音楽-«🎵🎶»-png.266784/";
await nodeFetch(url2, {headers}); // OK
await undiciFetch(url2, {headers}); // Error Also you can test it in the browser's console: function bSrt2Str(bString) {
return new TextDecoder().decode(binaryStringToArrayBuffer(bString));
}
function binaryStringToArrayBuffer(binaryString) {
const u8Array = new Uint8Array(binaryString.length);
for (let i = 0; i < binaryString.length; i++) {
u8Array[i] = binaryString.charCodeAt(i);
}
return u8Array;
}
// on https://xenforo.com/community/attachments/¡«£»ÿ-png.266785/ page
const fetchCdHeader = (await fetch("")).headers.get("Content-Disposition");
console.log(fetchCdHeader.length); // (86)
console.log(fetchCdHeader); // (..."¡«£»ÿ.png"...)
console.log(bSrt2Str(fetchCdHeader)); // (..."¡«£»ÿ.png"...) |
Lines 1950 to 1951 in a211b18
The fix: const key = headersList[n + 0].toString('binary')
const val = headersList[n + 1].toString('binary') Since Thx to Line 147 in e66422c
|
@AlttiRi would you like to send your fix as a PR? |
The additional note about
Setting header with and non- It's looks strange. Just a note. |
Also you can take a look at this issue: |
Please see my comment on nodejs/node#42579 - I think they also apply for undici. |
Not for this issue, definitely. This issue is about that |
So, what? I just can't use undici.fetch in my media downloader because of:
(And because of possible wrong names too.) BTW, my pull request was automatically removed because of I have archived the forked repo?
UPD. |
What does UPD mean? Given you are not interested in fixing this, could we close the issue then? |
"Update"/"Edit". (I have appended the additional information by post editing)
I'm very interested in fixing this. This bug is critical. I just removed my fork because my pull request has disappeared here from the list (that was unexpectedly for me). Also I'm not interesting in a "contribution" by sending pull requests. |
Oh, was it fixed? Finally, I will be able to use this library in a downloader program. BTW, a real life (with no authentication needed) URL for tests: (Web Archive is just for URL safety, it correctly returns the same headers as the original service (Mediafire).) Currently 5.8.0 fails on this URL:
I'm waiting for the next release with this bug fixed. |
5.10.0 works as expected: import {fetch} from "undici";
// Use this persistent Web Archive URL,
// or take the direct URL for your IP here:
// https://www.mediafire.com/file/gphbkhjqqx8aesq/%E2%9C%85%E2%8F%B3%F0%9F%94%A5%F0%9F%92%A7.txt
// from the "DOWNLOAD (14B)" button element
const url = "https://web.archive.org/web/1/https://download1084.mediafire.com/z7j89kwbqrzg/gphbkhjqqx8aesq/✅⏳🔥💧.txt";
const resp = await fetch(url);
if (!resp.ok) { // status === 503 if "Internet Archive services are temporarily offline."
throw "status: " + resp.status;
}
const cdHeader = Buffer.from(resp.headers.get("content-disposition"), "latin1").toString();
const {filename} = cdHeader.match(/filename="(?<filename>.+)"/)?.groups || {};
console.log(filename);
console.log(filename === "✅⏳🔥💧.txt"); // true
console.log(await resp.text() === "✅⏳🔥💧"); // true |
fetch
fails onByteString
header if the header contains char codes128
and over.The code:
server.js
client.js
util.js
Result
The expected result
Deno:
Browser console:
Browser:
Deno, with 2 last lines uncommented:
BTW, HTTP headers are
ByteString
(BinaryString).https://developer.mozilla.org/en-US/docs/Web/API/DOMString/Binary
https://webidl.spec.whatwg.org/#idl-ByteString
Hm... someone have deleted the article about
ByteString
:https://web.archive.org/web/20210608032047/https://developer.mozilla.org/en-US/docs/Web/API/ByteString
and replaced
ByteString
withString
:https://web.archive.org/web/20210731105134/https://developer.mozilla.org/en-US/docs/Web/API/Headers/get
That's not OK.
The text was updated successfully, but these errors were encountered: