cómo poner todas las etiquetas del directorio en diferentes variables

cómo poner todas las etiquetas del directorio en diferentes variables

Obtuve todas las etiquetas del directorio de un archivo. Ahora, estoy atrapado en una situación en la que quiero almacenar todas las etiquetas de directorio individuales en diferentes variables, como se muestra a continuación. Agradeciendo de antemano.

A continuación se muestra lo que he obtenido:

<Directory />
    AllowOverride none
    Order deny, allow
    Deny from all
</Directory>
<Directory "/var/www">
    AllowOverride None
    Require all granted
</Directory>

Requerido:

# echo $var1
<Directory /> 
AllowOverride none 
Order deny, allow 
Deny from all 
</Directory>

# echo $var2
<Directory "/var/www"> 
AllowOverride None  
Require all granted 
</Directory>

Tenga en cuenta: no hay solo 2 etiquetas de directorio, hay muchas etiquetas de directorio sin ningún espacio entre ellas. Cada directorio individual completo debe almacenarse en una variable separada.

agradeciendo de antemano

Respuesta1

Puede iterar sobre las líneas del archivo y agregar las nuevas líneas a una cadena hasta que encuentre una </Directory>etiqueta.

Si solo tienes Directoryetiquetas, el código sería mucho más sencillo. Deberá declarar varXvariables a medida que las utilice declaresi no sabe cuántas etiquetas tiene.

STR=""
i=1
DIRTAG=false
while read -r LINE; do
    if grep -q '^<Directory' <<< $LINE; then
        DIRTAG=true
    fi
    if $DIRTAG; then
        STR+="$LINE
"
    fi
    if grep -q '^</Directory>' <<< $LINE; then 
        declare var$i="\"\"\"$STR\"\"\"" #You're not clear on the quotes
        STR=""   
        i=$((i+1))
        DIRTAG=false
    fi
done < t.txt

Ahora echo "$var1"; echo "$var2"genera lo siguiente (no olvide las comillas dobles. De lo contrario, las nuevas líneas serán espacios en la salida impresa)

"""<Directory />
AllowOverride none
Order deny, allow
Deny from all
</Directory>
"""
"""<Directory "/var/www">
AllowOverride None
Require all granted
</Directory>
"""

Cuando no sepa la cantidad de etiquetas, puede usar esto para iterar sobre las variables creadas.

for j in `seq 1 $((i-1))`; do
    var=var$j
    echo "${!var}"
done

Respuesta2

Puede procesar el archivo para convertirlo en una lista de definiciones de variables y luego obtenerlo. Por ejemplo, podría agregar una línea vacía después de cada </Directory>etiqueta de cierre y luego usar el modo de párrafo de Perl para leer cada entrada como una sola línea:

$ sed 's|</Directory>|</Directory>\n|' file | 
    perl -000 -lne 'print "var" . ++$k . "=\"$_\"";' 
var1="<Directory />
    AllowOverride none
    Order deny, allow
    Deny from all
</Directory>"

var2="<Directory "/var/www">
    AllowOverride None
    Require all granted
</Directory>"

Y podrías obtenerlo directamente para configurar las variables en tu shell actual:

$ . <(sed 's|</Directory>|</Directory>\n|' file | 
    perl -000 -lne 'print "var" . ++$k . "=\"$_\"";' file )

$ echo "$var1"
<Directory />
    AllowOverride none
    Order deny, allow
    Deny from all
</Directory>

$ echo "$var2"
<Directory /var/www>
    AllowOverride None
    Require all granted
</Directory>

Explicación

  • sed s|</Directory>|</Directory>\n|' file: agrega una nueva línea después de cada </Directory>etiqueta de cierre.
  • -000: esto activa el "modo de párrafo" de Perl, donde una "línea" se define mediante dos caracteres de nueva línea consecutivos, básicamente una línea en blanco. Entonces, en lugar de líneas reales, cada "línea" ahora es un párrafo. Esto nos permite tratar todo lo que hay entre la apertura y el cierre < Directory />como una sola línea, ya que cada entrada está separada por una línea en blanco.
  • -lne: -lElimina las nuevas líneas finales y agrega un \na cada una print. Lee -nel archivo de entrada línea por línea (consulte más arriba lo que significa "línea" en este contexto) y aplica el script proporcionado por -ea cada línea.
  • print "var" . ++$k . "=\"$_\"": imprime el formato de salida deseado: la cadena varseguida de un número que se incrementa para cada línea procesada ( ++$k), luego =\"( "debe escaparse ya \"que estamos dentro de una cadena entre comillas dobles) y la "línea" actual ( $_) seguida por el cierre ".
  • . <(perl ...): .es el comando fuente, leerá el archivo que le proporcione y ejecutará su contenido en la sesión actual. el <()se llamasustitución de procesos, esencialmente nos permite tratar la salida de un comando como si fuera un archivo. Tenga en cuenta que no todos los shells admiten esto, por lo que si el suyo no lo admite, es posible que deba guardar el resultado en un archivo y luego obtener ese archivo.

información relacionada