J'ai un tas de répertoires et sous-répertoires qui contiennent des fichiers avec des caractères spéciaux, comme ce fichier:
robbie@phil:~$ ls test�sktest.txt
test?sktest.txt
Find révèle une séquence d'échappement:
robbie@phil:~$ find test�sktest.txt -ls
424512 4000 -rwxr--r-x 1 robbie robbie 4091743 Jan 26 00:34 test\323sktest.txt
La seule raison pour laquelle je peux même taper leurs noms sur la console est à cause de la complétion des onglets. Cela signifie également que je peux les renommer manuellement (et supprimer le caractère spécial).
J'ai mis LC_ALL sur UTF-8, ce qui ne semble pas aider (pas non plus sur un nouveau shell):
robbie@phil:~$ echo $LC_ALL
en_US.UTF-8
Je me connecte à la machine en utilisant ssh depuis mon mac. C'est une installation Ubuntu:
robbie@phil:~$ cat /etc/lsb-release
DISTRIB_ID=Ubuntu
DISTRIB_RELEASE=7.10
DISTRIB_CODENAME=gutsy
DISTRIB_DESCRIPTION="Ubuntu 7.10"
Shell est Bash, TERM est défini sur xterm-color.
Ces fichiers existent depuis un certain temps et n'ont pas été créés à l'aide de cette installation d'Ubuntu. Je ne sais donc pas quels étaient les paramètres d'encodage du système.
J'ai essayé des choses dans le sens de:
find . -type f -ls | sed 's/[^a-zA-Z0-9]//g'
Mais je ne trouve pas de solution qui fasse tout ce que je veux:
- Identifiez tous les fichiers qui ont des caractères non affichables (ce qui précède ignore beaucoup trop)
- Pour tous ces fichiers dans une arborescence de répertoires (récursivement), exécutez mv oldname newname
- En option, la possibilité de translittérer des caractères spéciaux tels que ä en a (non requis, mais serait génial)
OU
- Afficher correctement tous ces fichiers (et aucune erreur dans les applications lors de la tentative d'ouverture)
J'ai des morceaux, comme itérer sur tous les fichiers et les déplacer, mais identifier les fichiers et les formater correctement pour la commande mv semble être la partie difficile.
Toute information supplémentaire expliquant pourquoi ils ne s'affichent pas correctement ou comment "deviner" le codage correct est également la bienvenue. (J'ai essayé convmv mais il ne semble pas faire exactement ce que je veux: http://j3e.de/linux/convmv/ )
Réponses:
Je suppose que vous voyez ce
�
caractère invalide parce que le nom contient une séquence d'octets qui n'est pas UTF-8 valide. Les noms de fichiers sur les systèmes de fichiers Unix typiques (y compris le vôtre) sont des chaînes d'octets, et c'est aux applications de décider du codage à utiliser. De nos jours, il y a une tendance à utiliser UTF-8, mais ce n'est pas universel, en particulier dans les environnements locaux qui ne pourraient jamais vivre avec de l'ASCII ordinaire et qui utilisaient d'autres encodages avant même que l'UTF-8 n'existe.Essayez
LC_CTYPE=en_US.iso88591 ls
de voir si le nom de fichier a du sens dans ISO-8859-1 (latin-1). Si ce n'est pas le cas, essayez d'autres paramètres régionaux. Notez que seul leLC_CTYPE
paramètre régional est important ici.Dans un environnement local UTF-8, la commande suivante vous montrera tous les fichiers dont le nom n'est pas UTF-8 valide:
Vous pouvez vérifier si elles ont plus de sens dans un autre lieu avec recodage ou iconv :
Une fois que vous avez déterminé qu'un certain nombre de noms de fichiers sont dans un certain encodage (par exemple latin1), une façon de les renommer est
Cela utilise la commande perl rename disponible sur Debian et Ubuntu. Vous pouvez le transmettre
-n
pour montrer ce qu'il ferait sans renommer réellement les fichiers.la source
grep [^[:print:]]
rechercher des caractères non imprimables. Mais je viens de tester avec GNU grep et les séquences UTF-8 invalides ne sont pas capturées[^[:print:]]
(ce qui est logique car ce ne sont pas des caractères non imprimables, ce ne sont pas du tout des caractères). J'ai édité mon article avec un moyen plus long de saisir les lignes avec des séquences utf8 invalides. Notez que j'ai également fixé la direction des exemplesrecode
eticonv
.Je sais que c'est une vieille question mais j'ai cherché toute la nuit une solution similaire. J'ai trouvé quelques conseils utiles mais ils n'ont pas fait exactement ce dont j'avais besoin, j'ai donc dû en mélanger quelques-uns pour obtenir le résultat correct que je cherchais
pour supprimer simplement les caractères spéciaux et les remplacer par un point (.)
à utiliser dans un cronjob j'ai fait ce qui suit pour exécuter chaque minute
J'espère que quelqu'un trouve cela utile car cela a fait ma journée :)
la source
`…`
pour$(…)
- voir ceci , ceci et ceci . (2) Vous devez toujours citer les références de vos variables shell (par exemple,"$f"
) sauf si vous avez une bonne raison de ne pas le faire et que vous êtes sûr de savoir ce que vous faites. Cela s'applique même àecho "$f" | sed …
. Elle s'applique également à l' expression entière$(…)
(ou`…`
); à savoirmv "$f" "$(echo "$f" | sed "…")"
. … (Suite)mv
--
"$f" …
-
Maintenant, lorsque vous savez quel encodage est utilisé pour les noms de fichiers sur l'extrémité distante ("latin1" - selon les commentaires de la première réponse), vous pouvez également suivre la deuxième façon - exécuter un terminal local et ssh dans un tel manière que les noms de fichiers distants s'affichent correctement (plutôt que la première façon: les renommer) .
Comme moi , vous pouvez démarrer un terminal localement qui fonctionnerait dans cet encodage spécial, peut-être comme ceci:
LC_ALL = en_US.latin1 xvt &
xvt
représente votre programme de terminal.Peut-être que les paramètres régionaux existants sont appelés
en_US.iso88591
, et nonen_US.latin1
, comme je l'ai supposé.la source
Cela ne répond pas aux exigences de masse, mais je viens d'avoir un problème similaire où j'avais plusieurs versions d'un fichier avec des noms similaires qui ne différaient que par un seul caractère étrange. Malheureusement, cela signifiait que je ne pouvais pas renommer les contrevenants à l'aide de l'astuce générique que j'utilise habituellement.
À la fin, j'ai utilisé Filezilla pour me connecter en tant que client SFTP, j'ai parcouru les fichiers et les ai renommés à l'aide de l'interface graphique. Filezilla a très bien géré les caractères douteux.
la source