简体   繁体   English

从Thor类外部访问命令行参数

[英]Accessing command line arguments from outside of Thor class

Pretty new to Ruby and OO. 对Ruby和OO来说还很新。 Studying the text books, and all the articles that google found on Thor. 研究教科书以及Google在Thor上找到的所有文章。

I have Thor working to capture multiple command line arguments and options. 我让Thor工作来捕获多个命令行参数和选项。 I'd like to do the rest of my programming from outside the Cli < Thor class though, and am having trouble accessing the command line arguments from outside the Cli class. 不过,我想从Cli <Thor类之外进行其余的编程,并且无法从Cli类外部访问命令行参数。

Questions: 问题:

Q1. Q1。 Can the Cli < Thor class be treated like any other ruby class, or does inheriting from Thor, or the "Cli.start" command, cripple certain functionality of the Cli class versus not using Thor? 可以将Cli <Thor类与其他任何ruby类一样对待,还是可以继承自Thor或“ Cli.start”命令,从而削弱Cli类的某些功能而不是不使用Thor? Asking because I may simply not know how to access an instance variable from outside a class that doesn't use the initialize method. 问,因为我可能根本不知道如何从不使用initialize方法的类外部访问实例变量。 Thor will not let me use the initialize method to bring in the command line variables, probably because initialize is a reserved method name in ruby. Thor不会让我使用initialize方法来引入命令行变量,可能是因为initialize是ruby中的保留方法名称。

Q2. Q2。 How can I access the command line argument variables a and b from outside the Thor class? 如何从Thor类外部访问命令行参数变量a和b?

Here's my code 这是我的代码

#!/usr/bin/env ruby

require 'thor'

class Cli < Thor
  attr_reader :a, :b
  method_option :add, :type => :string, :desc => 'add servers'
  method_option :prod, :type => :string, :desc => 'production stack'

  desc "tier <stack folder name> <app | web>", "creates an app or web server tier for the stack"
  def tier(a,b)
    @a = a
    @b = b
    puts a
    puts b
  end
end

Cli.start

arguments = Cli.new

puts "the first argument is #{arguments.a}"

Here's the result. 这是结果。 Close (maybe). 关闭(也许)。 No errors, but arguments.a is nil. 没有错误,但是arguments.a为nil。

$ ./create.rb tier a b
a
b
the first argument is 

-- -

puts arguments.tier.a

threw the error: 抛出错误:

./create.rb:11:in `tier': wrong number of arguments (0 for 2) (ArgumentError)
    from ./create.rb:23:in `<main>'

The following works without Thor and using an initialize method and attr_reader, straight out of the text books. 以下内容在没有Thor的情况下可以直接在教科书中使用,并且使用初始化方法和attr_reader。 Can't figure out how to access the variables from a non-initialize method though. 虽然无法弄清楚如何从非初始化方法访问变量。

#!/usr/bin/env ruby

class Cli 
  attr_reader :a, :b
  def initialize(a,b)
    @a = a
    @b = b
  end
end

arguments = Cli.new("a","b")

puts arguments.a

outupt: outupt:

$ ./create_wo_thor.rb    
a

Instantiating your Cli class doesn't make much sense; 实例化Cli类没有多大意义。 that's not how Thor is designed. 那不是Thor设计的方式。

You have a few options to access internal data from outside the class. 您可以通过几种方法从班级外部访问内部数据。 If there are only a few variables that you want access to, storing them as class variables and making them available through getters (and setters, if you need them) would work: 如果只想访问几个变量,请将它们存储为类变量,并通过getter(如果需要,可以使用setter)使它们可用:

require 'thor'

class Cli < Thor
  method_option :add, :type => :string, :desc => 'add servers'
  method_option :prod, :type => :string, :desc => 'production stack'

  desc "tier <stack folder name> <app | web>", "creates an app or web server tier for the stack"
  def tier(a,b)
    @@a = a
    @@b = b
    puts a
    puts b
  end

  def self.get_a
    @@a
  end

  def self.get_b
    @@b
  end
end

Cli.start

puts "the first argument is #{Cli.get_a}"

This works as you hope: 这可以如您所愿:

$ ./thor.rb tier a b                                                                                                                                                                                                   
a                                                                                                                                                                                                                                           
b                                                                                                                                                                                                                                           
the first argument is a

I prefer the following, using a global Hash: 我更喜欢以下使用全局哈希的方法:

require 'thor'

$args = {}

class Cli < Thor
  method_option :add, :type => :string, :desc => 'add servers'
  method_option :prod, :type => :string, :desc => 'production stack'

  desc "tier <stack folder name> <app | web>", "creates an app or web server tier for the stack"
  def tier(a,b)
    $args[:a] = a
    $args[:b] = b
    puts a
    puts b
  end
end

Cli.start

puts "the first argument is #{$args[:a]}"

Last, I'd be remiss not to point out that all the command line arguments are available in the global ARGV , anyway: 最后,我不愿指出所有命令行参数在全局ARGV都可用,无论如何:

require 'thor'

class Cli < Thor
  method_option :add, :type => :string, :desc => 'add servers'
  method_option :prod, :type => :string, :desc => 'production stack'

  desc "tier <stack folder name> <app | web>", "creates an app or web server tier for the stack"
  def tier(a,b)
    puts a
    puts b
  end
end

Cli.start

puts "The first argugment is #{ARGV[1]}"

What would be best depends on how you intend to use it. 最佳选择取决于您打算如何使用它。 If you just want raw access to the command line arguments, ARGV is the way to go. 如果您只想对命令行参数进行原始访问,则可以使用ARGV If you want to access certain pieces after Thor has done some processing for you, one of the first two might be more helpful. 如果您想在Thor完成某些处理后访问某些作品,则前两个之一可能会更有帮助。

Here's my code with all three options included for accessing the command line arguments from outside the Cli < Thor class. 这是我的代码,其中包含所有三个选项,用于从Cli <Thor类之外访问命令行参数。 Compliments to Darshan. 赞扬达山。

#!/usr/bin/env ruby

require 'thor'
$args = {}

class Cli < Thor
  attr_reader :a, :b
  method_option :add, :type => :string, :desc => 'add servers'
  method_option :prod, :type => :string, :desc => 'production stack'

  desc "tier <stack folder name> <app | web>", "creates an app or web server tier for the stack"
  def tier(a,b)
    # store a and b in a global hash
    $args[:a] = a
    $args[:b] = b
    # store a and b in class variables 
    @@a = a
    @@b = b
  end

  # getter methods, for access of the class variables from outside the class
  def self.get_a
    @@a
  end
  def self.get_b
    @@b
  end
end

Cli.start

# three ways now to access the command line arguments from outside the Cli < Thor class
puts "the first argument, from $args[:a], is #{$args[:a]}"
puts "the second argument, from Cli.get_b, is #{Cli.get_b}"
puts "the first argument, from ARGV[1], is #{ARGV[1]}"

Results: 结果:

$ ./create.rb tier a b
the first argument, from $args[:a], is a
the second argument, from Cli.get_b, is b
the first argument, from ARGV[1], is a

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM