Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

1. Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Dev 2 pe
dev-2

(usa Outra)

Enviado em 09/01/2020 - 08:57h

Ao converter um lote com varias imagens, me deparei este erro linha 29: /bin/mv: Lista de argumentos muito longa

meu script para conversão:

#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

mv *.webp $dirtemp


  


2. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Daniel Lara Souza
danniel-lara

(usa Fedora)

Enviado em 09/01/2020 - 11:58h


tu tem muito mas muitos arquivos e com isso o comando mv não consegue mover os arquivos deixei assim seu script


#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

find ./ -name '.webp' -exec mv {} $dirtemp \;







3. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Dev 2 pe
dev-2

(usa Outra)

Enviado em 09/01/2020 - 12:01h

danniel-lara escreveu:


tu tem muito mas muitos arquivos e com isso o comando mv não consegue mover os arquivos deixei assim seu script


#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

find ./ -name '.webp' -exec mv {} $dirtemp \;







SIM TENHO MAIS DE 70MIL




4. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Perfil removido
removido

(usa Nenhuma)

Enviado em 09/01/2020 - 16:09h

Update: minha resposta tinha funcionado anteriormente com 80 mil arquivos, mas a retestei e ela não funcionou de novo com 100 mil arquivos. Andei vendo e parece mesmo que existe um limite de buffer no Bash ou no kernel.. Ainda não achei uma forma fácil de alterar isso...

Update2: Para aumentar o valor de buffer dos processos da sua shell atual, use '$ ulimit -s 100000' antes. Se tiver 2 Gb sobrando de RAM (parece ser o limite máximo), pode colocar 'ulimit -s unlimited'. Mas isso é um hack , não é bom alterar o padrão do ulimit para sempre..
https://unix.stackexchange.com/questions/128559/solving-mv-argument-list-too-long
Testei aqui com o ulimit aumentado, e agora moveu 144 mil arquivos de boas..

Update3: Este artigo, em inglês, é o mais esclarecedor que consegui encontrar.. O problema com limite de memória é especificamente com comandos que usam exec(), ou seja, o 'mv'. Já a expansão do bash só é limitada pela memória virtual do seu sistema. De fato, se você usar 'echo *' em um dir com centenas de milhares de arq ele não vai apresentar esse problema já que o 'echo' é um built-in do bash e não usa uma função exec().. Veja os limites:

eu@archhost ~ $ xargs --show-limits
Your environment variables take up 2906 bytes
POSIX upper limit on argument length (this system): 2092198
POSIX smallest allowable upper limit on argument length (all systems): 4096
Maximum length of command we could actually use: 2089292

Então, para driblar esse limite, sem precisar alterar o ulimit, é usando um built-in do bash 'printf' pois ele não usa a função exec(), e depois o 'xargs'.

Por que isso é importante: se você usar o 'find .. -exec mv', ele vai abrir uma nova sub-shell para cada 'mv' que ele fizer, isso vai deixar o processo muuuito lento (é possível otimizar esse comando um pouco..). Um 'for loop' é OK e super portável, porém ele pode ser muito devagar.. O 'printf' e o 'mv' são built-ins do bash, ou seja executam super rápido. Já o 'xargs', só vai abrir *uma* subshell e depois executar os 'mv', e portanto é muito mais rápido.
$ printf  '%s\0'  *.webp  |  xargs  -0  mv  -t  "$dirtemp" 

O 'printf' vai mandar um caracter nulo ao invés de uma nova linha entre cada nome de arquivo, o que vai evitar problemas com nomes com caracteres em branco, e será lido corretamente pelo 'xargs' com opção '-0'. Opção -t do 'mv' é para indicar corretamente qual o destino dos arquivos.
https://www.in-ulm.de/~mascheck/various/argmax/



