
Actualmente tengo este comando, que imprime con éxito cada nombre de archivo en su propia línea:
find . -exec echo {} \;
Estoy intentando dividir la lógica para que el find
comando ejecute una función. Residencia enesta preguntaHe probado esto:
my_function() {
echo $1
}
export -f my_function
find . -exec bash -c 'my_function "$@"' bash {} +
Entonces obtengo este resultado:
.
También intenté reemplazar $@
con $*
, pero esto hace $1
que todos los archivos no tengan saltos de línea. Me gustaría ejecutar una lógica que verifique cada archivo, por lo que me gustaría $1
ser solo un archivo a la vez. Intenté dividir la salida con espacios for file in $1
pero esto no funciona para archivos que tienen espacios en el nombre del archivo. ¿Cómo ejecuto una función Bash para cada archivo encontrado por el find
comando?
EDITAR: Aquí está el script completo que estoy usando. Parece que funciona bien.
# Ensures that non-csproj text files are formatted with LF line endings.
format() {
for pathname do
if [[ $pathname == *"git"* ]]; then
continue
elif [[ $pathname == *"csproj"* ]]; then
continue
fi
dos2unix $pathname
done
}
export -f format
find . -exec bash -c 'format "$@"' bash {} \;
Respuesta1
Para ejecutar dos2unix --newline
en todos los archivos normales dentro y debajo del directorio actual, evitando cualquier archivo cuyo nombre contenga la cadena git
:
find . -type f ! -name '*git*' -exec dos2unix --newline {} +
Es decir, busque todos los archivos normales cuyos nombres no coincidan con el patrón *git*
y ejecútelos dos2unix --newline
todos en lotes tan grandes como sea posible a la vez. Cambie ! -name '*git*'
a ! -path '*git*'
para evitar cualquier archivo cuyo nombre de ruta contenga la cadena git
(por ejemplo, archivos en .git
directorios).
Para evitar explícitamente cualquier .git
directorio, pero incluir cualquier otra cosa que pueda tener git
en su nombre:
find . -name .git -prune -o -type f -exec dos2unix --newline {} +
Esto impide find
incluso ingresar a cualquier directorio llamado .git
mediante el uso -prune
para eliminar dichas rutas del árbol de búsqueda.
Responda antes de editar la pregunta:
Su función imprime solo su primer argumento. El punto es la ruta de búsqueda de nivel superior que utiliza con find
. Se pasa porque no realiza ningún filtrado particular de las entradas del directorio (como, por ejemplo, -type f
solo para archivos normales, -name
o cualquier otro tipo de find
prueba).
Si desea que su función imprima cada uno de sus argumentos, utilice cualquiera de los dos
my_function() {
printf '%s\n' "$@"
}
que permite printf
imprimir cada uno de los argumentos con una nueva línea en el medio, o
my_function() {
for pathname do
printf '%s\n' "$pathname"
done
}
que recorre los argumentos y llama printf
una vez para cada uno.
Se esperaría que esto funcionara correctamente si llamara a la función como
my_function "$@"
desde dentro de su secuencia de comandos en línea bash -c
. Se "$@"
amplía a todos los argumentos dados al guión, citados individualmente.
Otra forma sería mover el bucle al bash -c
script:
for pathname do
my_function "$pathname"
done
y luego tener
my_function () {
printf '%s\n' "$1"
}
Esto sería hacer explícitamente lo que usted dice que desea hacer, es decir, llamar a la función una vez para cada nombre de ruta.
El find
comando entonces se vería así
find . -exec bash -c 'for pathname do my_function "$pathname"; done' bash {} +
o, posiblemente, un poco más legible,
find . -exec bash -c '
for pathname do
my_function "$pathname"
done' bash {} +
Por cierto, esto sería lo mismo que
shopt -s globstar nullglob dotglob
for pathname in ./**/*; do
my_function "$pathname"
done
excepto que .
no sería procesado. Al usar esto, no tendría que exportar su my_function
función.
Con el bucle dentro de la función (como en los dos primeros fragmentos de código de esta respuesta), esto se reduciría a
shopt -s globstar nullglob dotglob
my_function ./**/*