diff options
Diffstat (limited to 'feature-distributed-locking')
3 files changed, 75 insertions, 0 deletions
diff --git a/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/DistributedLockingFeature.java b/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/DistributedLockingFeature.java index 88035ca7..f1c8b687 100644 --- a/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/DistributedLockingFeature.java +++ b/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/DistributedLockingFeature.java @@ -73,6 +73,14 @@ public class DistributedLockingFeature implements PolicyEngineFeatureAPI, Policy return(tLock.lock(holdSec) ? OperResult.OPER_ACCEPTED : OperResult.OPER_DENIED); } + + @Override + public OperResult beforeRefresh(String resourceId, String owner, int holdSec) { + + TargetLock tLock = new TargetLock(resourceId, uuid, owner, dataSource); + + return(tLock.refresh(holdSec) ? OperResult.OPER_ACCEPTED : OperResult.OPER_DENIED); + } @Override public OperResult beforeUnlock(String resourceId, String owner) { diff --git a/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/TargetLock.java b/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/TargetLock.java index fe6f2fe0..1db34538 100644 --- a/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/TargetLock.java +++ b/feature-distributed-locking/src/main/java/org/onap/policy/distributed/locking/TargetLock.java @@ -73,6 +73,17 @@ public class TargetLock { return grabLock(holdSec); } + + /** + * refresh a lock + * + * @param holdSec the amount of time, in seconds, that the lock should be held + * @return {@code true} if the lock was refreshed, {@code false} if the resource is + * not currently locked by the given owner + */ + public boolean refresh(int holdSec) { + return updateLock(holdSec); + } /** * Unlock a resource by deleting it's associated record in the db @@ -158,6 +169,36 @@ public class TargetLock { } } + + /** + * Updates the DB record associated with the lock. + * + * @param holdSec the amount of time, in seconds, that the lock should be held + * @return {@code true} if the record was updated, {@code false} otherwise + */ + private boolean updateLock(int holdSec) { + + try (Connection conn = dataSource.getConnection(); + + PreparedStatement updateStatement = conn.prepareStatement( + "UPDATE pooling.locks SET host = ?, owner = ?, expirationTime = timestampadd(second, ?, now()) WHERE resourceId = ? AND owner = ? AND expirationTime >= now()")) { + + int i = 1; + updateStatement.setString(i++, this.uuid.toString()); + updateStatement.setString(i++, this.owner); + updateStatement.setInt(i++, holdSec); + updateStatement.setString(i++, this.resourceId); + updateStatement.setString(i++, this.owner); + + // refresh succeeded iff a record was updated + return (updateStatement.executeUpdate() == 1); + + } catch (SQLException e) { + logger.error("error in TargetLock.refreshLock()", e); + return false; + } + + } /** *To remove a lock we simply delete the record from the db diff --git a/feature-distributed-locking/src/test/java/org/onap/policy/distributed/locking/TargetLockTest.java b/feature-distributed-locking/src/test/java/org/onap/policy/distributed/locking/TargetLockTest.java index c1b46d67..6e33f224 100644 --- a/feature-distributed-locking/src/test/java/org/onap/policy/distributed/locking/TargetLockTest.java +++ b/feature-distributed-locking/src/test/java/org/onap/policy/distributed/locking/TargetLockTest.java @@ -119,6 +119,32 @@ public class TargetLockTest { assertEquals(OperResult.OPER_DENIED, distLockFeat.beforeLock("resource1", "owner2", MAX_AGE_SEC)); } + + @Test + public void testUpdateLock() throws InterruptedException, ExecutionException { + // not locked yet - refresh should fail + assertEquals(OperResult.OPER_DENIED, distLockFeat.beforeRefresh("resource1", "owner1", MAX_AGE_SEC)); + + // now lock it + assertEquals(OperResult.OPER_ACCEPTED, distLockFeat.beforeLock("resource1", "owner1", MAX_AGE_SEC)); + + // refresh should work now + assertEquals(OperResult.OPER_ACCEPTED, distLockFeat.beforeRefresh("resource1", "owner1", MAX_AGE_SEC)); + + // expire the lock + try (PreparedStatement updateStatement = conn.prepareStatement("UPDATE pooling.locks SET expirationTime = timestampadd(second, -1, now()) WHERE resourceId = ?");) + { + updateStatement.setString(1, "resource1"); + updateStatement.executeUpdate(); + + } catch (SQLException e) { + logger.error("Error in TargetLockTest.testGrabLockSuccess()", e); + throw new RuntimeException(e); + } + + // refresh should fail now + assertEquals(OperResult.OPER_DENIED, distLockFeat.beforeRefresh("resource1", "owner1", MAX_AGE_SEC)); + } @Test |