All Downloads are FREE. Search and download functionalities are using the official Maven repository.

com.taobao.diamond.notify.utils.task.TaskManager Maven / Gradle / Ivy

There is a newer version: 3.2.4
Show newest version
package com.taobao.diamond.notify.utils.task;

import java.lang.management.ManagementFactory;
import java.util.Date;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.ReentrantLock;

import javax.management.ObjectName;

import com.taobao.middleware.logger.Logger;


import com.taobao.diamond.common.Constants;
import com.taobao.diamond.utils.LogUtils;


public final class TaskManager implements TaskManagerMBean {
    
    private static final Logger log = LogUtils.logger(TaskManager.class);

    private final ConcurrentHashMap tasks = new ConcurrentHashMap();

    private final ConcurrentHashMap taskProcessors =
            new ConcurrentHashMap();

    private TaskProcessor defaultTaskProcessor;

    Thread processingThread;

    private final AtomicBoolean closed = new AtomicBoolean(true);
    
    private String name;

    class ProcessRunnable implements Runnable {

        public void run() {
            while (!TaskManager.this.closed.get()) {
                try {
                    Thread.sleep(100);
                    TaskManager.this.process();
                }
                catch (Throwable e) {
                }
            }

        }

    }

    ReentrantLock lock = new ReentrantLock();

    Condition notEmpty = this.lock.newCondition();


    public TaskManager() {
        this(null);
    }


    public Task getTask(String type) {
        return this.tasks.get(type);
    }


    public TaskProcessor getTaskProcessor(String type) {
        return this.taskProcessors.get(type);
    }


    public TaskManager(String name) {
        this.name = name;
        if (null != name && name.length() > 0) {
            this.processingThread = new Thread(new ProcessRunnable(), name);
        }
        else {
            this.processingThread = new Thread(new ProcessRunnable());
        }
        this.processingThread.setDaemon(true);
        this.closed.set(false);
        this.processingThread.start();
    }

    public int size() {
        return tasks.size();
    }

    public void close() {
        this.closed.set(true);
        this.processingThread.interrupt();
    }


    public void await() throws InterruptedException {
        this.lock.lock();
        try {
            while (!this.isEmpty()) {
                this.notEmpty.await();
            }
        }
        finally {
            this.lock.unlock();
        }
    }


    public void await(long timeout, TimeUnit unit) throws InterruptedException {
        this.lock.lock();
        try {
            while (!this.isEmpty()) {
                this.notEmpty.await(timeout, unit);
            }
        }
        finally {
            this.lock.unlock();
        }
    }


    public void addProcessor(String type, TaskProcessor taskProcessor) {
        this.taskProcessors.put(type, taskProcessor);
    }


    public void removeProcessor(String type) {
        this.taskProcessors.remove(type);
    }


    public void removeTask(String type) {
        this.lock.lock();
        try {
            this.tasks.remove(type);
        }
        finally {
            this.lock.unlock();
        }
    }


    public void addTask(String type, Task task) {
        this.lock.lock();
        try {
            Task oldTask = tasks.put(type, task);
            if (null != oldTask) {
                task.merge(oldTask);
            }
        } finally {
            this.lock.unlock();
        }
    }


    protected void process() {
        for (Map.Entry entry : this.tasks.entrySet()) {
            Task task = null;
            this.lock.lock();
            try {
                task = entry.getValue();
                if (null != task) {
                    if (!task.shouldProcess()) {
                        continue;
                    }
                    this.tasks.remove(entry.getKey());
                }
            }
            finally {
                this.lock.unlock();
            }

            if (null != task) {
                TaskProcessor processor = this.taskProcessors.get(entry.getKey());
                if (null == processor) {
                    processor = this.getDefaultTaskProcessor();
                }
                if (null != processor) {
                    boolean result = false;
                    try {
                        result = processor.process(entry.getKey(), task);
                    }
                    catch (Throwable t) {
						log.error("task_fail", "", t);
                    }
                    if (!result) {
                        task.setLastProcessTime(System.currentTimeMillis());

                        this.addTask(entry.getKey(), task);
                    }
                }
            }
        }

        if (tasks.isEmpty()) {
            this.lock.lock();
            try {
                this.notEmpty.signalAll();
            }
            finally {
                this.lock.unlock();
            }
        }
    }


    public boolean isEmpty() {
        return tasks.isEmpty();
    }


    public TaskProcessor getDefaultTaskProcessor() {
        this.lock.lock();
        try {
            return this.defaultTaskProcessor;
        }
        finally {
            this.lock.unlock();
        }
    }


    public void setDefaultTaskProcessor(TaskProcessor defaultTaskProcessor) {
        this.lock.lock();
        try {
            this.defaultTaskProcessor = defaultTaskProcessor;
        }
        finally {
            this.lock.unlock();
        }
    }


    public String getTaskInfos() {
        StringBuilder sb = new StringBuilder();
        for(String taskType: this.taskProcessors.keySet()) {
            sb.append(taskType).append(":");
            Task task = this.tasks.get(taskType);
            if(task != null) {
                sb.append(new Date(task.getLastProcessTime()).toString());
            } else {
                sb.append("finished");
            }
            sb.append(Constants.DIAMOND_LINE_SEPARATOR);
        }
        
        return sb.toString();
    }
    
    
    public void init() {
        try {
            ObjectName oName = new ObjectName(this.name + ":type=" + TaskManager.class.getSimpleName());
            ManagementFactory.getPlatformMBeanServer().registerMBean(this, oName);
        }
        catch (Exception e) {
			log.error("registerMBean_fail", "", e);
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy