Contenu | Rechercher | Menus

Annonce

Si vous avez des soucis pour rester connecté, déconnectez-vous puis reconnectez-vous depuis ce lien en cochant la case
Me connecter automatiquement lors de mes prochaines visites.

À propos de l'équipe du forum.

#1 Le 21/12/2010, à 18:07

iuchiban

Développement de regexp

Bonjour tout le monde,

J'ai un petit soucis dans un script shell que je développe.
Il permet d'effectuer divers actions sur des instances tomcat (pour le boulot)

Il est appelé de la manière suivante :

./FlagProd -f <UnFlag> -i <UneOuPlusieursInstances>
par exemple :
./FlagProd -f up -i "INSTANCE1 INSTANCE2 INSTANCE3"

Je voudrais pouvoir gérer les listes d'instances à l'aide de regexp du type

./FlagProd -f up -i "INSTANCE{1,2,3}"
ou
./FlagProd -f up -i "INSTANCE[123]"
ou
./FlagProd -f up -i "INSTANCE[1-3]"

J'ai une variable qui contient la valeur du paramètre -i, mais sans développer la regexp.

Donc y a t il un moyen de développer ma regexp (via echo ou autre) ??


C'est depuis que Chuck Norris a laissé la vie sauve à un manchot que l'on dit que Linux est libre.

Chuck Norris n'a pas besoin d'éditer son premier message pour ajouter [Résolu]. Chuck Norris est toujours [Résolu], quoi qu'il arrive.

Hors ligne

#2 Le 21/12/2010, à 18:28

ehmicky

Re : Développement de regexp

Salut,

./FlagProd -f up -i "INSTANCE"{1,2,3}

ne marche pas ? En théorie l'expansion a lieu avant l'appel à FlagProd, qui doit donc voir trois options à -i.

Dernière modification par ehmicky (Le 21/12/2010, à 18:32)


Stego++, bibliothèque libre de stéganographie (avec cryptographie), à venir !
Besoin de votre aide :
Stats sur les compilateurs C++ les plus utilisés
Comment utiliser les archetypes C++ ?

Hors ligne

#3 Le 22/12/2010, à 09:42

iuchiban

Re : Développement de regexp

non ca ne fonctionne pas car :
"INSTANCE"{1,2,3} est bien développé en INSTANCE1 INSTANCE2 INSTANCE3, mais -i ne prends que la première valeur qui suit ce paramètre, donc INSTANCE1.

Bon, je viens de trouver du coup, mais ça fait un peut un truc de goret :

$ ./Flag_Prod.sh -f up -i \" "INSTANCE"{1,2,3}"CMP" \" # parce que en fait, mes instances, sont de la forme INSTANCExCMP
-f up -i " INSTANCE1CMP INSTANCE2CMP INSTANCE3CMP "

et là, mon paramètre -i prend la valeur des 3 instances.
Bon, je vais devoir forcer mes utilisateurs à cette syntaxe, ça va pas être simple big_smile

EDIT : bon en fait non, il me prend le " et pas tout ce qu'il y a derrière....
Bon ben, je vais continuer à chercher...

Dernière modification par iuchiban (Le 22/12/2010, à 10:01)


C'est depuis que Chuck Norris a laissé la vie sauve à un manchot que l'on dit que Linux est libre.

Chuck Norris n'a pas besoin d'éditer son premier message pour ajouter [Résolu]. Chuck Norris est toujours [Résolu], quoi qu'il arrive.

Hors ligne

#4 Le 22/12/2010, à 10:43

FRUiT

Re : Développement de regexp

En fait la procédure déclenchée par -i dans ton script doit aussi savoir appréhender plusieurs paramètres (automatiquement épandus par bash, donc)... Elle doit aussi pouvoir ajouter "CMP" a la fin des arguments passés sans devoir les coller dans la ligne de commande.

Soit en utilisant getopts, soit à base de while [ "$1" ]; do ... shift.

Est-ce prévu dans ta fonction ou procédure -i ? Si c'est pas trop grave tu devrais poster ton script.

Dernière modification par FRUiT (Le 22/12/2010, à 10:50)


Neon Suite by FRUiT (kde4.6) [url]http://[Merci de relire les règles]/yzm7cee[/url]
"Pour la carotte, le lapin est la plus parfaite incarnation du mal" (R. Sheckley)
clean

Hors ligne

#5 Le 22/12/2010, à 11:00

iuchiban

Re : Développement de regexp

Je pense qu'il n'y a rien qui donne des indications dans mon script, donc le voila :

#!/bin/bash
#set -x

