You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@roller.apache.org by ag...@apache.org on 2007/07/27 22:04:04 UTC

svn commit: r560368 - in /roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business: hibernate/HibernateThreadManagerImpl.java jpa/JPAThreadManagerImpl.java runnable/TaskScheduler.java runnable/ThreadManagerImpl.java

Author: agilliland
Date: Fri Jul 27 13:04:02 2007
New Revision: 560368

URL: http://svn.apache.org/viewvc?view=rev&rev=560368
Log:
a couple fixes for task scheduler.

1. the new scheduler expects the tasklock entry to exist in the db before running a task, so the initialization process for the thread manager has been updated such that all enabled tasks are checked for an a tasklock record and if it doesn't exist it is created.

2. added in a small amount of time adjustment to the scheduler so that it tries to reawaken each minute a small amount of time after the beginning of the first second rather than right at the zeroith millisecond.  this accounts for possible imprecisions in the way the sleep time is chosen.

Modified:
    roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/hibernate/HibernateThreadManagerImpl.java
    roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/jpa/JPAThreadManagerImpl.java
    roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/TaskScheduler.java
    roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/ThreadManagerImpl.java

Modified: roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/hibernate/HibernateThreadManagerImpl.java
URL: http://svn.apache.org/viewvc/roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/hibernate/HibernateThreadManagerImpl.java?view=diff&rev=560368&r1=560367&r2=560368
==============================================================================
--- roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/hibernate/HibernateThreadManagerImpl.java (original)
+++ roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/hibernate/HibernateThreadManagerImpl.java Fri Jul 27 13:04:02 2007
@@ -73,30 +73,17 @@
         // query for existing lease record first
         TaskLock taskLock = null;
         try {
-            taskLock = this.getTaskLockByName(task.getName());
-            
+            taskLock = getTaskLockByName(task.getName());
             if(taskLock == null) {
-                log.debug("Task record does not exist, inserting empty record to start with");
-                
-                // insert an empty record, then we will actually acquire the
-                // lease below using an update statement 
-                taskLock = new TaskLock();
-                taskLock.setName(task.getName());
-                taskLock.setTimeAquired(new Date(0));
-                taskLock.setTimeLeased(0);
-                
-                // save it and flush
-                this.saveTaskLock(taskLock);
-                roller.flush();
+                log.warn("Cannot acquire lease when no tasklock record exists for task - "+task.getName());
             }
-            
         } catch (WebloggerException ex) {
-            log.warn("Error getting or inserting TaskLock", ex);
+            log.warn("Error getting TaskLock", ex);
             return false;
         }
         
         // try to acquire lease
