Recuperando a linha de Comando em Scripts Python

Utilizar linhas de comando em scripts Python é razoavelmente simples. O script abaixo funciona no Python 2.8 ou superior. Existem mais opções e alternativas para ler a linha de comando, mas vamos nos ater ao básico…

Explicando o fonte acima:

  • Primeiro importamos a classe que processa as linhas de comando;
  • Depois criamos um Parser para analisar a linha de comando. O atributo ‘description’ será exibido quando esta linha for processada;
  • O próximo passo é adicionar os argumentos que você deseja receber no seu script;
    • Os dois primeiros atributos são nome e flag do atributo. Qualquer um destes valores poderá ser utilizado na linha de comando;
    • default é o valor padrão para este argumento, caso ele seja omitido;
    • required define se o argumento é obrigatório ou não. Se ele for obrigatório, o atributo default não é utilizado;
    • help é o texto que será exibido quando o script for executado com -h (ou –help);
  • Uma vez que todos os argumentos forem declarados, basta utilizar o a função parse_args() para recuperar os valores informados na linha de comando. Esta função vai retornar uma variável com com todas os argumentos que você definiu.

Este seria o resultado do código acima, caso o script seja executado sem argumentos:

 

Ao mudar o atributo required para true…

 

Executando o script passando a linha de comando com chamando o argumento pelo nome (-b) ou pela flag (–blockfile)…

 

*Update: 13/09/2018*

Antes de começar com o update de conteúdo deste post, gostaria de acrescentar um breve contexto: O exemplo acima foi de um script que fiz para bloquear acessos a sites. Ele lê o arquivo blocklist.txt e adiciona os sites no arquivo host, apontando eles para localhost.

Ok. Vamos a atualização de conteúdo…

O exemplo anterior funciona bem, mas o argparse tem outras opções que podem ser uteis.

Vamos imaginar um novo script com uma nova linha de comando. A primeira coisa que você deve fazer é instanciar o parser:

 

Agora vamos adicionar alguns argumentos com configurações diferentes. No final, mostro um resumo destas possibilidades de configuração.

Argumento obrigatório do tipo numérico

No código acima existem dois parâmetros que não foram utilizados no exemplo anterior:

  1. dest: Indica qual o nome da variável que vai armazenar o valor deste argumento. Se não for informado, o valor é armazenado em uma variável com o nome do argumento. Neste caso, se eu não tivesse informado o parâmetro dest, o valor seria acessado por uma propriedade chamada ‘number’;
  2. type: Indica o tipo do valor do argumento. Isso quer dizer a variável arg_num vai possuir um valor numérico e não uma string (que é o padrão);

 

Argumento obrigatório do tipo string

Similar ao argumento anterior, mas com o tipo (type) definido para string (str), que é o padrão.

 

Argumento opcional do tipo numérico

 

Argumento opcional do tipo string

Neste argumento eu falo que estou esperando um número, mas como o type não foi definido para int, então o valor dele será sempre uma string.

 

Outro argumento opcional do tipo string

Este argumento é opcional (required=False) e foi definido explicitamente como string (type=str)

 

Mais um argumento opcional do tipo string

Este argumento é similar ao anterior, mas possui um parâmetro a mais, o action. Ele define o que será feito com o argumento informado. O valor padrão é ‘store‘, que simplesmente armazena o valor do argumento em uma variável.

 

Argumento do tipo flag (define valor para True)

O argumento acima possui uma action diferente, a store_true. Isso indica que se você utilizar esta flag, o valor armazenado na variável dest será True. O valor padrão para este argumento é (por razões obvias) False.

Por flag eu quero dizer que é um argumento que você utiliza apenas ele. Ao contrário de um argumento do tipo numérico (-i 42), você vai utilizar apenas o argumento em si (-t ou –true)

 

Argumento do tipo flag (define valor para False)

Este argumento é similar ao anterior, mas seus valores são invertidos: Por padrão, este argumento é considerado como True e se for informado, muda para False. Isso foi definido na action com valor store_false.

 

Argumento do tipo flag sem valor default definido