## Variables Globales
_ENV="/HOME/uxwadm/scripts/Env.cfg"
_TOOLBOX=/HOME/uxwadm/scripts/toolbox_wrapper.pl
_LOG="/tmp/${0}.log"
> ${_LOG}
_ACTIONS="/tmp/${0}.actions"
_SSH="/tmp/${0}.ssh"
echo "#!/bin/bash" > ${_SSH}
_FLAG=""
_INSTANCE=""
_ALL=0
_CHECK=0

## Fonction qui affiche le mode d'utilisation du script
Utilisation()
{
  clear
  echo
  echo "Utilisation du script :"
  echo
  echo "${0} [--all] [-f FLAG] [--nocheck|--checkon] -i INSTANCE"
  echo
  echo "--all     : permet de faire le traitement sur toutes les instances du serveur"
  echo "-f        : FLAG à appliquer"
  echo "--nocheck : pose un flag nocheck sur l'instance"
  echo "--checkon : supprime le flag nocheck sur l'instance"
  echo "-i        : INSTANCE a parametrer"
  echo
  echo "L'utilisation du FLAG HaProxy up supprime forcément le FLAG nocheck."
  echo "L'utilisation du FLAG HaProxy stop pose forcément un FLAG nocheck."
  echo
  exit 0
}

## Fonction qui affiche un message d'erreur si un retour de la toolbox est "probleme"
Probleme()
{
  if [[ "${1}" == "probleme" ]]
  then
    clear
    echo "Il y a eu un probleme lors de la recuperation du ${2}."
    exit 3
  fi
}

## Le script nécessite un minimum de 4 arguments
if [[ ${#} -lt 3 ]]
then
  Utilisation
fi

## Gestion des parametres
## Il est possible de lancer le script en renseignant directement :
while getopts ":h:af:i:-:" _OPTION
do
  # gestion des options longues
  if [[ ${_OPTION} = "-" ]]
  then
    case "${OPTARG%%=*}" in
      all )
        _ALL=1
        _OPTION="z"
      ;;
      nocheck )
        _CHECK=1
        _OPTION="z"
      ;;
      checkon )
        _CHECK=-1
        _OPTION="z"
      ;;
      * )
        echo "option longue non permise -- ${OPTARG%%=*}" >&2
        exit 1
      ;;
    esac
  fi
  case ${_OPTION} in
  f )
    case ${OPTARG} in
      up | stop | down )
        _FLAG=${OPTARG}
      ;;
      * )
        echo -e "Ce FLAG (${_RED}${OPTARG}${_RESET}) n'est pas autorisé !!"
        exit 1
      ;;
    esac
  ;;
  i )
    _INSTANCE=${OPTARG}
  ;;
  z )
  ;;
  * )
    Utilisation
  ;;
  esac
done
shift $((${OPTIND} - 1))

[[ ${_FLAG} == "" && ${_CHECK} -eq 0 ]] && echo "Il faut choisir au moins une action (FLAG HaProxy ou NoCheck) !!" && exit 3
[[ ${_INSTANCE} == "" ]] && echo "L'INSTANCE n'a pas été définie !!" && exit 3

_LISTE=$(echo ${_INSTANCE} | tr "[:punct:]" " ")

if [[ ${_ALL} -eq 1 ]]
then
  _LISTE_A=""
  for _INST in ${_LISTE}
  do
    _LISTE_A=$(echo ${_LISTE_A} $(grep -v "#" /home/uxwadm/scripts/Env.cfg | grep -w ${_INST} | tr ";" "\n" | grep "INST=" | cut -d"=" -f2 | tr "," "\n" | grep ${_INST} | cut -d":" -f2- | tr ":" " ") | tr " " "\n" | egrep -v "ADM|GST")
  done
  _LISTE=${_LISTE_A}
fi

_LISTE=$(echo ${_LISTE} | tr " " "\n" | sort -u)

case ${_FLAG} in
  up )
    _CHECK=-1
  ;;
  stop | down )
    _CHECK=1
  ;;
  * )
  ;;
esac
case ${_CHECK} in
  0 )
    _CHECK_CMD=""
    _CHECK_MSG="NoCheck : rien."
  ;;
  1 )
    _CHECK_CMD="touch scripts/nagios/data/_INSTANCE_.nocheck"
    _CHECK_MSG="NoCheck : touch nocheck."
  ;;
  -1 )
    _CHECK_CMD="touch scripts/nagios/data/_INSTANCE_.nocheck; rm scripts/nagios/data/_INSTANCE_.nocheck"
    _CHECK_MSG="NoCheck : rm nocheck."
  ;;
esac

