¿Cómo puedo proteger los paréntesis pasados ​​a un comando cd?

¿Cómo puedo proteger los paréntesis pasados ​​a un comando cd?

Yo preguntéaquícómo hacer cdespacios protegidos. La función de tabulación es excelente, pero a veces pegas la ruta desde el portapapeles, por lo que resulta útil.

Sin embargo, la solución rompe con los paréntesis. No importa cómo intentes escapar y proteger la entrada, siempre devuelve:

bash: syntax error near unexpected token `('

¿Hay alguna manera de que también se ocupe de los paréntesis? Lo que quiero es que cuando entre a esto funcione:

cd My path with spaces (and parentheses)

Respuesta1

Utilice comillas simples 'alrededor del argumento. (Esto funciona para cualquier comando, no solo cd).

cd 'My path with spaces (and parentheses)'

No puedes hacer que bash pase los paréntesis a cd. Hacer que los espacios funcionen es un truco muy especializado.

Las comillas simples funcionan con todos los caracteres excepto con 'él mismo. Reemplace las comillas simples por la secuencia de 4 caracteres '\''.

cd 'Apostrophe'\''s a pain'

Esto no funciona si el nombre del directorio comienza con un guión, porque eso hace que el cdcomando interprete el argumento como una opción. Pase --antes del nombre del directorio para evitar esto.

Verhttps://unix.stackexchange.com/questions/69144/how-do-i-escape-a-sub-directory-name-with-an-ampersand-in-it/69147#69147para más detalles.

Otro método es hacer que el shell lea una línea de texto separada en lugar de pasar el argumento en la línea de comando.

Strapakowsky@darkstar ~$ read -r; cd -- "$REPLY"
My path with spaces (and parentheses)
Strapakowsky@darkstar ~/My path with spaces (and parentheses)$ 

En lugar de copiar y pegar manualmente, también puedes hacerlo mediante programación. Instalar cualquieraxclipoxsel.

cd -- "$(xclip -o -selection clipboard)"
cd -- "$(xsel -bo)"

Podrías convertir esto en un alias.

alias cde='cd -- "$(xsel -bo)"'

Respuesta2

Cómo acceder correctamente cda directorios con caracteres como espacios y paréntesis en sus nombres:

Si el nombre de su carpeta no incluye un carácter de comilla simple ', simplemente escríbalo entre comillas simples:

cd 'My path with spaces (and parentheses)'

Si incluye ', pero no incluye un carácter de comilla doble ", una reacción violenta \, una comilla invertida `o un dólar $, enciérrelo entre comillas dobles:

cd "My path with spaces (and parentheses)"

No es muy común que el nombre de un archivo o directorio contenga comillas simples y dobles. (Esto quizás se deba a que no es común que un nombre de archivo o directorio contenga comillas dobles. La única razón por la que no recomendé las comillas dobles originalmente es que, a diferencia de las comillas simples, las comillas dobles permiten $expandir las variables de entorno. Esto sería un problema si su nombre de archivo contuviera un $carácter seguido de texto).

Si contiene ambos, o simplemente desea otro método, puede escapar de cada espacio y paréntesis manualmente insertando un carácter de barra invertida \antes:

cd My\ path\ with\ spaces\ \(and parentheses\)

Eso es molesto, pero afortunadamente, el caparazón conhazlo por ti, si escribe el comienzo del nombre y presiona Tab. Si hay más de un nombre de archivo o directorio que comienza con My, es posible que deba escribir algo más para que se expanda. Si presiona Taby no se expande, puede presionar Tabnuevamente para ver una lista de archivos que coinciden con lo que ha escrito hasta ahora. Entonces sabrá cuánto más debe escribir para que coincida de forma única y se expanda.

Alternativamente, puedes escapar de las comillas internas. Por ejemplo, supongamos que tiene una carpeta llamada:

Mischa's gardening tips for "home and office"

Puedes usar:

cd Mischa\'s\ gardening\ tips\ for\ \"home\ and\ office\"

Pero también puedes simplemente usar:

cd 'Mischa'\''s gardening tips for "home and office"'

Las barras invertidas no son especiales entre comillas simples, por lo que terminamos la cadena entre comillas simples, agregamos una comilla simple protegida por barra invertida e inmediatamente comenzamos otra cadena entre comillas simples, todo sin ningún espacio que pueda iniciar un argumento separado.

Por qué probablemente no puedas hacer que cdfuncione como querías:

En cuanto a ponerse cd My path with spaces (and parentheses)a trabajar: no, realmente no puede hacer eso, porque este comportamiento no es específico del cdcomando, es parte de la forma en que funciona la ejecución de cualquier comando. Cuando se ejecuta un comando, se proporciona una lista de argumentos proporcionados por el usuario. Cuando el shell ve un espacio, sabe que un argumento acaba de terminar y otro acaba de comenzar. Para pasar un espacio como parte de un argumento, se debe citar de una de las formas anteriores.

Podrías lograrpartede estaalgunode las veces, podrías hacer cd My path with spacestrabajo para ir a la My path with spacescarpeta. Podría lograr esto escribiendo un script de shell que concatene todos los argumentos proporcionados por el usuario con espacios. (Entonces, si lo desea, puede cdllamar a ese script, creando un alias de shell con cdsu nombre; eso tendría prioridad sobre el shell incorporado cdque normalmente está ejecutando). Pero:

  • El script no recibiría argumentos diferentes para My path with spacesy My path with spaces, por lo que cd My path with spacesfallaría o ingresaría a la carpeta incorrecta.

  • No puede hacer esto con los paréntesis, porque el shell los usa para agruparlos de modo que no se comunican de ninguna manera a un comando. En realidad, la mayoría de las veces el shell simplemente arrojará un error de sintaxis (tal como has visto):

    ek@Kip:~$ cd My path with spaces (and parentheses)
    bash: syntax error near unexpected token `('
    

    No importa lo que cambie, ese error de sintaxis seguirá ocurriendo cuando se dé ese comando.

Digo que "probablemente" no puedas hacer que esto funcione porque hay una manera de hacerlo: puedes crear tu propio caparazón que se comporte como deseas. Pero esto es extremadamente difícil y es poco probable que alguien quiera hacerlo, sólo para realizar este cambio. (También puede modificar el código fuente de un shell existente, lo cual es una solución más práctica pero aún requiere más esfuerzo del que la mayoría de la gente desearía realizar). Además de eso, es poco probable que cdpueda aceptar nombres de directorio con caracteres arbitrarios, incluidos espacios. , como ocurre en Windows.

En caso de que se pregunte por qué esto funciona en Windows pero no en Ubuntu: en Windows, los comandos se pasan el texto escrito después de ellos como uncadena de texto, y cuando un comando necesita interpretar esa cadena como una secuencia de argumentos separados (lo que generalmente hace, pero no siempre), el código del comando debe llamar a una función de biblioteca especial que analiza la cadena de la línea de comandos. (En un programa C, esto sucede detrás de escena, pero aún implica el uso de la API de Windows).

información relacionada