continuum-commits mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From batkin...@apache.org
Subject svn commit: r1674638 - in /continuum/trunk: continuum-api/src/main/java/org/apache/continuum/dao/ continuum-core/src/main/java/org/apache/continuum/builder/ continuum-core/src/test/java/org/apache/continuum/builder/ continuum-store/src/main/java/org/ap...
Date Sun, 19 Apr 2015 16:32:38 GMT
Author: batkinson
Date: Sun Apr 19 16:32:37 2015
New Revision: 1674638

URL: http://svn.apache.org/r1674638
Log:
Modified orphan scanning to: consider more cases, run less frequently, set endtimes and log
affected ids

Modified:
    continuum/trunk/continuum-api/src/main/java/org/apache/continuum/dao/BuildResultDao.java
    continuum/trunk/continuum-core/src/main/java/org/apache/continuum/builder/OrphanBuildStatusUpdater.java
    continuum/trunk/continuum-core/src/test/java/org/apache/continuum/builder/OrphanBuildStatusUpdaterTest.java
    continuum/trunk/continuum-store/src/main/java/org/apache/continuum/dao/BuildResultDaoImpl.java
    continuum/trunk/continuum-webapp/src/main/webapp/WEB-INF/applicationContext.xml

Modified: continuum/trunk/continuum-api/src/main/java/org/apache/continuum/dao/BuildResultDao.java
URL: http://svn.apache.org/viewvc/continuum/trunk/continuum-api/src/main/java/org/apache/continuum/dao/BuildResultDao.java?rev=1674638&r1=1674637&r2=1674638&view=diff
==============================================================================
--- continuum/trunk/continuum-api/src/main/java/org/apache/continuum/dao/BuildResultDao.java
(original)
+++ continuum/trunk/continuum-api/src/main/java/org/apache/continuum/dao/BuildResultDao.java
Sun Apr 19 16:32:37 2015
@@ -26,6 +26,7 @@ import org.apache.maven.continuum.store.
 import java.util.Date;
 import java.util.List;
 import java.util.Map;
+import java.util.Set;
 
 /**
  * @author <a href="mailto:evenisse@apache.org">Emmanuel Venisse</a>
@@ -56,7 +57,14 @@ public interface BuildResultDao
     BuildResult getPreviousBuildResultInSuccess( int projectId, int buildResultId )
         throws ContinuumStoreException;
 
-    int resolveOrphanedInProgressResults()
+    /**
+     * Marks results in the BUILDING status with a start time before the specified cutoff
as CANCELLED.
+     *
+     * @param ageCutoff the time in milliseconds, before which a building result is considered
orphaned
+     * @return the set of ids considered orphaned, and consequently marked CANCELLED
+     * @throws ContinuumStoreException
+     */
+    Set<Integer> resolveOrphanedInProgressResults( long ageCutoff )
         throws ContinuumStoreException;
 
     long getNbBuildResultsForProject( int projectId );

Modified: continuum/trunk/continuum-core/src/main/java/org/apache/continuum/builder/OrphanBuildStatusUpdater.java
URL: http://svn.apache.org/viewvc/continuum/trunk/continuum-core/src/main/java/org/apache/continuum/builder/OrphanBuildStatusUpdater.java?rev=1674638&r1=1674637&r2=1674638&view=diff
==============================================================================
--- continuum/trunk/continuum-core/src/main/java/org/apache/continuum/builder/OrphanBuildStatusUpdater.java
(original)
+++ continuum/trunk/continuum-core/src/main/java/org/apache/continuum/builder/OrphanBuildStatusUpdater.java
Sun Apr 19 16:32:37 2015
@@ -23,10 +23,13 @@ import org.apache.continuum.builder.dist
 import org.apache.continuum.dao.BuildResultDao;
 import org.apache.maven.continuum.store.ContinuumStoreException;
 import org.codehaus.plexus.component.annotations.Component;
+import org.codehaus.plexus.component.annotations.Configuration;
 import org.codehaus.plexus.component.annotations.Requirement;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
+import java.util.Set;
+
 @Component( role = BuildStatusUpdater.class, hint = "orphans" )
 public class OrphanBuildStatusUpdater
     implements BuildStatusUpdater
@@ -36,13 +39,37 @@ public class OrphanBuildStatusUpdater
     @Requirement
     private BuildResultDao buildResultDao;
 