clear
for _INSTANCE in ${_LISTE}
do
  _APP=$(grep ${_INSTANCE} ${_ENV} | grep -v "^#" | grep "INST=" | cut -d";" -f1)
  [[ ${_APP} == "" ]] && echo "Probleme de recuperation de l'APP" && exit 3
  _PTF=$(grep ${_INSTANCE} ${_ENV} | grep -v "^#" | grep "INST=" | cut -d";" -f2)
  _TYP=$(grep ${_INSTANCE} ${_ENV} | grep -v "^#" | grep "INST=" | cut -d";" -f3)
  ##Recuperation du composant
  if [[ $(perl -w ${_TOOLBOX} getComposant ${_APP}${_PTF}) == "none" ]]
  then
    _CMP=""
  else
    _CMP=$(grep "^${_APP};${_PTF};${_TYP}" ${_ENV} | tr ";" "\n" | grep INST | cut -d"=" -f2 | tr "%" "\n" | grep ${_INSTANCE} | cut -d"$" -f1)
  fi
  _SERVEUR=$(perl -w ${_TOOLBOX} getServerList ${_APP}${_PTF} ${_TYP} ${_CMP})
  Probleme ${_SERVEUR} "serveur"
  if [[ "${_SERVEUR: -4}" == "-bck" ]]
  then
    _SERVEUR=$(echo ${_SERVEUR} | tr "," "\n" | grep "^$(echo ${_INSTANCE} | cut -b4-6 | tr "[A-Z]" "[a-z]")")
  else
    _SERVEUR=$(echo ${_SERVEUR} | tr "," "\n" | cut -b 2- | grep "^$(echo ${_INSTANCE} | cut -b4-6 | tr "[A-Z]" "[a-z]")")
  fi

  _USER=$(perl -w ${_TOOLBOX} getUser ${_APP}${_PTF} ${_TYP}USER ${_CMP})
  Probleme ${_USER} "user"

  ## Recherche de l'Etat haproxy actuel de l'instance
  ssh ${_USER}@${_SERVEUR} "find haproxy/${_INSTANCE}" > ${_LOG} 2>/dev/null
  if [[ $(stat ${_LOG} | grep "Size:" | awk '{print $2}') -eq 0 ]]
  then
    _MODE="conf"
  elif [[ $(grep ${_INSTANCE} ${_LOG} | egrep "stop|down|up") ]]
  then
    _MODE=$(grep ${_INSTANCE} ${_LOG} | egrep "stop|down|up" | awk -F"/" '{print $NF}')
  else
    _MODE="up"
  fi
  rm ${_LOG}

  _HAPROXY_CMD=""
  case ${_MODE}${_FLAG} in
    upup|stopstop|downdown )
      _HAP_MSG="HaProxy : FLAG déjà positionné à ${_FLAG} !!"
    ;;
    upstop )
      _HAP_MSG="HaProxy : up => stop."
      _HAPROXY_CMD="touch haproxy/${_INSTANCE}/up; rm haproxy/${_INSTANCE}/up; touch haproxy/${_INSTANCE}/stop"
    ;;
    updown )
      _HAP_MSG="HaProxy : up => down (non recommandé)."
    ;;
    stopup )
      _HAP_MSG="HaProxy : stop => up."
      _HAPROXY_CMD="rm haproxy/${_INSTANCE}/${_MODE}; touch haproxy/${_INSTANCE}/${_FLAG}"
    ;;
    stopdown )
      _HAP_MSG="HaProxy : stop => down."
      _HAPROXY_CMD="rm haproxy/${_INSTANCE}/${_MODE}; touch haproxy/${_INSTANCE}/${_FLAG}"
    ;;
    downup )
      _HAP_MSG="HaProxy : down => up."
      _HAPROXY_CMD="rm haproxy/${_INSTANCE}/${_MODE}; touch haproxy/${_INSTANCE}/${_FLAG}"
    ;;
    confup|confstop )
      _HAP_MSG="HaProxy : Creation du repertoire ~/haproxy/${_INSTANCE}. FLAG => ${_FLAG}."
      _HAPROXY_CMD="mkdir -p ~/haproxy/${_INSTANCE}; touch ~/haproxy/${_INSTANCE}/${_FLAG}"
    ;;
    * )
      _HAP_MSG="HaProxy : rien."
    ;;
  esac
  echo "$_INSTANCE : ${_HAP_MSG} / ${_CHECK_MSG}"
  echo "${_HAPROXY_CMD:+"${_HAPROXY_CMD}; "}${_CHECK_CMD}" | sed 's/_INSTANCE_/'"${_INSTANCE}"'/g' >> "/tmp/${_USER}@${_SERVEUR}_actions"
  echo "${_USER}@${_SERVEUR}" >> ${_ACTIONS}
