module Buildr::DRbApplication
This addon allows you start a DRb server hosting a buildfile, so that you can later invoke tasks on it without having to load the complete buildr runtime again.
Usage:
buildr -r buildr/drb drb:start
Once the server has been started you can invoke tasks using a simple script:
#!/usr/bin/env ruby require 'rubygems' require 'buildr/drb' Buildr::DRbApplication.run
Save this script as 'dbuildr', make it executable and use it to invoke tasks.
dbuildr clean compile
The dbuildr script will run as the server if there isn't one already running. Subsequent calls to dbuildr will act as the client and invoke the tasks you provide in the server. If the buildfile has been modified it will be reloaded on the BuildrServer.
JRuby users can use a nailgun client to invoke tasks as fast as possible without having to incur JVM startup time. See the documentation for buildr/nailgun.
Constants
- PORT
Attributes
original[RW]
snapshot[RW]
Public Class Methods
client_uri()
click to toggle source
# File addon/buildr/drb.rb, line 116 def client_uri "druby://:#{PORT + 1}" end
remote_run(cfg)
click to toggle source
# File addon/buildr/drb.rb, line 120 def remote_run(cfg) with_config(cfg) { Buildr.application.remote_run(self) } rescue => e cfg[:err].puts e.message e.backtrace.each { |b| cfg[:err].puts "\tfrom #{b}" } raise e end
run()
click to toggle source
# File addon/buildr/drb.rb, line 106 def run begin client = connect rescue DRb::DRbConnError => e run_server! else run_client(client) end end
save_snapshot(app)
click to toggle source
# File addon/buildr/drb.rb, line 128 def save_snapshot(app) if app.instance_eval { @rakefile } @snapshot = self::Snapshot.new app.buildfile_reloaded! end end
Private Class Methods
connect()
click to toggle source
# File addon/buildr/drb.rb, line 141 def connect buildr = DRbObject.new(nil, server_uri) uri = buildr.client_uri # obtain our uri from the server DRb.start_service(uri) buildr end
delegate_stdio()
click to toggle source
# File addon/buildr/drb.rb, line 187 def delegate_stdio $stdin = SimpleDelegator.new($stdin) $stdout = SimpleDelegator.new($stdout) $stderr = SimpleDelegator.new($stderr) end
run_client(client)
click to toggle source
# File addon/buildr/drb.rb, line 148 def run_client(client) client.remote_run :dir => Dir.pwd, :argv => ARGV, :in => $stdin, :out => $stdout, :err => $stderr end
run_server()
click to toggle source
# File addon/buildr/drb.rb, line 170 def run_server setup DRb.start_service(server_uri, self) puts "#{self} waiting on #{server_uri}" end
run_server!()
click to toggle source
# File addon/buildr/drb.rb, line 176 def run_server! setup if RUBY_PLATFORM[/java/] require 'buildr/nailgun' Buildr.application['nailgun:drb'].invoke else run_server DRb.thread.join end end
server_uri()
click to toggle source
# File addon/buildr/drb.rb, line 137 def server_uri "druby://:#{PORT}" end
setup()
click to toggle source
# File addon/buildr/drb.rb, line 153 def setup unless original # Create the stdio delegator that can be cached (eg by fileutils) delegate_stdio # Lazily load buildr the first time it's needed require 'buildr' # Save the tasks,rules,layout defined by buildr # before loading any project @original = self::Snapshot.new Buildr.application.extend self save_snapshot(Buildr.application) end end
with_config(remote) { || ... }
click to toggle source
# File addon/buildr/drb.rb, line 193 def with_config(remote) @invoked = true set = lambda do |env| ARGV.replace env[:argv] $stdin.__setobj__(env[:in]) $stdout.__setobj__(env[:out]) $stderr.__setobj__(env[:err]) Buildr.application.instance_variable_set :@original_dir, env[:dir] end original = { :dir => Buildr.application.instance_variable_get(:@original_dir), :argv => ARGV, :in => $stdin.__getobj__, :out => $stdout.__getobj__, :err => $stderr.__getobj__ } begin set[remote] yield ensure set[original] end end
Public Instance Methods
buildfile_reloaded!()
click to toggle source
# File addon/buildr/drb.rb, line 234 def buildfile_reloaded! @last_loaded = buildfile.timestamp if @rakefile end
remote_run(server)
click to toggle source
# File addon/buildr/drb.rb, line 219 def remote_run(server) @options = server.original.options.clone init 'Distributed Buildr' if @rakefile if buildfile_needs_reload? reload_buildfile(server, server.original) else clear_invoked_tasks(server.snapshot || server.original) end else reload_buildfile(server, server.original) end top_level end
Private Instance Methods
buildfile_needs_reload?()
click to toggle source
# File addon/buildr/drb.rb, line 240 def buildfile_needs_reload? !@last_loaded || @last_loaded < buildfile.timestamp end
clear_for_reload(snapshot)
click to toggle source
# File addon/buildr/drb.rb, line 250 def clear_for_reload(snapshot) Project.clear @tasks = {} @rules = snapshot.rules.clone snapshot.tasks.each_pair { |name, saved| saved.define! } Layout.default = snapshot.layout.clone end
clear_invoked_tasks(snapshot)
click to toggle source
# File addon/buildr/drb.rb, line 258 def clear_invoked_tasks(snapshot) @rules = snapshot.rules.clone (@tasks.keys - snapshot.projects.keys).each do |name| if saved = snapshot.tasks[name] # reenable this task, restoring its actions/prereqs task = @tasks[name] task.reenable task.prerequisites.replace saved.prerequisites.clone task.actions.replace saved.actions.clone else # tasks generated at runtime, drop it @tasks.delete(name) end end end
reload_buildfile(server, snapshot)
click to toggle source
# File addon/buildr/drb.rb, line 244 def reload_buildfile(server, snapshot) clear_for_reload(snapshot) load_buildfile server.save_snapshot(self) end