Работая с файлами в NodeJS, можно столкнуться с проблемой — полученные массивы с именами файлов из директорий сайта(приложения) могут содержать символы «вопроса в ромбе«.
То есть, если у нас файлы на сервере именуются не в латинице, то могут начаться проблемы при переезде сайта в другую систему (на другой хост).
Методы readdir() или readdirSync() могут перестать выдавать корректный результат.
Как это выглядит?
В чём проблема?
Такая беда неизбежно встретится в Debian (Linux) сервере, если файлы со старого хоста двигаются транзитом в новый хост, через ОС Windows. Радует в этой ситуации только то, что NodeJS тут не причём. NodeJS доверяет операционной системе Debian (Linux) во многих вопросах, поэтому иногда не пытается «умничать» и что-то менять на лету.
Исторически в IT так сложилось, что чем дольше живёт человечество и чем больше появляется новых языков, тем крупнее должна быть «символьная» база, которая хранит в себе все возможные наборы символов разных языков (алфавитов).
Когда всё только начиналось, тогда были только 256 символов — (цифры, латинские буквы, знаки препинания). Этот набор послужил появлению такого понятия как «кодировка«. Каждому символу присваивался свой уникальный числовой код.
Операционных систем становилось больше, кодировок становилось больше. В результате появились проблемы с общением разных систем друг с другом. Нужно было решить проблему на международном уровне.
Сегодня только русский язык застолбил для себя 66 символов своего алфавита. (33 строчные, 33 заглавные). Но есть ещё и другие языки. Появились всякие смайлики, эмодзи и прочее.
Сегодня все символы планеты упакованы в одну систему. Она называется ЮНИКОД. По сути в ЮНИКОДе учли все предыдущие несостыковки. Но…
Но ещё продолжают существовать старые системы, которые участвуют в сетевом обмене файлами в сети интернет. И может оказаться такая нехорошая ситуация, когда какая-то операционная система захочет перекодировать имена файлов к какую-то старую кодировку. И естественно не скажет об этом. В результате разработчик получает неработающее приложение и у него начинает болеть голова от этой проблемы.
Решение
Если беда с именами файлов уже случилась, то нужно срочно менять их кодировки на новом хосте. Менять кодировки имён, а не самого содержимого файлов.
Так как Debian (Linux) уже вовсю работает в кодировке UTF-8, то и приводить все имена файлов мы будем к UTF-8. Напомню, что UTF-8 — это часть ЮНИКОДа.
В Debian (Linux) сервере это можно сделать при помощи программы «convmv«:
convmv -r -f cp1251 -t utf-8 /var/www/tabletka.efim360.ru/bad
- cp1251 — Это кодировка из которой хотим сделать UTF-8. Это кодировка, в которую были приведены имена файлов в Windows. Но в вашем случае может быть что-то иное («koi8-r» или «iso-8859-15» или ещё чего)
- utf-8 — Это кодировка, в которую мы приводим имена файлов.
- /var/www/tabletka.efim360.ru/bad — Это путь до директории, в которой лежат файлы с русскими именами в неправильной кодировке
Вызов команды будет выводить потенциальные пути до файлов, а также варианты перекодировки.
Мы зрительно наблюдаем за ходом процесса и в конце нам говорится, что изменения не внесены.
Если нас текущая перекодировка устраивает, тогда мы можем выполнить замену «плохой кодировки» на «хорошую кодировку». Для этого просто дописываем в команду выражение «—notest»:
convmv -r --notest -f cp1251 -t utf-8 /var/www/tabletka.efim360.ru/bad
И после этого кодировка имён файлов будет исправлена навечно на новом хосте.
Мы получаем запись вида: «Ready! I converted 15683 files in 4 seconds.»
Теперь возвращаемся на сайт и перезагружаем страницу.
NodeJS тут же подхватит правильную кодировку из Debian и методы readdir() или readdirSync() смогут корректно заполнить массив строками имён файлов в правильной кодировке с русскими символами.