class Rake::Task


use the file and task convenience methods.
Tasks are not usually created directly using the new method, but rather
opportunity to run and then it will execute its own actions.
invoked, a task will first ensure that all of its prerequisites have an
actions (possibly more than one) and a list of prerequisites. When
A Task is the basic unit of work in a Rakefile. Tasks have associated
#########################################################################

def [](task_name)

task with no dependencies or actions.
found, but an existing file matches the task name, assume it is a file
known, try to synthesize one from the defined rules. If no rules are
Return a task with the given name. If the task is not currently
def [](task_name)
  Rake.application[task_name]
end

def add_comment(comment)

the new comment with " / ".
Add a comment to the task. If a comment alread exists, separate
def add_comment(comment)
  if @full_comment
    @full_comment << " / "
  else
    @full_comment = ''
  end
  @full_comment << comment
  if @full_comment =~ /\A([^.]+?\.)( |$)/
    @comment = $1
  else
    @comment = @full_comment
  end
end

def add_description(description)

argument list (enclosed brackets) and an optional comment.
Add a description to the task. The description can consist of an option
def add_description(description)
  return if ! description
  comment = description.strip
  add_comment(comment) if comment && ! comment.empty?
end

def arg_description # :nodoc:

:nodoc:
Argument description (nil if none).
def arg_description # :nodoc:
  @arg_names ? "[#{(arg_names || []).join(',')}]" : nil
end

def arg_names

Name of arguments for this task.
def arg_names
  @arg_names || []
end

def clear

tasks that have been assigned. (Normally used in the unit tests.)
Clear the task list. This cause rake to immediately forget all the
def clear
  Rake.application.clear
end

def comment=(description)

Writing to the comment attribute is the same as adding a description.
def comment=(description)
  add_description(description)
end

def create_rule(*args, &block)

Define a rule for synthesizing tasks.
def create_rule(*args, &block)
  Rake.application.create_rule(*args, &block)
end

def define_task(*args, &block)

the existing task. Returns the defined task.
given name already exists, the prerequisites and actions are added to
Define a task given +args+ and an option block. If a rule with the
def define_task(*args, &block)
  Rake.application.define_task(self, *args, &block)
end

def enhance(deps=nil, &block)

Enhance a task with prerequisites or actions. Returns self.
def enhance(deps=nil, &block)
  @prerequisites |= deps if deps
  @actions << block if block_given?
  self
end

def execute(args)

Execute the actions associated with this task.
def execute(args)
  if application.options.dryrun
    puts "** Execute (dry run) #{name}"
    return
  end
  if application.options.trace
    puts "** Execute #{name}"
  end
  application.enhance_with_matching_rule(name) if @actions.empty?
  @actions.each do |act|
    case act.arity
    when 1
      act.call(self)
    else
      act.call(self, args)
    end
  end
end

def format_trace_flags

Format the trace flags for display.
def format_trace_flags
  flags = []
  flags << "first_time" unless @already_invoked
  flags << "not_needed" unless needed?
  flags.empty? ? "" : "(" + flags.join(", ") + ")"
end

def initialize(task_name, app)

+enhance+ to add actions and prerequisites.
Create a task named +task_name+ with no actions or prerequisites. Use
def initialize(task_name, app)
  @name = task_name.to_s
  @prerequisites = FileList[]
  @actions = []
  @already_invoked = false
  @full_comment = nil
  @comment = nil
  @lock = Mutex.new
  @application = app
  @scope = app.current_scope
  @arg_names = nil
end

def inspect

def inspect
  "<#{self.class} #{name} => [#{prerequisites.join(', ')}]>"
end

def investigation

debugging.
Return a string describing the internal state of a task. Useful for
def investigation
  result = "------------------------------\n"
  result << "Investigating #{name}\n"
  result << "class: #{self.class}\n"
  result <<  "task needed: #{needed?}\n"
  result <<  "timestamp: #{timestamp}\n"
  result << "pre-requisites: \n"
  prereqs = @prerequisites.collect {|name| application[name]}
  prereqs.sort! {|a,b| a.timestamp <=> b.timestamp}
  prereqs.each do |p|
    result << "--#{p.name} (#{p.timestamp})\n"
  end
  latest_prereq = @prerequisites.collect{|n| application[n].timestamp}.max
  result <<  "latest-prerequisite time: #{latest_prereq}\n"
  result << "................................\n\n"
  return result
end

def invoke(*args)

Invoke the task if it is needed. Prerequites are invoked first.
def invoke(*args)
  task_args = TaskArguments.new(arg_names, args)
  invoke_with_call_chain(task_args, InvocationChain::EMPTY)
end

def invoke_prerequisites(task_args, invocation_chain)

Invoke all the prerequisites of a task.
def invoke_prerequisites(task_args, invocation_chain)
  @prerequisites.each { |n|
    prereq = application[n, @scope]
    prereq_args = task_args.new_scope(prereq.arg_names)
    prereq.invoke_with_call_chain(prereq_args, invocation_chain)
  }
end

def invoke_with_call_chain(task_args, invocation_chain)

circular dependencies.
Same as invoke, but explicitly pass a call chain to detect
def invoke_with_call_chain(task_args, invocation_chain)
  new_chain = InvocationChain.append(self, invocation_chain)
  @lock.synchronize do
    if application.options.trace
      puts "** Invoke #{name} #{format_trace_flags}"
    end
    return if @already_invoked
    @already_invoked = true
    invoke_prerequisites(task_args, new_chain)
    execute(task_args) if needed?
  end
end

def name

Name of the task, including any namespace qualifiers.
def name
  @name.to_s
end

def name_with_args # :nodoc:

:nodoc:
Name of task with argument list description.
def name_with_args # :nodoc:
  if arg_description
    "#{name}#{arg_description}"
  else
    name
  end
end

def needed?

Is this task needed?
def needed?
  true
end

def scope_name(scope, task_name)

part of the name.
this kind of task. Generic tasks will accept the scope as
Apply the scope to the task name according to the rules for
def scope_name(scope, task_name)
  (scope + [task_name]).join(':')
end

def set_arg_names(args)

an array of symbols, one for each argument name.
Set the names of the arguments for this task. +args+ should be
def set_arg_names(args)
  @arg_names = args.map { |a| a.to_sym }
end

def source

First source from a rule (nil if no sources)
def source
  @sources.first if defined?(@sources)
end

def sources

def sources
  @sources ||= []
end

def task_defined?(task_name)

TRUE if the task name is already defined.
def task_defined?(task_name)
  Rake.application.lookup(task_name) != nil
end

def tasks

List of all defined tasks.
def tasks
  Rake.application.tasks
end

def timestamp

time stamp. Other tasks can be more sophisticated.
Timestamp for this task. Basic tasks return the current time for their
def timestamp
  @prerequisites.collect { |p| application[p].timestamp }.max || Time.now
end

def to_s

Return task name
def to_s
  name
end