Comment passer l'argument à Makefile à partir de la ligne de commande?
Je comprends que je peux faire
$ make action VAR="value"
$ value
avec Makefile
VAR = "default"
action:
@echo $(VAR)
Comment obtenir le comportement suivant?
$ make action value
value
?
Que diriez-vous
$make action value1 value2
value1 value2
command-line
parameters
makefile
arguments
Meng Lu
la source
la source
Réponses:
Vous ne devriez probablement pas faire cela; vous cassez le schéma de base du fonctionnement de Make. Mais voici:
EDIT:
Pour expliquer la première commande,
$(MAKECMDGOALS)
est la liste des "cibles" énoncées sur la ligne de commande, par exemple "action value1 value2".$@
est une variable automatique pour le nom de la cible de la règle, dans ce cas "action".filter-out
est une fonction qui supprime certains éléments d'une liste. Donc$(filter-out bar, foo bar baz)
revientfoo baz
(ça peut être plus subtil, mais on n'a pas besoin de subtilité ici).Mettez-les ensemble et
$(filter-out $@,$(MAKECMDGOALS))
renvoie la liste des cibles spécifiées sur la ligne de commande autre que "action", qui peut être "valeur1 valeur2".la source
$(shell echo $(MAKECMDGOALS) | sed 's!^.* $@ !!')
d'omettre toutes les cibles avant et de considérer simplement ce qui suit comme arguments:make target1 target2 action value1 value2
%:
et je@:
ne trouve pas d'informations sur ce que font ces "directives" (ou ce qu'elles appellent). Pouvez-vous expliquer?%:
et@:
est une règle . Le nom de la cible%
signifie qu'il s'agit d' une règle qui correspond à tout ; c'est-à-dire que si Make ne trouve aucun autre moyen de construire l'objet que vous lui dites de construire, il exécutera cette règle. Le@:
est une recette ; les:
moyens ne font rien, et les@
moyens le font en silence.%:
c'était en fait% :
un nom de cible de type générique. Je ne vois rien dans cette page de manuel concernant@:
cependant ... cela suggère qu'une règle "ne rien faire" aurait simplement un;
après la spécification cible, alors, ne serait-il pas plus précis d'écrire% : ;
comme le font le caractère générique -aucune règle "?filter-out
ne fonctionne pas lorsque l'action est une dépendance de la cible spécifiée sur la ligne de commande, car$@
elle sera définie sur le nom de la dépendance, et non sur l'argument d'origine appelé sur la ligne de commande. Au lieu de cela, j'assigneMAKECMDGOALS
à un tableau de shell puis supprime le premier élément:@ args=($(MAKECMDGOALS)); args=("$${args[@]:1}")
Voici une solution de travail générique basée sur @ Beta
J'utilise GNU Make 4.1 avec
SHELL=/bin/bash
au sommet de mon Makefile, donc YMMV!Cela nous permet d'accepter des arguments supplémentaires (en ne faisant rien lorsque nous obtenons un travail qui ne correspond pas, plutôt que de lancer une erreur).
Et c'est une macro qui obtient les arguments pour nous:
Voici un travail qui pourrait appeler celui-ci:
Le résultat serait:
Remarque! Vous feriez peut-être mieux d'utiliser un "Taskfile", qui est un modèle bash qui fonctionne de la même manière, mais sans les nuances de Maketools. Voir https://github.com/adriancooney/Taskfile
la source
tab
avant@echo
, nonspace
.Approche beaucoup plus facile. Considérez une tâche:
Maintenant, quand je veux l'appeler, je lance juste quelque chose comme:
AT="build assets" make provision
ou juste:
make provision
dans ce casAT
est une chaîne videla source
n'essaye pas de faire ça
créez plutôt un script:
et faites ceci:
pour plus d'explications sur pourquoi cela et les mises en garde concernant le piratage de makefile, lisez ma réponse à une autre question très similaire mais apparemment pas dupliquée: Passer des arguments pour "faire fonctionner"
la source