426 votes

Comment mettre un commentaire de ligne pour une commande multi-lignes

Je sais comment écrire une commande multiligne dans un script de Bash, mais comment ajouter un commentaire pour chaque ligne dans une commande multiligne ?

CommandName InputFiles      \ # This is the comment for the 1st line
            --option1 arg1  \ # This is the comment for the 2nd line
            --option2 arg2    # This is the comment for the 3nd line

Mais malheureusement, le commentaire après le caractère de continuation \ interrompra la commande.

0 votes

Copiez le bloc de code dans un bloc commenté/annoté adjacent. Si vous mettez à jour le code, n'oubliez pas de mettre à jour le bloc de commentaires.

0 votes

Note : ce problème et ses solutions s'appliquent également aux chaînes de caractères multilignes.

2 votes

Pour information, il ne s'agit pas d'une copie de cette question la question liée demande une commande qui utilise des tuyaux... alors que cette question parle d'une commande qui a plusieurs options. ce n'est pas la même chose.

784voto

Marwan Alsabbagh Points 4245

C'est comme ça que je fais. Essentiellement en utilisant le backtick de Bash. substitution de commande on peut placer ces commentaires n'importe où le long d'une longue ligne de commande, même si elle est divisée en plusieurs lignes. J'ai placé la commande echo devant votre exemple pour que vous puissiez exécuter l'exemple et voir comment il fonctionne :

echo CommandName InputFiles `#1st comment` \
             --option1 arg1 `#2nd comment` \
             --option2 arg2 `#3rd comment`

Un autre exemple où vous pouvez placer plusieurs commentaires à différents endroits sur une même ligne :

some_cmd --opt1 `#1st comment` --opt2 `#2nd comment` --opt3 `#3rd comment`

10 votes

Cela fonctionne même au sein des sous-commandes pipées : "echo `#1` foo \(newline) | perl -ne `#2` 'print'"... exactement ce dont j'avais besoin !

273 votes

C'est l'abus le plus ingénieux de la substitution que j'ai vu !

3 votes

Pour moi, c'est utile pour résoudre rapidement le problème lorsque je veux bloquer l'action de certaines options dans une longue commande multiligne dans un fichier script.

121voto

Philipp Points 21479

Vous pourriez stocker les arguments dans un tableau :

args=(InputFiles      # This is the comment for the 1st line
      # You can have whole lines of comments in between, useful for:
      #--deprecated-option # This isn't use any more
      --option1 arg1  # This is the comment for the 2nd line

      # And even blank lines in between for readability
      --option2 arg2  # This is the comment for the 3nd line
     )
CommandName "${args[@]}"

Cependant, je pense que cela semble un peu bidon si c'est uniquement dans le but de permettre des commentaires pour chaque argument. Par conséquent, je réécrirais simplement le commentaire pour qu'il fasse référence aux arguments individuels, et je le placerais au-dessus de la commande entière.

9 votes

Cela fonctionne pour quelque chose de simple comme l'exemple de l'OP, mais cela ne supportera pas > y < y | y || y && et ainsi de suite.

0 votes

@Philipp Hmmm, merci. C'est une bonne solution de contournement, mais j'ai peur que cela soit un peu confus si mon --option arg a à la fois ' y " .

0 votes

@Philipp, je ne sais vraiment pas laquelle des deux est la bonne réponse. Il semble qu'il n'y ait pas de réponse correcte. J'ai donc mis votre réponse en haut de la liste et marqué celle de Perry comme étant la réponse correcte.

99voto

Perry Points 2241

Je crains qu'en général, vous ne puissiez pas faire ce que vous demandez. Le mieux que vous puissiez faire est un commentaire sur les lignes avant la commande, ou un commentaire unique à la fin de la ligne de commande, ou un commentaire après la commande.

Vous ne pouvez pas réussir à intercaler des commentaires à l'intérieur d'une commande de cette manière. Le site \ expriment l'intention de fusionner des lignes, donc, à toutes fins utiles, vous essayez d'intercaler des commentaires dans une seule ligne, ce qui ne fonctionne pas de toute façon parce qu'un fichier \ doit être à la fin de la ligne pour avoir cet effet.

9 votes

Sans oublier que "Le \ s fusionnent effectivement ces lignes" n'est même pas correct, le problème est que la barre oblique inverse doit immédiatement précéder la nouvelle ligne afin de l'échapper, alors qu'avec cmd \ # comment il y a un espace et un commentaire entre la barre oblique inversée et la nouvelle ligne.

11 votes

La réponse acceptée devrait être celle de Marwan ci-dessous.

3 votes

Je pense que je ne suis pas d'accord, la réponse de Marwan est intelligente mais ressemble à un abus de substitution. Je dirais même que la réponse de Philipp est plus proche de ce que je voudrais faire.

20voto

chepner Points 54078

D'après le commentaire de pjh à une autre réponse à cette question en remplaçant IFS avec une variable connue pour ne pas contenir de caractères autres que des espaces blancs.

comment=
who ${comment# This is the command} \
    -u ${comment# This is the argument}

Pourquoi les expansions de paramètres ne sont-elles pas citées ? La variable est initialisée avec une chaîne vide. Lorsque l'expansion du paramètre se produit, la variable # (sans rapport avec le caractère de commentaire du shell # mais utilisé pour la similarité) tente de retirer le commentaire réel de la valeur du paramètre. Le résultat, bien sûr, est toujours une chaîne vide.

Une expansion de paramètre non citée subit un découpage de mots et une génération de nom de chemin. Dans ce cas, aucun de ces processus ne crée de mots supplémentaires à partir d'une chaîne vide, le résultat est donc toujours une chaîne vide. Une telle chaîne vide est simplement rejetée sans affecter la commande dans laquelle elle apparaît. Ce qui précède est précisément équivalent à

who \
  -u

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X