O argumento acima não possui um valor padrão, mas seu action está definido como store_false, ou seja, se for omitido, a variável arg_flag vai ficara com valor True.

Isso demonstra que o argparse é esperto o suficiente para entender que, se você quer armazenar False na variável, caso o argumento seja utilizado, então esta mesma variável deve possuir o valor oposto (True) como padrão.

 

Argumento do tipo lista

O argumento acima é do tipo lista, ou seja, você pode utiliza-lo varias vezes na linha de comando, pois todos os valores informados serão adicionados a variável. Este comportamento é definido pelo valor append, informado no parametro action.

 

Argumento do tipo lista (numérico)

Este argumento é similar ao anterior. A primeira diferença é que definido um tipo para os valores passados (type=int) e isso implica em dizer que a variável vai possuir uma lista de integers.

A outra diferença é que não definimos um valor padrão (default=[]) para este argumento, ou seja, se este argumento não for utilizado, a variável arg_list_int terá o valor None ao invés de uma lista vazia ([]).

 

Argumento do tipo lista de constantes

Acima estão dois argumentos, mas eles fazem parte do mesmo processo. Ambos estão com a action definida para append_const e isso quer dizer que eles vão adicionar um valor pre-definido a variável, resultando em uma lista de valores padrões.

A diferença entre append e append_const é que o append vai adicionar o valor que o usuário informar para a lista, enquanto o append_const vai adicionar o valor que você definiu.

Para que esta action funcione corretamente, o parametro dest deve ser igual para todos os argumentos relevantes.

 

Argumento do tipo versão

Assim como o argumento que mostra o texto de ajuda (-h ou –help), um argumento com action definido para version vai sobrescrever os outros argumentos e exibir apenas a sua informação, ou seja, você não pode misturar o argumento do tipo versão com os outros na mesma linha de comando.

O que este tipo de argumento faz é padronizar uma forma de exibir a versão da sua aplicação. Quando utilizado, ele vai mostrar o texto definido no parametro version.

 

Resumindo os parametros da função add_argument

  • Primeiro parametro (posicional) recebe o ‘apelido’ do argumento. (Exemplo: -v);
  • Segundo parametro (posicional) recebe o nome completo do argumento. Se o parâmetro dest não for informado, este será o nome da variável que armazena o valor do argumento;
  • required: Indica se o argumento é ou não obrigatório (True/False);
  • dest: Indica o nome da variável que vai receber o valor do argumento;
  • action: Indica qual ação será tomada no argumento. Os valores possíveis são:
    1. store: (padrão) armazena o valor do argumento na variável;
    2. store_true: Armazena True se o argumento for utilizado. Caso contrário, o valor será False;
    3. store_false: Armazena False se o argumento for utilizado. Caso contrário, o valor será True;
    4. append: Adiciona o valor do argumento a uma lista;
    5. append_const: Adiciona um valor pre-definido a um lista. Devem ser adicionados varios argumentos, um para cada valor que poderá ser adicionado a lista;
    6. version: Exibe a verão do aplicativo (definido no parametro chamado version);
  • const: Utilizado apenas quando o action está definido como append_const. Neste caso, o valor definido neste parametro será adicionado a lista;
  • default: Valor padrão do argumento, caso ele não seja informado pelo usuário;
  • version: Utilizado apenas quando o action está definido para “version”. Neste caso, o valor informado neste parametro será exibido para o usuário;

 

 

Para facilitar, fiz um exemplo no Github onde você pode passar estes valores e ver o resultado no console. Ele vai apenas exibir o nome da variável passada via linha de comando, seu valor e o tipo do valor.

 

 

Espero ter ajudado!

Referência:

The following two tabs change content below.
Breno RdV
Ex-Psicólogo, com quase uma década de experiência em Recursos Humanos e Gestão de Pessoas, atual desenvolvedor e Analista de Sistemas, trabalhando com PowerBuilder, C#, PowerShell e expandindo horizontes para Python, Xamarin, PHP, Angular e (por que não?) Unity.

Comments

comments

Posted in Dev, Python and tagged , , , .