+    @Configuration( "24" )
+    private int orphanAfterHours;
+
+    public void setOrphanAfterHours( int orphanAfterHours )
+    {
+        this.orphanAfterHours = orphanAfterHours;
+    }
+
     public void performScan()
     {
+        if ( orphanAfterHours <= 0 )
+        {
+            log.warn( "disabled by configuration: orphan-after-hours = {}", orphanAfterHours
);
+            return;
+        }
+
         try
         {
-            log.info( "scanning for orphaned in-progress build results" );
-            int updated = buildResultDao.resolveOrphanedInProgressResults();
-            log.info( "finished: fixed {} results", updated );
+            long hourInMillis = 1000 * 60 * 60, now = System.currentTimeMillis();
+            long orphanCutoff = now - ( orphanAfterHours * hourInMillis );
+            log.info( "attempting to cancel results in-progress for more than {} hours",
orphanAfterHours );
+            Set<Integer> orphans = buildResultDao.resolveOrphanedInProgressResults(
orphanCutoff );
+            if ( orphans.isEmpty() )
+            {
+                log.info( "marked no results as canceled" );
+            }
+            else
+            {
+                log.info( "marked {} results as canceled: {}", orphans.size(), orphans );
+            }
+
         }
         catch ( ContinuumStoreException e )
         {

Modified: continuum/trunk/continuum-core/src/test/java/org/apache/continuum/builder/OrphanBuildStatusUpdaterTest.java
URL: http://svn.apache.org/viewvc/continuum/trunk/continuum-core/src/test/java/org/apache/continuum/builder/OrphanBuildStatusUpdaterTest.java?rev=1674638&r1=1674637&r2=1674638&view=diff
==============================================================================
--- continuum/trunk/continuum-core/src/test/java/org/apache/continuum/builder/OrphanBuildStatusUpdaterTest.java
(original)
+++ continuum/trunk/continuum-core/src/test/java/org/apache/continuum/builder/OrphanBuildStatusUpdaterTest.java
Sun Apr 19 16:32:37 2015
@@ -40,24 +40,33 @@ public class OrphanBuildStatusUpdaterTes
     extends AbstractContinuumTest
 {
 
+    private final int ageCutoff = 2;
+
     private BuildResultDao resultDao;
 
     private BuildDefinitionDao buildDefDao;
 
-    private List<BuildResult> canceled = new ArrayList<BuildResult>();
-
-    private List<BuildResult> ok = new ArrayList<BuildResult>();
+    private List<BuildResult> aged = new ArrayList<BuildResult>();
 
-    private List<BuildResult> building = new ArrayList<BuildResult>();
+    private List<BuildResult> recent = new ArrayList<BuildResult>();
 
     private BuildDefinition defOne;
 
     private BuildDefinition defTwo;
 
+    private OrphanBuildStatusUpdater updater;
+
+    @Override
+    protected String[] getConfigLocations()
+    {
+        return super.getConfigLocations();
+    }
+
     @Before
     public void populateTestData()
         throws Exception
     {
+        updater = (OrphanBuildStatusUpdater) lookup( BuildStatusUpdater.class, "orphans"
);
         resultDao = lookup( BuildResultDao.class );
         buildDefDao = lookup( BuildDefinitionDao.class );
 
@@ -66,31 +75,85 @@ public class OrphanBuildStatusUpdaterTes
 
         // NOTE: Build results added in build order - last added is most recent build
 
-        Project noCleanup = addProject( "One In-Progress (No Cleanup)" );
-        addResult( noCleanup, defOne, BUILDING, building );
+        Project p1 = addProject( "One Too Young" );
+        addRecent( p1, defOne, BUILDING );
+
+        Project p2 = addProject( "One Orphan" );
+        addAged( p2, defOne, BUILDING );
 
-        Project oneCleanup = addProject( "Two In-Progress With Success (One Cleanup)" );
-        addResult( oneCleanup, defTwo, BUILDING, canceled );
-        addResult( oneCleanup, defTwo, OK, ok );
-        addResult( oneCleanup, defTwo, BUILDING, building );
-
-        Project twoCleanup = addProject( "Three In-Progress With Success (Two Cleanup)" );
-        addResult( twoCleanup, defTwo, BUILDING, canceled );
-        addResult( twoCleanup, defTwo, OK, ok );
-        addResult( twoCleanup, defTwo, BUILDING, canceled );
-        addResult( twoCleanup, defTwo, BUILDING, building );
-
-        Project bdNoCleanup = addProject( "Two In-Progress (No Cleanup)" );
-        addResult( bdNoCleanup, defOne, BUILDING, building );
-        addResult( bdNoCleanup, defTwo, BUILDING, building );
+        Project p3 = addProject( "Two Orphans, Interleaved Success" );
+        addAged( p3, defTwo, BUILDING );
+        addRecent( p3, defTwo, OK );
+        addAged( p3, defTwo, BUILDING );
+
+        Project p4 = addProject( "Two Orphans, Interleaved Success, One Too Young" );
+        addAged( p4, defTwo, BUILDING );
+        addRecent( p4, defTwo, OK );
+        addAged( p4, defTwo, BUILDING );
+        addRecent( p4, defTwo, BUILDING );
+
+        Project p5 = addProject( "Two In-Progress, No Orphans" );
+        addAged( p5, defOne, BUILDING );
+        addAged( p5, defTwo, BUILDING );
+
+        Project p6 = addProject( "Two In-Progress, No Orphans (Diff Build Defs)" );
+        addRecent( p6, defOne, BUILDING );
+        addRecent( p6, defTwo, BUILDING );
+
+        updater.setOrphanAfterHours( ageCutoff );
+    }
+
+    @Test
+    public void testOrphansCanceled()
+        throws ContinuumStoreException
+    {
+        updater.performScan();
+        verifyUntouched( recent );
+        verifyCanceled( aged );
     }
 
     @Test
-    public void testOrphansResolvedSafely()
+    public void testDisabledByZeroCutoff()
+        throws ContinuumStoreException
+    {
+        updater.setOrphanAfterHours( 0 );
+        updater.performScan();
+        verifyUntouched( recent, aged );
+    }
+
+    @Test
+    public void testDisabledByNegativeCutoff()
+        throws ContinuumStoreException
+    {
+        updater.setOrphanAfterHours( Integer.MIN_VALUE );
+        updater.performScan();
+        verifyUntouched( recent, aged );
+    }
+
+    private void verifyUntouched( List<BuildResult>... resultLists )
+        throws ContinuumStoreException
+    {
+        for ( List<BuildResult> list : resultLists )
+        {
+            for ( BuildResult br : list )
+            {
+                assertEquals( "Status should not have been touched: " + br, br.getState(),
+                              resultDao.getBuildResult( br.getId() ).getState() );
+            }
+        }
+    }
+
+    private void verifyCanceled( List<BuildResult>... resultLists )
         throws ContinuumStoreException
     {
-        lookup( BuildStatusUpdater.class, "orphans" ).performScan();
-        verifyResults();
+        for ( List<BuildResult> list : resultLists )
+        {
+            for ( BuildResult br : list )
+            {
+                assertEquals( "Status should be canceled: " + br, CANCELLED,
+                              resultDao.getBuildResult( br.getId() ).getState() );
+            }
+        }
     }
 
     private BuildDefinition addBuildDef()
@@ -105,7 +168,20 @@ public class OrphanBuildStatusUpdaterTes
         return def;
     }
 
-    private void addResult( Project project, BuildDefinition buildDef, int state, List<BuildResult>
expected )
+    private void addRecent( Project project, BuildDefinition buildDef, int state )
+        throws ContinuumStoreException
+    {
+        addResult( project, buildDef, state, recent, ageCutoff - 1 );
+    }
+
+    private void addAged( Project project, BuildDefinition buildDef, int state )
+        throws ContinuumStoreException
+    {
+        addResult( project, buildDef, state, aged, ageCutoff + 1 );
+    }
+
+    private void addResult( Project project, BuildDefinition buildDef, int state, List<BuildResult>
expected,
+                            long ageInHours )
         throws ContinuumStoreException
     {
         BuildResult br = new BuildResult();
@@ -114,7 +190,7 @@ public class OrphanBuildStatusUpdaterTes
         br.setBuildNumber( 0 );
         br.setEndTime( 0 );
         br.setExitCode( 0 );
-        br.setStartTime( 0 );
+        br.setStartTime( System.currentTimeMillis() - ( 1000 * 60 * 60 * ageInHours ) );
         br.setTrigger( 0 );
 
         // associate relationship
@@ -128,26 +204,4 @@ public class OrphanBuildStatusUpdaterTes
         br = resultDao.getBuildResult( br.getId() );
         expected.add( br );
     }
-
-    private void verifyResults()
-        throws ContinuumStoreException
-    {
-        for ( BuildResult br : ok )
-        {
-            assertEquals( "Successful results should be untouched", OK,
-                          resultDao.getBuildResult( br.getId() ).getState() );
-        }
-
-        for ( BuildResult br : building )
-        {
-            assertEquals( "Latest building result for build def should be untouched", BUILDING,
-                          resultDao.getBuildResult( br.getId() ).getState() );
-        }
-
-        for ( BuildResult br : canceled )
-        {
-            assertEquals( "Prior building results for build def should be canceled", CANCELLED,
-                          resultDao.getBuildResult( br.getId() ).getState() );
-        }
-    }
 }

Modified: continuum/trunk/continuum-store/src/main/java/org/apache/continuum/dao/BuildResultDaoImpl.java
URL: http://svn.apache.org/viewvc/continuum/trunk/continuum-store/src/main/java/org/apache/continuum/dao/BuildResultDaoImpl.java?rev=1674638&r1=1674637&r2=1674638&view=diff
==============================================================================
--- continuum/trunk/continuum-store/src/main/java/org/apache/continuum/dao/BuildResultDaoImpl.java
(original)
+++ continuum/trunk/continuum-store/src/main/java/org/apache/continuum/dao/BuildResultDaoImpl.java
Sun Apr 19 16:32:37 2015
@@ -727,7 +727,7 @@ public class BuildResultDaoImpl
         }
     }
 
