Como grep corretamente para texto em scripts de bash

Como grep corretamente para texto em scripts de bash

grep é um utilitário linux versátil, que pode levar alguns anos para dominar bem. Até os engenheiros do Linux experientes podem cometer o erro de assumir que um determinado arquivo de texto de entrada terá um determinado formato. grep também pode ser usado, diretamente em combinação com se Pesquisas baseadas para digitalizar a presença de uma string dentro de um determinado arquivo de texto. Descubra como grep corretamente para o texto independente dos conjuntos de caracteres, como usar o -q opção para enviar mensagens de texto para presença de string e mais!

Neste tutorial, você aprenderá:

  • Como fazer o correto de texto independente de conjunto de personagens pesquisa com grep
  • Como usar declarações de grep avançadas de scripts ou comandos terminais de OneLiner
  • Como testar presença de sequência usando o -q opção para grep
  • Exemplos destacando o uso do Grep para esses casos de uso
Como grep corretamente para texto em scripts de bash

Requisitos de software e convenções usadas

Requisitos de software e convenções de linha de comando Linux
Categoria Requisitos, convenções ou versão de software usada
Sistema Independente da distribuição Linux
Programas Linha de comando Bash, sistema baseado em Linux
Outro Qualquer utilidade que não esteja incluída no shell bash por padrão pode ser instalada usando sudo apt-get install utility-name (ou yum install para sistemas baseados em redhat)
Convenções # - requer que o Linux -Commands seja executado com privilégios de raiz diretamente como usuário root ou por uso de sudo comando
$-exige que o Linux-Commands seja executado como um usuário não privilegiado regular

Exemplo 1: Texto de conjunto de caracteres correto pesquisas de texto com Grep

O que acontece quando você grep através de um arquivo que é baseado em texto/caractere, mas contém caracteres especiais fora do intervalo normal? Isso pode acontecer quando o arquivo contém conjuntos de caracteres complexos ou parecem conter conteúdo binário como. Para entender melhor isso, primeiro precisamos entender o que são dados binários.

A maioria (mas não todos) computadores usa em seu nível mais básico, apenas dois estados: 0 e 1. Talvez o mais simplificado você possa pensar sobre isso como um interruptor: 0 não é volt, sem energia e 1 é "algum nível de tensão" ou alimentado. Computadores modernos são capazes de processar milhões desses 0 e 1 em uma fração de segundo. Este é o estado de 0/1 é chamado de 'bit' e é um sistema numérico base-2 (assim como nosso sistema decimal 0-9 é um sistema numérico Base-10). Existem outras maneiras de representar dados baseados em bits/binários, como Octal (8-Base: 0-7) e Hexadecimal (16-Base: 0-F).

Voltando ao 'binário' (bin, duplo), você pode começar a ver como é comumente usado para descrever qualquer tipo de dados que não pode ser facilmente reconhecido pelos seres humanos, mas pode ser entendida por computadores baseados em binários. Talvez não seja a melhor analogia, pois o binário geralmente se refere a dois estados (verdadeiros/falsos), enquanto em comum o jargão 'dados binários' passou a mal dados que não são facilmente interpretáveis ​​facilmente interpretáveis.

Por exemplo, um arquivo de código -fonte compilado com um compilador contém dados binários Principalmente ilegível por humanos. Por exemplo, um arquivo de código -fonte compilado com um compilador contém dados binários Principalmente ilegível pelo olho humano. Outro exemplo pode ser um arquivo criptografado ou um arquivo de configuração escrito em um formato de propriedade.

Como é quando você tenta ver dados binários?

Geralmente, ao visualizar dados binários para executáveis, você verá alguns dados binários reais (todos os caracteres de aparência estranha - seu computador está exibindo dados binários nos recursos limitados de formato de saída que seu terminal suporta), bem como em alguns resultados baseados em texto. No caso de ls Como visto aqui, eles parecem ser nomes de funções dentro do ls código.

Para visualizar dados binários corretamente, você realmente precisa de um visualizador de arquivo binário. Esses espectadores simplesmente formatam dados em seu formato nativo, juntamente com uma coluna lateral baseada em texto. Isso evita limitações de saída textual e permite que você veja o código do computador para o que realmente é: 0 e 1, embora frequentemente formatado em formatação hexadecimal (0-F ou 0-F, como mostrado abaixo).

Vamos dar uma olhada em dois conjuntos de 4 linhas do código binário de ls Para ver como isso parece:

