2017-03-01 2 views
0

Je souhaite obtenir l'indicateur d'option exact spécifié sur la ligne de commande depuis OptionParser de Ruby.Comment obtenir l'indicateur d'option spécifié depuis OptionParser

Par exemple, supposons que je le code suivant:

parser = OptionParser.new {                         
    |opts|                                                          
    opts.on('-f', '--file FILE', 'filename') {                        
    |arg|                             
    $filename = arg                         
    # Here I'd like to know whether '-f' or '--file' was entered 
    # on the command line.                    
    } 
    # ... etc. ... 
} 

Je voudrais savoir si l'utilisateur est arrivé sur la ligne de commande à taper « -f » ou « --file ». Est-ce possible sans écrire deux blocs séparés opts.on?

+3

Attendez, mais pourquoi ?? – ndn

+0

L'analyse du comportement de l'utilisateur @ndn? :) – mudasobwa

+0

@mudasobwa, sur une CLI? xd – ndn

Répondre

0

Je ne pense pas que vous puissiez faire passer les drapeaux à l'intérieur du bloc OptionParser.new. À ce moment-là, il est trop tard. Toutefois, avant l'analyse de la ligne de commande par OptionParser, il est possible de regarder et de voir ce qui est transmis.

ARGV contient la ligne de commande brute. Par exemple, si tel est l'invocation de ligne de commande pour un code:

foo -i 1 -j 2 

puis ARGV contiendra:

["-i", "1", "-j", "2"] 

et, il devient assez facile de saisir les drapeaux:

ARGV.grep(/^-/) # => ["-i", "-j"] 

Il existe d'autres outils semblables à OptionParser pour Ruby, et ceux-ci peuvent vous permettre d'accéder aux drapeaux utilisés, mais je ne peux pas penser à une raison dont je me soucierais. En regardant votre code, il semble que vous n'êtes pas comprendre comment utiliser OptionParser:

parser = OptionParser.new {                         
    |opts|                                                          
    opts.on('-f', '--file FILE', 'filename') {                        
    |arg|                             
    $filename = arg                         
    # Here I'd like to know whether '-f' or '--file' was entered 
    # on the command line.                    
    } 
    # ... etc. ... 
} 

lieu de le faire de cette façon, je l'écris:

options = {} 
OptionParser.new do |opts|                                                          
    opts.on('-f', '--file FILE', 'filename') { |arg| options[:filename] = arg } 
end.parse! 

if options[:filename] 
    puts 'exists' if File.exist?(options[:filename]) 
end 

Puis, plus tard dans votre code vous pouvez vérifier dans le hachage options pour voir si l'une des options -f ou --file a été donnée, et quelle était la valeur. Que ce soit l'un ou l'autre de -f ou --file ne devrait jamais avoir d'importance.

Si elle le fait, alors vous devez faire la différence entre les deux drapeaux, au lieu de les traiter comme si elles sont des alias:

options = {} 
OptionParser.new do |opts|                                                          
    opts.on('-f', 'filename') { |arg| options[:f] = arg } 
    opts.on('--file FILE', 'filename') { |arg| options[:file] = arg } 
end.parse! 

if options[:file] || options[:f] 
    puts 'exists' if File.exist?(options[:file] || options[:f]) 
end 
+0

Oui, j'ai fait quelque chose de similaire à cela. Je vois que l'obtention du drapeau d'option exacte n'est pas possible. J'ai mes propres raisons idiosyncratiques de vouloir obtenir la valeur exacte du drapeau, et j'ai donc abandonné OptionParser pour cette application particulière, et j'analyse simplement les arguments de la ligne de commande "à la main" (ie, en traversant ARGV moi-même dans ce cas). – HippoMan