среда, 17 января 2018 г.

Памятка: конвертация исходников CP-1251 в UTF-8 (Linux)

В долгоживущем проекте, который уже перенесли на линукс малая часть исходников была в кодировке CP-1251 (Windows 1251). А основная часть в кодировке UTF-8. Требовалось без затей перекодировать в UTF-8 указанную малую часть.

Выполнили следующим скриптом:

for incorrect_file in $(for file in $(find $(pwd) -type f | grep -E "*\.h$|*\.c$|*\.hpp$|*\.cpp$"); do file -i ${file}; done | grep charset=iso-8859-1 | awk 'BEGIN{FS=":"}{print $1}'); do echo ${incorrect_file}; iconv -f cp1251 -t utf-8 ${incorrect_file} -o ${incorrect_file}; done

Более читаемая форма:

files=$(find $(pwd) -type f | grep -E "*\.h$|*\.c$|*\.hpp$|*\.cpp$"); \
incorrect_files=$( for_ file in ${files}; do \
                                  file -i ${_file}; \
                              done | \
                              grep charset=iso-8859-1 | \
                              awk 'BEGIN{FS=":"}{print $1}'); \
for incorrect_file in ${incorrect_files} do \
    echo ${incorrect_file}; \
    iconv -f cp1251 -t utf-8 ${incorrect_file} -o ${incorrect_file}; \
done

Разбор:
  • find $(pwd) -type f - ищет рекурсивно все файлы вглубь относительно текущей директории
  • grep -E "\.h$|\.c$|\.hpp$|.\cpp$" - фильтр - выводит в stdout только файлы с раширениями: .h .c .hpp .cpp
  • file -i ${file} - выдаёт информацию о файле, включая его кодировку
  • grep charset=iso-8859-1 - фильтр - выводит в stdout только информацию по файлам, имеющим указанную кодировку. Суть в том, что для файла с фактической кодировкой CP1251 команда file  -i выводит информацию, что кодировка iso-8859-1.
  • awk 'BEGIN {FS=":"}{print $1}' из отфильтрованной строки команды file -i выводит только имя файла.
  • iconv -f cp1251 -t utf-8 ${incorrect_file} -o ${incorrect_file} - собственно перекодирует файл из кодировки CP1251 в UTF-8.

Комментариев нет:

Отправить комментарий