-    public int resolveOrphanedInProgressResults()
+    public Set<Integer> resolveOrphanedInProgressResults( long ageCutoff )
         throws ContinuumStoreException
     {
         PersistenceManager pm = getPersistenceManager();
@@ -736,14 +736,10 @@ public class BuildResultDaoImpl
         {
             tx.begin();
             Query query = pm.newQuery( BuildResult.class );
-            query.declareVariables( "BuildResult r1" );
-            String filter = String.format( "this.project.id == r1.project.id"
-                                               + " && this.buildDefinition.id ==
r1.buildDefinition.id"
-                                               + " && this.state == %s"
-                                               + " && this.id < r1.id", BUILDING
);
+            query.declareParameters( "long orphanCutoff" );
+            String filter = String.format( " this.state == %s && this.startTime <
orphanCutoff", BUILDING );
             query.setFilter( filter );
-            int updateCount = 0;
-            List<BuildResult> orphans = (List<BuildResult>) pm.detachCopyAll(
(List) query.execute() );
+            List<BuildResult> orphans = (List<BuildResult>) pm.detachCopyAll(
(List) query.execute( ageCutoff ) );
             Set<Integer> updatedIds = new HashSet<Integer>();
             for ( BuildResult orphan : orphans )
             {
@@ -751,11 +747,12 @@ public class BuildResultDaoImpl
                     continue;
                 orphan.setState( CANCELLED );
                 orphan.setError( "Build appears to have been orphaned, final status is unknown."
);
+                orphan.setEndTime( System.currentTimeMillis() );
                 updateObject( orphan );
                 updatedIds.add( orphan.getId() );
             }
             tx.commit();
-            return updatedIds.size();
+            return updatedIds;
         }
         finally
         {

Modified: continuum/trunk/continuum-webapp/src/main/webapp/WEB-INF/applicationContext.xml
URL: http://svn.apache.org/viewvc/continuum/trunk/continuum-webapp/src/main/webapp/WEB-INF/applicationContext.xml?rev=1674638&r1=1674637&r2=1674638&view=diff
==============================================================================
--- continuum/trunk/continuum-webapp/src/main/webapp/WEB-INF/applicationContext.xml (original)
+++ continuum/trunk/continuum-webapp/src/main/webapp/WEB-INF/applicationContext.xml Sun Apr
19 16:32:37 2015
@@ -128,7 +128,7 @@
   </bean>
   <bean id="orphanedBuildTrigger" class="org.springframework.scheduling.quartz.CronTriggerBean">
     <property name="jobDetail" ref="orphanedBuildJob"/>
-    <property name="cronExpression" value="0 */5 * * * ?"/>
+    <property name="cronExpression" value="0 0 * * * ?"/>
   </bean>
 
 



Mime
View raw message