分布式任务分解树,针对元数据和中间结果数据作树状任务分解.

 

#====================(^_^)====================
#desc: 分布式任务分解树, 可支持 分布式/并行/并发 任务执行
#核心: 任务树的容错方式为continue, 单个节点的任务分解和任务执行为atomic执行, 容错方式为redo
#author: edisonpeng
#last-modified: 2008-08-14
#====================(^_^)====================

class TaskNode
  Pending = 0
  Executing = 1
  Executed = 2
  Resolving = 3
  Resolved = 4
 
  attr_accessor :type, :name, :path, :data, :state
  def initialize(type, name, path, data)
    @type = type
    @name = name
    @path = path
    @data = data
    @state = Pending
  end
end


class TaskNodeHandler
  def on_execute(task)
    puts "on_execute: #{task.type}, #{task.path}"
  end
 
  def on_expand(task)
    return nil
  end
end

class LockServer
  def initialize(ip, port)
    puts "LockServer.init(#{ip}, #{port})"
    @path2children = Hash.new
  end
 
  def update(task)
    puts "  LockServer.update #{task.path} #{task.state}"
    return true;
  end
 
  def add(task)
    puts "  LockServer.add #{task.path}"
    return true;
  end
 
  def get(path)
    task = TaskNode.new 1, "task1", "task data"
    return task
  end
 
  def get_children(path)
    puts "  LockServer.get_children #{path}"
    return if path != "/"

    tasks = Array.new
    task1 =TaskNode.new 1, "task1", path+"task1/", "task data1"
    task2 = TaskNode.new 2, "task2", path+"task2/", "task data2"
    tasks.push task1
    tasks.push task2
    return tasks
  end
 
  def delete(path)
    puts "  LockServer.delete(#{path})"
    return true
  end
end


class DistributedTaskResolvingTree
 
  def initialize(ip, port)
    @lockServer = LockServer.new ip, port
    @handlers = Hash.new
  end
 
  def set_handler(type, handler)
    @handlers[type] = handler
  end
 
  def expand_task(task, handler)
    puts "expand_task #{task.type}"
   
    task.state = TaskNode::Resolving
    #如果子任务节点已经被展开了,noop
    if @lockServer.update task
      children = handler.on_expand task
      if children!=nil
        children.each{|child|
          @lockServer.add child
        }
      end
      task.state = TaskNode::Resolved
      @lockServer.update task
    end
  end

  def execute_task(task, handler)
    task.state = TaskNode::Executing
    #如果
    if @lockServer.update task
      #钩子函数
      handler.on_execute task
      task.state = TaskNode::Executed
      @lockServer.update task
    end

    expand_task task, handler
   
    #从此处开始,子任务可以被 多机/进程/线程 分布式/并行/并发 执行.
    children = @lockServer.get_children task.path

    if children!=nil
      children.each{|child|
        child_handler = @handlers[child.type]
        execute_task child, child_handler if child_handler!=nil
      }
    end
   
    #任务执行完毕,删除自身节点
    @lockServer.delete task.path
  end
 
  def run task
    handler = @handlers[task.type]
    execute_task task, handler
  end
end


class RootHandler < TaskNodeHandler
  def on_execute task
    puts "    RootHandler.on_execute #{task.path}"
  end
 
  def on_expand task
    puts "    RootHandler.on_expand #{task.path}"
    tasks = Array.new
    task1 =TaskNode.new 1, "task1", task.path+"task1/", "task data1"
    task2 = TaskNode.new 2, "task2", task.path+"task2/", "task data2"
    tasks.push task1
    tasks.push task2
    return tasks
  end
end

class ChildHandler < TaskNodeHandler
  def on_execute task
    puts "    ChildHandler.on_execute #{task.path}"
  end
 
  def on_expand task
    puts "    ChildHandler.on_expand #{task.path}"
    return nil
  end
end


puts "=====begin====="
begin
  dtrt = DistributedTaskResolvingTree.new "172.1.1.1", 8088
  dtrt.set_handler(0, RootHandler.new)
  child_handler = ChildHandler.new
  dtrt.set_handler(1, child_handler)
  dtrt.set_handler(2, child_handler)
 
  Root = TaskNode.new 0, "root", "/", nil
  dtrt.run Root
end
puts "=====end====="

posted on 2008-08-15 01:41  彭帅  阅读(398)  评论(0)    收藏  举报