-        try {
+        if(taskLock != null) try {
             // calculate lease expiration time
             Date leaseExpiration = taskLock.getLeaseExpiration();
             

Modified: roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/jpa/JPAThreadManagerImpl.java
URL: http://svn.apache.org/viewvc/roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/jpa/JPAThreadManagerImpl.java?view=diff&rev=560368&r1=560367&r2=560368
==============================================================================
--- roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/jpa/JPAThreadManagerImpl.java (original)
+++ roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/jpa/JPAThreadManagerImpl.java Fri Jul 27 13:04:02 2007
@@ -72,30 +72,17 @@
         // query for existing lease record first
         TaskLock taskLock = null;
         try {
-            taskLock = this.getTaskLockByName(task.getName());
-
+            taskLock = getTaskLockByName(task.getName());
             if(taskLock == null) {
-                log.debug("Task record does not exist, inserting empty record to start with");
-                
-                // insert an empty record, then we will actually acquire the
-                // lease below using an update statement
-                taskLock = new TaskLock();
-                taskLock.setName(task.getName());
-                taskLock.setTimeAquired(new Date(0));
-                taskLock.setTimeLeased(0);
-
-                // save it and flush
-                this.saveTaskLock(taskLock);
-                roller.flush();
+                log.warn("Cannot acquire lease when no tasklock record exists for task - "+task.getName());
             }
-
         } catch (WebloggerException ex) {
-            log.warn("Error getting or inserting TaskLock", ex);
+            log.warn("Error getting TaskLock", ex);
             return false;
         }
 
         // try to acquire lease
-        try {
+        if(taskLock != null) try {
             // calculate lease expiration time
             Date leaseExpiration = taskLock.getLeaseExpiration();
             

Modified: roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/TaskScheduler.java
URL: http://svn.apache.org/viewvc/roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/TaskScheduler.java?view=diff&rev=560368&r1=560367&r2=560368
==============================================================================
--- roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/TaskScheduler.java (original)
+++ roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/TaskScheduler.java Fri Jul 27 13:04:02 2007
@@ -18,7 +18,6 @@
 
 package org.apache.roller.weblogger.business.runnable;
 
-import java.util.ArrayList;
 import java.util.Calendar;
 import java.util.Date;
 import java.util.List;
@@ -50,21 +49,19 @@
     private static final long ONE_MINUTE_MS = (60 * 1000);
     
     private final ExecutorService pool;
-    private List<RollerTask> tasks = new ArrayList<RollerTask>();
+    private final List<RollerTask> tasks;
     
     
-    public TaskScheduler() {
+    public TaskScheduler(List<RollerTask> webloggerTasks) {
+        
+        // store list of tasks available to run
+        tasks = webloggerTasks;
+        
         // use an expanding thread executor pool
         pool = Executors.newCachedThreadPool();
     }
     
     
-    // TODO: this should probably be a constructor arg so the list can be final
-    public void scheduleTask(RollerTask task) {
-        tasks.add(task);
-    }
-    
-    
     public void run() {
         
         boolean firstRun = true;
@@ -72,7 +69,7 @@
         // run forever, or until we get interrupted
         while(true) {
             try {
-                // get current time (from db?)
+                // get current time
                 Date now = new Date();
                 log.debug("Current time = "+now);
                 
@@ -98,10 +95,22 @@
                 }
                 
                 // wait 'til next minute
-                // TODO: make sure we don't get a negative value here
+                // NOTE: we add 50ms of adjustment time to make sure we awaken
+                //       during the next minute, and not before.  awakening at
+                //       exactly the .000ms is not of any concern to us
                 Date endOfMinute = DateUtil.getEndOfMinute(now);
-                log.debug("sleeping - "+(endOfMinute.getTime() - System.currentTimeMillis()));
-                Thread.sleep(endOfMinute.getTime() - System.currentTimeMillis());
+                long sleepTime = (endOfMinute.getTime() + 50) - System.currentTimeMillis();
+                if(sleepTime > 0) {
+                    log.debug("sleeping - "+sleepTime);
+                    Thread.sleep(sleepTime);
+                } else {
+                    // it's taken us more than 1 minute for the last loop
+                    // so recalculate to sleep 'til the end of the current minute
+                    endOfMinute = DateUtil.getEndOfMinute(new Date());
+                    sleepTime = (endOfMinute.getTime() + 50) - System.currentTimeMillis();
+                    log.debug("sleeping - "+sleepTime);
+                    Thread.sleep(sleepTime);
+                }
                 
             } catch (InterruptedException ex) {
                 // thread interrupted

Modified: roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/ThreadManagerImpl.java
URL: http://svn.apache.org/viewvc/roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/ThreadManagerImpl.java?view=diff&rev=560368&r1=560367&r2=560368
==============================================================================
--- roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/ThreadManagerImpl.java (original)
+++ roller/trunk/apps/weblogger/src/java/org/apache/roller/weblogger/business/runnable/ThreadManagerImpl.java Fri Jul 27 13:04:02 2007
@@ -18,6 +18,9 @@
 
 package org.apache.roller.weblogger.business.runnable;
 
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
 import java.util.concurrent.ExecutorService;
 import java.util.concurrent.Executors;
 import java.util.concurrent.Future;
@@ -27,6 +30,7 @@
 import org.apache.roller.weblogger.WebloggerException;
 import org.apache.roller.weblogger.business.InitializationException;
 import org.apache.roller.weblogger.config.WebloggerConfig;
+import org.apache.roller.weblogger.pojos.TaskLock;
 
 
 /**
@@ -53,26 +57,40 @@
     
     
     public void initialize() throws InitializationException {
-        
-        // create scheduler
-        TaskScheduler scheduler = new TaskScheduler();
                     
-        // okay, first we look for what tasks have been enabled
+        // initialize tasks, making sure that each task has a tasklock record in the db
+        List<RollerTask> webloggerTasks = new ArrayList<RollerTask>();
         String tasksStr = WebloggerConfig.getProperty("tasks.enabled");
         String[] tasks = StringUtils.stripAll(StringUtils.split(tasksStr, ","));
-        for (int i=0; i < tasks.length; i++) {
+        for ( String taskName : tasks ) {
             
-            String taskClassName = WebloggerConfig.getProperty("tasks."+tasks[i]+".class");
+            String taskClassName = WebloggerConfig.getProperty("tasks."+taskName+".class");
             if(taskClassName != null) {
-                log.info("Initializing task: "+tasks[i]);
+                log.info("Initializing task: "+taskName);
                 
                 try {
                     Class taskClass = Class.forName(taskClassName);
                     RollerTask task = (RollerTask) taskClass.newInstance();
                     task.init();
                     
-                    // schedule it
-                    scheduler.scheduleTask(task);
+                    // make sure there is a tasklock record in the db
+                    TaskLock taskLock = getTaskLockByName(task.getName());
+                    if (taskLock == null) {
+                        log.debug("Task record does not exist, inserting empty record to start with");
+
+                        // insert an empty record
+                        taskLock = new TaskLock();
+                        taskLock.setName(task.getName());
+                        taskLock.setLastRun(new Date(0));
+                        taskLock.setTimeAquired(new Date(0));
+                        taskLock.setTimeLeased(0);
+
+                        // save it
+                        this.saveTaskLock(taskLock);
+                    }
+                    
+                    // add it to the list of configured tasks
+                    webloggerTasks.add(task);
                     
                 } catch (ClassCastException ex) {
                     log.warn("Task does not extend RollerTask class", ex);
@@ -84,10 +102,15 @@
             }
         }
         
-        // only start if we aren't already running
+        // create scheduler
+        TaskScheduler scheduler = new TaskScheduler(webloggerTasks);
+        
+        // start scheduler thread, but only if it's not already running
         if (schedulerThread == null && scheduler != null) {
             log.debug("Starting scheduler thread");
             schedulerThread = new Thread(scheduler, "Roller Weblogger Task Scheduler");
+            // set thread priority between MAX and NORM so we get slightly preferential treatment
+            schedulerThread.setPriority((Thread.MAX_PRIORITY + Thread.NORM_PRIORITY)/2);
             schedulerThread.start();
         }
     }