done
echo
echo "Etes vous d'accord avec ces actions ??"
read -p "[OUI/non] " _CHOIX
case ${_CHOIX} in
  OUI )
    echo "Exécution du fichier actions"
    for _CMD in $(sort -u ${_ACTIONS}) 
    do
      echo "ssh ${_CMD} '$(cat /tmp/${_CMD}_actions | tr "\n" ";")'" >> ${_SSH}
    done
    chmod +x ${_SSH}
    ${_SSH}
  ;;
  * )
    echo "On annule tout"
  ;;
esac
rm /tmp/*_actions  ${_ACTIONS} ${_SSH}

C'est depuis que Chuck Norris a laissé la vie sauve à un manchot que l'on dit que Linux est libre.

Chuck Norris n'a pas besoin d'éditer son premier message pour ajouter [Résolu]. Chuck Norris est toujours [Résolu], quoi qu'il arrive.

Hors ligne

#6 Le 22/12/2010, à 12:06

ehmicky

Re : Développement de regexp

Sinon peut-être que tu peux rajouter une option mettons -nNOMBRE, qui fassent que NOMBRE instances sont crées.
Par exemple du côté utilisateur, il tape :

./Flag_Prod.sh -f up -i "INSTANCE" -n3

et le script produit lui-même une seule variable _INSTANCE valant "INSTANCE1 INSTANCE2 INSTANCE3" ?


Stego++, bibliothèque libre de stéganographie (avec cryptographie), à venir !
Besoin de votre aide :
Stats sur les compilateurs C++ les plus utilisés
Comment utiliser les archetypes C++ ?

Hors ligne

#7 Le 22/12/2010, à 12:08

Totor

Re : Développement de regexp

FRUiT a raison. Le synopsis de l'utilisation de ton script n'est pas adapté à ton besoin.
il devrait être soit  en indiquant une option -i par instance ou une option -i pour toutes les instances indiquées avec un séparateur.
1ère forme :
${0} [--all] [-f FLAG] [--nocheck|--checkon] -i INSTANCE1 [-i INSTANCE2] [-i ...]
2nde forme (plus facile à implémenter):
${0} [--all] [-f FLAG] [--nocheck|--checkon] -i INSTANCE1,INSTANCE2,...,INSTANCEn

Par ailleurs, tel que tu l'indiques, il est à la fois possible de préciser l'option --all en même temps que l'opn -i.
Cela devrait plutôt être ainsi :
${0} [-f FLAG] [--nocheck|--checkon] --all|-i INSTANCE[,...]

Aussi, évite les options à double '-', c'est moins facile à gérer. Je te propose -a pour --all.

Enfin, --nocheck et --checkon peuvent être regroupés en une seule option : -c on|no

au final :
${0} [-f FLAG] [-c on|no] --a|-i INSTANCE[,...]

Utilise getopts pour gérer tout ça et ce sera plus fiable. (un script que j'avais fait montrant un exemple assez complet)

Dernière modification par Totor (Le 22/12/2010, à 12:09)


-- Lucid Lynx --

Hors ligne

#8 Le 22/12/2010, à 14:10

FRUiT

Re : Développement de regexp

case ${_OPTION} in
  i )
    _INSTANCE=${OPTARG}
  ;;
esac

Là ça me parait pas bon.

Si tu es sur que -i est toujours la dernière option sur la ligne de commande, tu peux faire quelque chose comme :

case ${_OPTION} in
  i )
    [ "$OPTARG" ] && while [ "$1" ]; do
      _INSTANCE="$1"
      commandes géantes sur $1 ou procédure de traitement
      shift
    done
  ;;
esac

J'ai pas testé c'est juste un exemple d'implémentation de gestion de plusieurs paramètres pour l'option -i, faudrait peut-être aussi un shift avant le while ou autres adaptations.

Dernière modification par FRUiT (Le 22/12/2010, à 14:18)


Neon Suite by FRUiT (kde4.6) [url]http://[Merci de relire les règles]/yzm7cee[/url]
"Pour la carotte, le lapin est la plus parfaite incarnation du mal" (R. Sheckley)
clean

Hors ligne

#9 Le 22/12/2010, à 16:01

iuchiban

Re : Développement de regexp

@Fruit : eh ben non justement, comme c'est des paramètre, le -i n'est pas forcément la dernière option.
@Totor : la aussi, tu peux à la fois avoir un -i INSTANCE et un --all, car le all fait rechercher toutes les instances présentes sur le serveur.
En gros, sur une application, tu as 10 instances par serveur, notées de 0 à 9, et je veux appliquer mon script sur les 1 à 5.
Mais sur une autre, j'ai 4 instance et je veux l'appliquer à toutes les instances.
Dans le premier, je fais actuellement :

./Flag_Prod.sh -f up -i "INSTANCE1 INSTANCE2 INSTANCE3 INSTANCE4 INSTANCE5"

dans le deuxieme cas

./Flag_Prod.sh -f up -i "INSTANCE1" --all

Ta deuxième forme est actuellement ce que je gère, mais en mettant les différentes insatnces entre quotes (avec n'importe quelle ponctuation au milieu, je la supprime ensuite).


C'est depuis que Chuck Norris a laissé la vie sauve à un manchot que l'on dit que Linux est libre.

Chuck Norris n'a pas besoin d'éditer son premier message pour ajouter [Résolu]. Chuck Norris est toujours [Résolu], quoi qu'il arrive.

Hors ligne

#10 Le 22/12/2010, à 17:02

Totor

Re : Développement de regexp

script iuchiban a écrit :

[...]echo "--all     : permet de faire le traitement sur toutes les instances du serveur"
[...]
echo "-i        : INSTANCE a parametrer"
[...]

Lors d'une seule exécution de ton script (quelque soit le serveur), comment peux-tu traiter à la fois une seule instance et toutes les instances ??? Vas-tu toutes les traiter ou seulement celle qui est précisée ? Il y a quelque chose qui n'est pas logique (où alors je n'ai rien compris).

pour revenir à la forme de ta ligne de commande. On peut effectivement considérer qu'elle correspond à ma 2nde forme avec comme séparateur l'espace. Cependant, ce n'est pas le cas pour "bash". La preuve en est : l'objet de ton fil.


-- Lucid Lynx --

Hors ligne

#11 Le 22/12/2010, à 17:12

iuchiban

Re : Développement de regexp

Totor a écrit :

Lors d'une seule exécution de ton script (quelque soit le serveur), comment peux-tu traiter à la fois une seule instance et toutes les instances ??? Vas-tu toutes les traiter ou seulement celle qui est précisée ? Il y a quelque chose qui n'est pas logique (où alors je n'ai rien compris).

Contexte :
3 serveurs (TOTO, TITI, TATA), sur lesquels tournent 10 instances. (TOTO_00 -> TOTO_09, TATA_00 ...)
1 serveur central sur lequel je lance mon script

Mise en pratique :
je veux faire un test sur une seule INSTANCE (TOTO_01) :

./Flag_Prod -f stop -i TOTO_01

Je veux maintenant généraliser à toutes les instances de TOTO :

./Flag_Prod -f stop -i TOTO_01 --all

exécute les commandes sur TOTO_00, TOTO_01, TOTO_02, ...

Si je veux faire toutes les instances des 3 serveurs :

./Flag_Prod -f stop -i "TOTO_01 TITI_00 TATA_08" --all

trouve les 10 instances de chaque serveur et exécute les actions.

Maintenant, je veux faire une action sur 5 instances (les paires par exemple), actuellement je dois taper le nom des 5 instances.
La regexp permettrait d'économiser des copier coller de noms d'instaces.


C'est depuis que Chuck Norris a laissé la vie sauve à un manchot que l'on dit que Linux est libre.

Chuck Norris n'a pas besoin d'éditer son premier message pour ajouter [Résolu]. Chuck Norris est toujours [Résolu], quoi qu'il arrive.

Hors ligne

#12 Le 22/12/2010, à 17:57

Totor

Re : Développement de regexp

je suis loin d'être convaincu car pour moi tu as un problème conceptuel. tu utilises parfois la notion d'instance comme de serveur.
pour moi, tu as 3 serveurs ayant chacun 10 instances.
de ce fait, pour moi :
- toto est un serveur et toto_01 est une instance de toto
- titi est un serveur et titi_00 est une instance de titi
- tata est un serveur et tata_08 est une instance de tata

donc :
./Flag_Prod -f stop -i TOTO_01 : est correcte
./Flag_Prod -f stop -i TOTO_01 --all : non correcte car toto_01 est une instance et non un serveur
./Flag_Prod -f stop -i "TOTO_01 TITI_00 TATA_08" --all : n'est pas correcte car toto_0&, titi_0& et tata_08 sont des instances et non des serveurs

il te faudrait plutôt avoir quelque chose comme ça :
./Flag_Prod -f stop -i[0-9|all] -s [toto|titi|tata|all]

Dernière modification par Totor (Le 22/12/2010, à 17:57)


-- Lucid Lynx --

Hors ligne