getopt dentro de funções - bug??? (Resolvido)

Iniciado por gwarah, 07 de Agosto de 2013, 12:33

tópico anterior - próximo tópico

gwarah

Olá amigos experts em scripts bash, isso tá me parecendo um bug do interpretador. Criei uma função para gerar nomes de arquivos temporários que utiliza getopts. Esta função foi feita para gerar nomes de arquivos temporários da seguinte forma:

__tmp[_label]_Date<YYYYMMDD_HHMMSS>

Onde [label] aparece no nome se for informado como parâmetro da função. O problema é que na segunda chamada da função informando label, este não é reconhecido. Aparentemente o getopts não está processando uma segunda chamada com a mesma chave. O script com resultado vai abaixo (falha a partir da 3. chamada da função).

-------------------------------

#!/bin/bash
# getopt com bug ??

####
#
# Função     : fn_file_tmp
# Objetivo   : Gera um nome para arquivo temporario
# Sintaxe :
#   fn_file_tmp [-l "label"]
#   -l, opcional. Label que vai fazer parte do nome para identificação
#
# Retorno :
#       $?=0, se a geração teve sucesso
#       $FNV_RETORNO= preenchida com o nome do arquivo temporário, caso $?=0
# Observações:
#       Padrão de nomeclatura: __tmp[_label]_Date<YYYYMMDD_HHMMSS>
#
####
function fn_file_tmp() {

   # inicializando variaveis
   opt_found=0
   FN_LABEL=""
   opt_file_tmp=""
   SINTAX="fn_file_tmp [-l \"label\"]"
   
   while getopts "l:" opt_file_tmp
   do
     (( opt_found++ ))
     case $opt_file_tmp in
       l)
           # mensagem de entrada de dados
           FN_LABEL="${OPTARG}"
           if [ -z "${FN_LABEL}" ]; then
               echo "label deve ser informado"
               echo "Sintaxe: ${SINTAX}"
               return 1
           fi
       ;;
       :)
           echo "Opcao -$OPTARG requer argumento."
           echo "Sintaxe: ${SINTAX}"
           return 1
       ;;
       \?)
           echo "Opção inválida: -$OPTARG"
           echo "Sintaxe: ${SINTAX}"
           return 1
       ;;
     esac
   done

   if [ $opt_found -gt 1 ]; then
       echo "Erro. Sintaxe: ${SINTAX}"
       return 1
   fi
   
   # geral o nome do arquivo temporario
   FNV_RETORNO="__tmp"
   [ -n "${FN_LABEL}" ] && FNV_RETORNO=`echo "${FNV_RETORNO}_${FN_LABEL}"`
   FNV_RETORNO="${FNV_RETORNO}_"$(date +"%Y%m%d_%H%M%S")
}

FNV_RETORNO=""

# chamada da função sem parâmetros (ok)
# Resultado 1 __tmp_20130807_122108
fn_file_tmp
echo Resultado 1 $FNV_RETORNO

# chamada da função com -l err (ok)
# Resultado 2 __tmp_err_20130807_122108
fn_file_tmp -l err
echo Resultado 2 $FNV_RETORNO

# chamada da função com -l ttp (falha - nome gerado não tem ttp)
# Resultado 3 __tmp_20130807_122108
fn_file_tmp -l ttp
echo Resultado 3 $FNV_RETORNO

# chamada da função com -l err (falha - nome gerado não tem err)
# Resultado 4 __tmp_20130807_122108
fn_file_tmp -l err
echo Resultado 4 $FNV_RETORNO



Quem puder me ajudar agradeço!

;)
"Cantar a beleza de ser um eterno aprendiz" (Gonzaguinha)

gwarah

Não é bug não. Mas eu não descobriria se não consultasse uns especialistas.

http://stackoverflow.com/questions/10454501/why-getopts-within-a-function-fails-to-work

A bronca é resolvida acrescentando local OPTIND=1  antes do getopts

o código agora fica assim:


#!/bin/bash
# getopt com bug ??

####
#
# Função     : fn_file_tmp
# Objetivo   : Gera um nome para arquivo temporario
# Sintaxe :
#   fn_file_tmp [-l "label"]
#   -l, opcional. Label que vai fazer parte do nome para identificação
#
# Retorno :
#       $?=0, se a geração teve sucesso
#       $FNV_RETORNO= preenchida com o nome do arquivo temporário, caso $?=0
# Observações:
#       Padrão de nomeclatura: __tmp[_label]_Date<YYYYMMDD_HHMMSS>
#
####
function fn_file_tmp() {

    # inicializando variaveis
   
    opt_found=0
    FN_LABEL=""
    opt_file_tmp=""
    SINTAX="fn_file_tmp [-l \"label\"]"

    local OPTIND=1
    while getopts "l:" opt_file_tmp
    do
      (( opt_found++ ))
      case $opt_file_tmp in
        l)
            # mensagem de entrada de dados
            FN_LABEL="${OPTARG}"
            if [ -z "${FN_LABEL}" ]; then
                echo "label deve ser informado"
                echo "Sintaxe: ${SINTAX}"
                return 1
            fi
        ;;
        :)
            echo "Opcao -$OPTARG requer argumento."
            echo "Sintaxe: ${SINTAX}"
            return 1
        ;;
        \?)
            echo "Opção inválida: -$OPTARG"
            echo "Sintaxe: ${SINTAX}"
            return 1
        ;;
      esac
    done

    if [ $opt_found -gt 1 ]; then
        echo "Erro. Sintaxe: ${SINTAX}"
        return 1
    fi
   
    # geral o nome do arquivo temporario
    FNV_RETORNO="__tmp"
    [ -n "${FN_LABEL}" ] && FNV_RETORNO=`echo "${FNV_RETORNO}_${FN_LABEL}"`
    FNV_RETORNO="${FNV_RETORNO}_"$(date +"%Y%m%d_%H%M%S")
}

FNV_RETORNO=""

# chamada da função sem parâmetros (ok)
# Resultado 1 __tmp_20130807_122108
fn_file_tmp
echo Resultado 1 $FNV_RETORNO

# chamada da função com -l err (ok)
# Resultado 2 __tmp_err_20130807_122108
fn_file_tmp -l err
echo Resultado 2 $FNV_RETORNO

# chamada da função com -l ttp (Ok - Nome com label ttp)
# Resultado 3 __tmp_ttp_20130807_140734
fn_file_tmp -l ttp
echo Resultado 3 $FNV_RETORNO

# chamada da função com -l err (Ok - Nome com label err)
# Resultado 4 __tmp_err_20130807_140734
fn_file_tmp -l err
echo Resultado 4 $FNV_RETORNO


"Cantar a beleza de ser um eterno aprendiz" (Gonzaguinha)