Class: My::Script

Inherits:
Object
  • Object
show all
Defined in:
lib/my/script.rb

Overview

The My::Script class acts as a wrapper around the My script DSL. A My::Script instance is created with a string or a Proc argument, which is instantly evaluated, converting the standard script syntax:

file "app.rb" => "http://pastie.org/994577.txt"
folder "views"
folder "lib"

To a My::Script instance with a registered queue of files and folders to be created when run.

Instance Method Summary collapse

Constructor Details

#initialize(script) ⇒ Script

Creates a new Script and calls instance_eval on the script argument, either as a string or as a Proc.

My::Script.new("file 'app.rb' => 'http://pastie.org/994577.txt'")
  # => #<My::Script:0x7fc5aef84398 @folders=[], @files=[{:proc=>nil, :to=>"app.rb", :from=>"http://pastie.org/994577.txt"}], @questions=[]> 

My::Script.new(Proc.new{file "app.rb" => "http://pastie.org/994577.txt"})
  # => #<My::Script:0x7fc5aef84398 @folders=[], @files=[{:proc=>nil, :to=>"app.rb", :from=>"http://pastie.org/994577.txt"}], @questions=[]>


28
29
30
31
32
33
34
35
36
37
# File 'lib/my/script.rb', line 28

def initialize(script)
  @files = []
  @folders = []
  @questions = []
  if script.class == Proc
    instance_eval &script
  else
    instance_eval script
  end
end

Instance Method Details

#ask(query) ⇒ Object

Registers a new question, with the query parameter as the prompt for the user.

s = My::Script.new('')
s.ask("Would you like to use HAML instead of ERB?")


83
84
85
# File 'lib/my/script.rb', line 83

def ask(query)
  @questions << {:query => query}
end

#file(args, &block) ⇒ Object

Registers a file to be created, using the first key in the args hash as the :to attribute and the first value as the :from attribute. Optionally, a block can be passed to specify a context for populating variables, if the file specified is an ERB-templated file.

s = My::Script.new('')
s.file("app.rb" => "http://pastie.org/994577.txt")

s = My::Script.new('')
s.file("app.rb" => "http://pastie.org/994577.txt") do
  @app_name = "AwesomeApp"
end


62
63
64
# File 'lib/my/script.rb', line 62

def file(args,&block)
  @files << {:from => args.values[0], :to => args.keys[0], :proc => block}
end

#folder(name) ⇒ Object

Registers a folder to be created, using the name as the path to the folder.

s = My::Script.new('')
s.folder "views"

s = My::Script.new('')
s.folder "/home/gisikw/.vim"


74
75
76
# File 'lib/my/script.rb', line 74

def folder(name)
  @folders << name
end

#get_bindingObject

Returns the binding for the Script object.

s = My::Script.new('')
s.get_binding
  # => #<Binding:0x7fc5aef7fc80>


44
45
46
# File 'lib/my/script.rb', line 44

def get_binding
  return binding
end

#no(&block) ⇒ Object

Registers a Proc to be used with the most recent question, should the user respond negatively. The block passed in will be evaluated in the context of an empty script, and so can make use of any My::Script functionality.

s = My::Script.new('')
s.ask("Would you like to use HAML instead of ERB?")
s.no do
  file "views/index.erb" => "http://pastie.org/994577.txt"
end


115
116
117
118
119
# File 'lib/my/script.rb', line 115

def no(&block)
  unless @questions.empty?
    @questions.last[:no] = block
  end
end

#runObject

The run command does several tasks in executing the script in the following order:

  • Create all registered folders

  • Create all registered files, evaluating them with ERB if a block was passed

  • Ask all questions, spawning and executing a new script, using a Proc that corresponds to the user’s answer.

    s = Script.new %Q{
      ask "Are you sure you would like to apply this script?"
      yes do
        file "app.rb" => "http://pastie.org/994577.txt"
        folder "lib"
        folder "views"
        ask "Would you like to use HAML instead of ERB?"
        yes do
          file => "views/index.haml" => "http://pastie.org/994577.txt"
        end
        no do
          file => "views/index.erb" => "http://pastie.org/994577.txt"
        end
      end
    }
    s.run
    

produces:

Are you sure you would like to apply this script? [y/N]
  # The user types "y\n"
Would you like to use HAML instead of ERB?
  # The user types "n\n"

# folders ["lib","views"] have been created
# files ["app.rb","views/index.erb"] have been created


153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
# File 'lib/my/script.rb', line 153

def run
  @folders.each do |folder|
    FileUtils.mkdir_p(folder)
  end
  @files.each do |file|
    $stdout.puts "Writing file!"
    FileUtils.mkdir_p(File.dirname(file[:to]))
    if file[:proc]
      open(file[:to],'w').write(ERB.new(open(file[:from]).read).result(My::Script.new(file[:proc]).get_binding))
    else
      open(file[:to],'w').write(open(file[:from]).read)
    end
  end
  @questions.each do |question|
    $stdout.print "#{question[:query]} [y/N] "
    if $stdin.gets.chomp.downcase =~ /^y(?:es)?$/
      My::Script.new(question[:yes]||Proc.new{}).run
    else
      My::Script.new(question[:no]||Proc.new{}).run
    end
  end
end

#yes(&block) ⇒ Object

Registers a Proc to be used with the most recent question, should the user respond affirmatively. The block passed in will be evaluated in the context of an empty script, and so can make use of any My::Script functionality.

s = My::Script.new('')
s.ask("Would you like to use HAML instead of ERB?")
s.yes do
  file "views/index.haml" => "http://pastie.org/994577.txt"
end


98
99
100
101
102
# File 'lib/my/script.rb', line 98

def yes(&block)
  unless @questions.empty?
    @questions.last[:yes] = block
  end
end