Предоставляет ли метод fetch ту же функциональность, что и FileReader? - PullRequest
0 голосов
/ 06 января 2019

Мне удалось прочитать байтовый текстовый файл и изменить кодировку с windows-1251 на Unicode для файла, загруженного с компьютера конечного пользователя через элемент input и FileReader. Теперь я хочу сделать то же самое для файла с моего сервера через fetch. Возможно ли это сделать? (fetch будет на странице, обслуживаемой через HTTP, и URL будет относительным, например, fetch("raw/graph_tab.txt") & mdash; я не пытаюсь прочитать файл непосредственно с компьютера конечного пользователя, как это было с полем input и FileReader).

Куски рабочего кода ( 'windows-1251.js' библиотека создана Матиасом Биненсом):

<input type="file" id="file"/>
<script type="text/javascript">
        document.getElementById("file").addEventListener("change", readFile, false);

        function readFile (evt) {
            var files = evt.target.files;
            var file = files[0];           
            var reader = new FileReader();
            reader.onload = function(event) {
                console.log(windows1251.decode(event.target.result));            
            }};

Ответы [ 2 ]

0 голосов
/ 07 января 2019

Вам вообще не нужно делать это преобразование: вы используете веб-сервер, который явно не правильно определяет кодировку файла. Он должен правильно идентифицировать его в возвращаемом заголовке Content-Type (например, Content-Type: text/plain; charset=windows-1251). См. эту статью от собственного Джоэла Спольски из SO для получения дополнительной информации.

Если вы не можете сделать это по какой-то причине: вы можете прочитать файл в двоичном виде и получить ArrayBuffer для него через arrayBuffer в ответе fetch:

fetch("raw/graph_tab.txt")
.then(response => {
    if (!response.ok) {
        throw new Error(response.status);
    }
    return response.arrayBuffer();
})
.then(buffer => {
    // ...convert it here...
})
.catch(error => {
    // Handle/report error
});

Итак, вопрос в том, что мы делаем для ...convert it here.... :-) Библиотека, на которую вы ссылаетесь, ожидает получить «байтовую строку», которая, как я предполагаю, такая же, как вы получили бы из readAsBinaryString метода FileReader. Если это так, вы можете преобразовать ArrayBuffer в этот формат следующим образом:

const str = new Uint8Array(buffer).map(byte => String.fromCharCode(byte)).join("");

Итак:

fetch("raw/graph_tab.txt")
.then(response => {
    if (!response.ok) {
        throw new Error(response.status);
    }
    return response.arrayBuffer();
})
.then(buffer => {
    const str = new Uint8Array(buffer).map(byte => String.fromCharCode(byte)).join("");
    console.log(windows1251.decode(str));
})
.catch(error => {
    // Handle/report error
});
0 голосов
/ 07 января 2019

Если вы хотите иметь параметр encoding метода FileReader.readAsText(Blob, encoding), то вы должны установить charset параметр в заголовке Content-Type вашего ответа.

Если это невозможно по какой-либо причине, вам придется использовать объект Response для BLOB-объекта, используя его Body.blob () метод, а затем передать полученный Blob в FileReader.

В противном случае, нет, даже если объект Response имеет методы, схожие с методами FileReader , метод text() не обеспечивает кодировку опция ...

...