$ hexdump -c /bin /ls | cabeça -n4; eco '…'; hexdump -c /bin /ls | Tail -n131 | Cabeça -N4 00000000 7F 45 4C 46 02 01 01 00 00 00 00 00 00 00 00 00 |.Elfo… | 00000010 03 00 3E 00 01 00 00 00 D0 67 00 00 00 00 00 00 |…>… G… | 00000020 40 00 00 00 00 00 00 00 C0 23 02 00 00 00 00 00 |@… #… | 00000030 00 00 00 00 40 00 38 00 0D 00 40 00 1E 00 1D 00 | @ @.8… @… |… 00022300 75 2e 76 65 72 73 69 6f 6e 00 2e 67 6e 75 2e 76 | u.Versão ... GNU.v | 000222310 65 72 73 69 6f 6e 5f 72 00 2e 72 65 6c 61 2e 64 | ersion_r… relA.d | 000222320 79 6e 00 2e 72 65 6c 61 2e 70 6c 74 00 2e 69 6e | yn… relA.PLT… in | 00022330 69 74 00 2e 70 6c 74 2e 67 6f 74 00 2e 70 6c 74 |.Tenho… PLT | 


Como tudo isso (além de aprender mais sobre como os computadores funcionam) ajuda a entender correto grep uso? Vamos voltar à nossa pergunta original: o que acontece quando você grep através de um arquivo que é baseado em texto/personagem, mas contém caracteres especiais fora do intervalo normal?

Agora podemos reformular com razão "o que acontece quando você grep através de um arquivo binário"? Sua primeira reação pode ser: Por que eu gostaria de pesquisar em um arquivo binário?. Em parte, a resposta mostra no acima ls exemplo já; frequentemente arquivos binários ainda contêm seqüências baseadas em texto.

E há uma razão muito mais importante e principal; grep Por padrão, assumirá muitos arquivos para conter dados binários assim que eles tiverem caracteres especiais, e talvez quando eles contêm certas seqüências de fuga binária, mesmo que o arquivo por si só possa ser baseado em dados. O pior é que, por padrão, Grep falhará e abortará a digitalização desses arquivos assim que esses dados forem encontrados:

$ head -n2 test_data.SQL CREATE TABELA T1 (ID INT); Inserir nos valores T1 (1); $ grep 'insert' test_data.sql | Tail -N2 Inserir nos valores T1 (1000); Arquivo binário test_data.SQL corresponde 

Como dois exemplos proeminentes da experiência pessoal com o trabalho de banco de dados, quando você verifica os logs de erros do servidor de banco de dados, que podem conter facilmente caracteres especiais, como às vezes mensagens de erro, banco de dados, tabela e nomes de campo podem chegar ao log de erros e essas mensagens são regularmente em conjuntos de caracteres específicos da região.

Outro exemplo é o teste SQL obtido de suítes de teste de banco de dados (mostrados no exemplo acima). Esses dados geralmente contêm caracteres especiais para testar e enfatizar o servidor de várias maneiras. O mesmo se aplicaria à maioria dos dados de teste do site e outros conjuntos de dados de teste de domínio. Como Grep falha por padrão contra esses dados, é importante garantir que adicionamos uma opção ao Grep para cobrir isso.

A opção é --Files binários = texto. Podemos ver como nosso grep agora funciona corretamente:

$ grep 'insert' test_data.sql | wc -l 7671 $ grep 'insert' test_data.sql | Tail -N1 Arquivo binário test_data.SQL corresponde $ grep--binário-files = text 'insert' test_data.sql | WC -L 690427 

Que diferença! Você pode imaginar quantos automatizados grep Scripts em todo o mundo estão deixando de digitalizar todos os dados que devem estar digitalizando. O que é pior e compostos significativamente a questão é que grep Falha 100% silenciosamente quando isso acontecer, o código de erro será 0 (sucesso) nos dois casos:

$ grep -q 'insert' test_data.sql; eco $? 0 $ grep - -binário -files = text -q 'insert' test_data.sql; eco $? 0 


Compondo ainda mais, a mensagem de erro é exibida em stdout saída, e não em stderr Como se poderia esperar. Podemos verificar isso redirecionando stderr para o dispositivo nulo /dev/null, Exibindo apenas stdout saída. A saída permanece:

$ grep 'insert' test_data.SQL 2>/dev/null | Tail -N1 Arquivo binário test_data.SQL corresponde 

Isso também significa que, se você redirecionar seus resultados de grep para outro arquivo (> Algum arquivo.TXT Após o comando Grep), que o 'arquivo binário… corresponde' agora seria parte desse arquivo, além de perder todas as entradas vistas após o ocorrido esse problema.

Outra questão é o aspecto de segurança: vamos levar uma organização que tem o Script Access Log Greps para enviar relatórios por e -mail para sysadmins sempre que um agente desonesto (como um hacker) tenta e acessar recursos não autorizados. Se esse hacker puder inserir alguns dados binários no registro de acesso antes de sua tentativa de acesso, e o grep não é protegido por --Files binários = texto, Esses e -mails não serão enviados.