---Antigo post---
O problema com o seu script não é o fato de você ter muitos arquivos. A mensagem de erro é enganosa, pois é um erro que advém (opa palavras difíceis, imprecionante) de como o Bash interpreta os nomes dos arquivos, já que a estrela * é um coringa e irá listar todos os nomes dos arquivos que casarem com o padrão *.webp

Porém, no seu caso, o problema é mesmo por que você deve ter nomes de arquivos com espaço em branco ou caracteres especiais.

Ao invés de usar o find, que é um desperdício de CPU e de tempo, use travessão -- antes dos argumentos do mv para o Bash interpretar corretamente os nomes dos arquivos.

mv -- *.webp $dirtemp 


PS: testei com 80mil arquivos aqui com espaço em branco no nome e foi de boas.


5. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Dev 2 pe
dev-2

(usa Outra)

Enviado em 10/01/2020 - 08:18h

marimbondo2 escreveu:

O problema com o seu script não é o fato de você ter muitos arquivos. A mensagem de erro é enganosa, pois é um erro que advém (opa palavras difíceis, imprecionante) de como o Bash interpreta os nomes dos arquivos, já que a estrela * é um coringa e irá listar todos os nomes dos arquivos que casarem com o padrão *.webp

Porém, no seu caso, o problema é mesmo por que você deve ter nomes de arquivos com espaço em branco ou caracteres especiais.

Ao invés de usar o find, que é um desperdício de CPU e de tempo, use travessão -- antes dos argumentos do mv para o Bash interpretar corretamente os nomes dos arquivos.

mv -- *.webp $dirtemp 


PS: testei com 80mil arquivos aqui com espaço em branco no nome e foi de boas.




#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do find

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

mv -- *.webp $dirtemp



seria desta forma?


6. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Daniel Lara Souza
danniel-lara

(usa Fedora)

Enviado em 10/01/2020 - 09:49h


dev-2 escreveu:

danniel-lara escreveu:


tu tem muito mas muitos arquivos e com isso o comando mv não consegue mover os arquivos deixei assim seu script


#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

find ./ -name '.webp' -exec mv {} $dirtemp \;







SIM TENHO MAIS DE 70MIL



chegou a testar o script que alterei pra ti ?

adicionando

find ./ -name '.webp' -exec mv {} $dirtemp \;



7. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Dev 2 pe
dev-2

(usa Outra)

Enviado em 10/01/2020 - 09:57h

danniel-lara escreveu:


dev-2 escreveu:

danniel-lara escreveu:


tu tem muito mas muitos arquivos e com isso o comando mv não consegue mover os arquivos deixei assim seu script


#!/bin/bash

# salva o diretorio atual
currentdir=`pwd`

# recuperar todos os arquivos *.jpg
for original in *.jpg; do

#substitui as extensões
format="${original/.jpg/.webp}"


echo $nome

# converte o .jpg em .webp
convert $original $format

done

# mover para o diretório da nova extensão
dirtemp=$currentdir/convertida

# se o diretorio não existir, entao criar o diretorio
if [ ! -e $dirtemp ];
then
mkdir $dirtemp
fi

find ./ -name '.webp' -exec mv {} $dirtemp \;







SIM TENHO MAIS DE 70MIL



chegou a testar o script que alterei pra ti ?

adicionando

find ./ -name '.webp' -exec mv {} $dirtemp \;



To fazendo Agora, ate o momento esta dando certo



8. Re: Me deparei com este erro linha 29: /bin/mv: Lista de argumentos muito longa

Daniel Lara Souza
danniel-lara

(usa Fedora)

Enviado em 13/01/2020 - 11:25h


opa e ai conseguiu resolver ?



9. RESOLVIDO

Dev 2 pe
dev-2

(usa Outra)

Enviado em 13/01/2020 - 11:40h

danniel-lara escreveu:


opa e ai conseguiu resolver ?


Deu certo sim, muito obrigado






Patrocínio

Site hospedado pelo provedor RedeHost.
Linux banner

Destaques

Artigos

Dicas

Tópicos

Top 10 do mês

Scripts