Module: Command::DSL::Action
Overview
The methods available within the DSL::CommandDefinition#action method
The trickiest thing to realize about writing Commands is that a CommandSet is an object that contains several Command subclasses; Commad::setup creates a subclass, and so CommandSet#command does too. It’s when a command is invoked that it’s actually instantiated.
Also note that you can access the arguments of a command as read-only attributes, and you can write to and read from instance variables, which will be local to the invocation of the command. This is especially useful for undo and redo.
Instance Method Summary collapse
-
#action_thread(&block) ⇒ Object
These methods are nodoc’d because at present, they don’t work.
-
#chain(klass_or_path, args) ⇒ Object
It frequently makes sense to offer shortcut chains to the user, or even commands that can only be run as part of another command.
-
#chain_first(klass_or_path, args) ⇒ Object
Like #chain, but interjects the command being chained to the start of the queue, immediately after this command completes.
-
#defer(deck = nil) ⇒ Object
Stop here and return control to the user.
-
#dont_undo ⇒ Object
Some commands sometimes cause side effects.
-
#farm_out(array, thread_count, &block) ⇒ Object
:nodoc:.
-
#interruptable ⇒ Object
This method is deprecated but remains as a nicety.
-
#pause(deck = nil) ⇒ Object
Stop here.
-
#sub_collector ⇒ Object
This returns a new Results::Collector, which can allow for some very sophisticated command output.
-
#subject ⇒ Object
This is how you’ll access the Command::Subject object that’s the interface of every command to the program state.
-
#task(id) ⇒ Object
Allows for a command to be broken into pieces so that a resume can pick up within a command.
-
#undo(box) ⇒ Object
Not normally called from within an #action block, this provides the default behavior for an undo (raise an exception).
Methods included from Formatting
#begin_list, #end_list, #item, #list
Instance Method Details
#action_thread(&block) ⇒ Object
These methods are nodoc’d because at present, they don’t work. They’d be awesome for big jobs - splitting them into subthreads and such. But they need to be debugged, and IIRC there’s a deadlock condition
528 529 530 531 532 533 534 535 |
# File 'lib/command-set/dsl.rb', line 528 def action_thread(&block) #:nodoc: return Thread.new do collector = sub_collector $stdout.set_thread_collector(collector) block.call $stdout.remove_thread_collector(collector) end end |
#chain(klass_or_path, args) ⇒ Object
It frequently makes sense to offer shortcut chains to the user, or even commands that can only be run as part of another command. Calling chain with either a command class or a command path allows will cause that command to be invoked before returning control to the user.
484 485 486 487 488 489 |
# File 'lib/command-set/dsl.rb', line 484 def chain(klass_or_path, args) setup = CommandSetup.new setup.command = klass_or_path setup.args_hash = args || {} subject.chain_of_command.push(setup) end |
#chain_first(klass_or_path, args) ⇒ Object
Like #chain, but interjects the command being chained to the start of the queue, immediately after this command completes.
493 494 495 496 497 498 |
# File 'lib/command-set/dsl.rb', line 493 def chain_first(klass_or_path, args) setup = CommandSetup.new setup.command = klass_or_path setup.args_hash = args subject.chain_of_command.unshift(setup) end |
#defer(deck = nil) ⇒ Object
Stop here and return control to the user. If several commands are chained (c.f. #chain) and the pause is subsequently resumed (StandardCommands::Resume) the rest of the chain (not this command) will be dropped.
458 459 460 |
# File 'lib/command-set/dsl.rb', line 458 def defer(deck = nil) raise ResumeFromOnlyThis, deck end |
#dont_undo ⇒ Object
Some commands sometimes cause side effects. When evaluating arguments, if you discover that undoing doesn’t make sense, and will be confusing to the user, call dont_undo, and the interpreter will ignore the call for purposes of undoing
434 435 436 437 |
# File 'lib/command-set/dsl.rb', line 434 def dont_undo @should_undo = false return nil end |
#farm_out(array, thread_count, &block) ⇒ Object
:nodoc:
538 539 540 541 542 543 544 545 546 547 548 549 550 551 552 553 |
# File 'lib/command-set/dsl.rb', line 538 def farm_out(array, thread_count, &block) #:nodoc: first_batch = (array[0...thread_count]||[]).map do |item| action_thread { block.call(item) } end rest = (array[thread_count..-1] || []) waiter = ThreadsWait.new(*first_batch) rest.each do |item| waiter.next_wait waiter.join_nowait(action_thread{block.call(item)}) end waiter.join end |
#interruptable ⇒ Object
This method is deprecated but remains as a nicety. As it stands, any command can be interrupted at the command line with Ctrl-C, and return to the prompt.
520 521 522 |
# File 'lib/command-set/dsl.rb', line 520 def interruptable yield end |
#pause(deck = nil) ⇒ Object
Stop here. Return control to the user. If several commands are chained (c.f. #chain) and the pause is subsequently resumed (StandardCommands::Resume) the whole chain will be resumed.
450 451 452 |
# File 'lib/command-set/dsl.rb', line 450 def pause(deck = nil) raise ResumeFrom, deck end |
#sub_collector ⇒ Object
This returns a new Results::Collector, which can allow for some very sophisticated command output. Specifically, it can allow a command to loop over a large amount of data once, depositing output in multiple lists at once, for instance a status list (with hashmarks) and results(with useful data) list.
513 514 515 |
# File 'lib/command-set/dsl.rb', line 513 def sub_collector @main_collector.dup end |
#subject ⇒ Object
This is how you’ll access the Command::Subject object that’s the interface of every command to the program state.
441 442 443 |
# File 'lib/command-set/dsl.rb', line 441 def subject @subject end |
#task(id) ⇒ Object
Allows for a command to be broken into pieces so that a resume can pick up within a command. The block will be executed normally, but if the command is resumed with a task id, all task blocks until that id will be skipped.
466 467 468 469 470 471 472 473 474 475 |
# File 'lib/command-set/dsl.rb', line 466 def task(id) #:yield: if not @resume_from.nil? if @resume_from == id @resume_from = nil end return end yield if block_given? @last_completed_task = id end |
#undo(box) ⇒ Object
Not normally called from within an #action block, this provides the default behavior for an undo (raise an exception)
504 505 506 |
# File 'lib/command-set/dsl.rb', line 504 def undo(box) raise CommandException, "#{@name} cannot be undone" end |