Mesmo que o script seja desenvolvido bem o suficiente para verificar o grep Código de saída, ainda ninguém jamais notará um erro de script, pois Grep retorna 0, ou em outras palavras: sucesso. Sucesso não é embora 🙂

Existem duas soluções fáceis; adicionar --Files binários = texto Para todos os seus grep Declarações, e você pode considerar a saída da saída do grep (ou o conteúdo de um arquivo de saída redirecionado) para o arquivo de expressão regular '^.*partidas'. Para obter mais informações sobre expressões regulares, consulte Bash Regexps para iniciantes com exemplos e Bash Regex avançado com exemplos. No entanto, fazer tanto ou apenas o primeiro seria preferido, pois a segunda opção não é à prova de futuro; O texto 'Binário… corresponde' pode mudar.

Por fim, observe que quando um arquivo de texto for corrompido (falha do disco, falha na rede etc.). Este é mais um motivo para sempre proteger o seu grep declarações com o --Files binários = texto opção.

Tl; dr: Usar --Files binários = texto para todos os seus grep declarações, mesmo que atualmente funcionem bem. Você nunca sabe quando esses dados binários podem atingir seu arquivo.

Exemplo 2: teste para a presença de uma determinada string dentro de um arquivo de texto

Podemos usar grep -q em combinação com um se Declaração para testar a presença de uma determinada string em um arquivo de texto:

$ se grep - -binário -files = text -qi "insert" test_data.sql; Então eco "encontrado!"; else eco" não encontrado!"; Fi encontrou! 

Vamos dividir isso um pouco pela primeira vez, se os dados realmente existirem:

$ grep - -binário -files = text -i "insert" test_data.sql | Cabeça -n1 Inserir nos valores T1 (1); 

Aqui deixamos cair o q (silencioso) opção para obter a saída e ver que a string 'inserir' - tomada de maneira insensível ao caso (especificando o -eu opção para grep existe no arquivo como 'inserção…'.

Observe que o q a opção não é especificamente um teste opção. É antes um modificador de saída que informa grep para ficar 'quieto', eu.e. Não para produzir nada. Então, como o se Declaração sabe se existe uma presença de uma determinada string em um arquivo de texto? Isso é feito através do grep Código de saída:

$ grep - -binário -files = text -i "insert" test_data.sql 2> & 1>/dev/null; eco $? 0 $ grep - -binário -files = text -i "Isso realmente não existe" test_data.sql 2> & 1>/dev/null; eco $? 1 


Aqui fizemos um redirecionamento manual de todos stderr e sdtout saída para /dev/null redirecionando stderr (2>) para stdout (& 1) e redirecionando tudo stdout saída para o dispositivo nulo (>/dev/null). Isso é basicamente equivalente ao -q (silenciosa) opção para grep.

Em seguida, verificamos o código de saída e estabelecemos que quando a string é encontrada, 0 (sucesso) é devolvido, enquanto 1 (falha) é retornado quando a string não é encontrada. se pode usar esses dois códigos de saída para executar o então ou o outro cláusulas especificadas para isso.

Em resumo, podemos usar Se grep -q Para testar a presença de uma certa string dentro de um arquivo de texto. A sintaxe totalmente correta, como visto anteriormente neste artigo, é Se grep - -binário -files = text -qi "search_term" your_file.SQL para pesquisas insensíveis ao caso e Se Grep - -Binário -Files = Texto -q "Search_term" Your_File.SQL Para pesquisas sensíveis ao caso.

Conclusão

Neste artigo, vimos as muitas razões pelas quais é importante usar --Files binários = texto Em quase todas as pesquisas grepas. Nós também exploramos usando grep -q em combinação com se declarações para testar a presença de uma determinada string em um arquivo de texto. Aproveite o uso grep, e deixe -nos um comentário com o seu melhor grep descobertas!

Tutoriais do Linux relacionados:

  • Coisas para instalar no Ubuntu 20.04
  • Manipulando a entrada do usuário em scripts bash
  • Mastering Bash Script Loops
  • Como encontrar uma string ou texto em um arquivo no Linux
  • Use o WPScan para digitalizar o WordPress quanto a vulnerabilidades em Kali
  • Mint 20: Melhor que o Ubuntu e o Microsoft Windows?
  • Como recuperar informações de hardware com DMIDecode no Linux
  • Loops aninhados em scripts de basquete
  • Uma introdução à automação, ferramentas e técnicas do Linux
  • Coisas para fazer depois de instalar o Ubuntu 20.04 fossa focal linux