Soy nuevo en UNIX y estoy usando la "Línea de comandos de Mac OS X" de Kirk McElhearn para enseñarme algunos comandos.
Estoy intentando utilizar tr
y grep
para poder buscar cadenas de texto en un documento de Word de MS-Office normal.
$ tr '\r' '\n' < target-file | grep search-string
Pero todo lo que devuelve es:
Illegal byte sequence.
robomechanoid:Position-Paper-Final-Draft robertjralph$ tr '\r' '\n' < Position-Paper-Final-Version.docx | grep DeCSS
tr: Illegal byte sequence
robomechanoid:Position-Paper-Final-Draft robertjralph$
Realmente ejecuté la misma línea en un script que creé vi
y realiza la búsqueda correctamente.
text-processing
grep
character-encoding
binary
tr
usuario74886
fuente
fuente
Respuestas:
grep
Es una herramienta de procesamiento de texto. Espera que su entrada sean archivos de texto . Parece que lo mismo ocurretr
con macOS (aunquetr
se supone que admite archivos binarios).Las computadoras almacenan datos como secuencias de bytes . Un texto es una secuencia de caracteres. Hay varias formas de codificar caracteres como bytes, llamadas codificaciones de caracteres . La codificación de caracteres estándar de facto en la mayoría del mundo, especialmente en OSX, es UTF-8 , que es una codificación para el conjunto de caracteres Unicode . Hay solo 256 bytes posibles, pero más de un millón de caracteres Unicode posibles, por lo que la mayoría de los caracteres están codificados como bytes múltiples. UTF-8 es una codificación de longitud variable: dependiendo del carácter, puede tomar de uno a cuatro bytes codificar un carácter. Algunas secuencias de bytes no representan ningún carácter en UTF-8. Por lo tanto, hay secuencias de bytes que no son archivos de texto UTF-8 válidos.
tr
se queja porque encontró una secuencia de bytes de este tipo. Espera ver un archivo de texto codificado en UTF-8, pero ve datos binarios que no son válidos UTF-8.Un documento de Microsoft Word no es un archivo de texto: es un documento de procesamiento de texto. Los formatos de documentos de procesamiento de texto codifican no solo texto, sino también formato, imágenes incrustadas, etc. El formato de Word, como la mayoría de los formatos de procesamiento de texto, no es un archivo de texto.
Puede indicar a las herramientas de procesamiento de texto que operen en bytes cambiando la configuración regional . Específicamente, seleccione la configuración regional "C", que básicamente significa "nada lujoso". En la línea de comando, puede elegir la configuración regional con variables de entorno .
Esto no emitirá ningún error, pero tampoco hará nada útil ya que
target-file
todavía es un archivo binario que es poco probable que contenga la mayoría de las cadenas de búsqueda que especificará.Por cierto,
tr '\r' '\n'
no es un comando muy útil a menos que le queden archivos de texto de Mac OS 9 o anterior.\r
(retorno de carro) era el separador de nueva línea en Mac OS antes de Mac OS X. Desde OSX, el separador de nueva línea es\n
(avance de línea, el estándar de Unix) y los archivos de texto no contienen retornos de carro. Windows usa la secuencia de dos caracteres CR-LF para representar saltos de línea;tr -d '\r'
convertiría un archivo de texto de Windows en un archivo de texto Unix / Linux / OSX.Entonces, ¿cómo puede buscar en un documento de Word desde la línea de comandos? Un
.docx
documento de Word es en realidad un archivo zip que contiene varios archivos, los principales están en XML .Mac OS X incluye la utilidad zipgrep para buscar dentro de archivos zip.
El resultado no será muy legible porque los archivos XML en formato docx consisten principalmente en una gran línea. Si desea buscar dentro del texto del cuerpo principal del documento, extraiga el archivo
word/document.xml
del archivo. Tenga en cuenta que, además del texto del documento, este archivo contiene marcado XML que representa la estructura del documento. Puede masajear un poco el marcado XMLsed
para dividirlo en líneas manejables.fuente
xml_pp
en el paquetexml-twig-tools
en Debian Gnu + Linux (no conoce un mac).tr
[...] espera que su entrada sean archivos de texto"; mientras que la especificación POSIX establece claramente "La entrada estándar puede ser cualquier tipo de archivo". . Por favor corrige tu respuesta.tr
se supone que procesa la entrada binaria (en particular, se supone que procesa bytes nulos correctamente). Sin embargo, POSIX no especifica claramente cómo se supone que debe lidiar con la entrada que no es una secuencia de caracteres. (Si fuera un implementador, pasaría secuencias de bytes no válidas sin modificarlas (o las eliminaría con-s
), y plantearía un defecto con el comité estándar.) Evidentemente, el tr de macOS se queja de ellas.Supongo que su mapa de caracteres de las configuraciones regionales es UTF-8, por lo que tendrá problemas con los archivos binarios. Simplemente cambie a la configuración regional C:
fuente
LC_ALL=C ( tr '\r' '\n' < target-file | grep search-string )
. Sin embargo, el docx no es C local. Es utf16 y está comprimido y es complejo, y nadie lo sabe. Me gustaría utilizar una herramienta que puede convertirlo a un formato diferente que puede procesar, por ejemplo, html u odt (odt también está comprimido, pero está bien definido y es fácil de interpretar).strings
comando da texto claro.( export LC_ALL=C; tr '\r' '\n' < target-file | grep search-string; )
debería funcionar.strings
tiene superpoderes: puede leer archivos que no son solo utf-8 o texto ascii.()
lo que pensé que funcionaría, gracias a @ vinc17 por una solución.