package com.mongodb.hvdf.async; import java.util.Date; import org.bson.types.ObjectId; import com.fasterxml.jackson.annotation.JsonIgnore; import com.fasterxml.jackson.annotation.JsonProperty; import com.mongodb.hvdf.api.MongoDataObject; import com.mongodb.BasicDBObject; import com.mongodb.DBObject; public class RecoveryRecord extends MongoDataObject{ public static final String ID_KEY = "_id"; public static final String TYPE_KEY = "_t"; public static final String PRIORITY_KEY = "_p"; public static final String STATE_KEY = "_s"; public static final String DATA_KEY = "_d"; public static final String WORKER_KEY = "_w"; public static final String LAST_TIMESTAMP_KEY = "_l"; public static final String FAILED_COUNT = "_f"; public RecoveryRecord(final DBObject obj) { super(obj); } public RecoveryRecord(final short typeId, final short priority, final DBObject data) { super(); _dbObject.put(ID_KEY, new ObjectId()); _dbObject.put(TYPE_KEY, typeId); _dbObject.put(PRIORITY_KEY, priority); _dbObject.put(STATE_KEY, (Short)AsyncTaskState.AVAILABLE.stateId()); _dbObject.put(LAST_TIMESTAMP_KEY, new Date()); _dbObject.put(FAILED_COUNT, (short)0); if(data != null) _dbObject.put(DATA_KEY, data); } public void markAsProcessing(String signature){ // flag as being processed directly by a worker _dbObject.put(STATE_KEY, (Short)AsyncTaskState.PROCESSING.stateId()); _dbObject.put(WORKER_KEY, signature); } @JsonIgnore public Object getId() { return _dbObject.get(ID_KEY); } @JsonProperty("_id") public String getIdAsString() { return _dbObject.get(ID_KEY).toString(); } @JsonProperty("created") public Date getCreationDate() { return ((ObjectId)_dbObject.get(ID_KEY)).getDate(); } @JsonProperty("priority") public short getPriority() { return (Short) _dbObject.get(PRIORITY_KEY); } public AsyncTaskType getType() { return AsyncTaskType.fromId(getTypeId()) ; } @JsonProperty("typeId") public short getTypeId() { return ((Integer)_dbObject.get(TYPE_KEY)).shortValue(); } @JsonProperty("data") public DBObject getRecoveryData() { return (DBObject) _dbObject.get(DATA_KEY); } public static DBObject findById(RecoveryRecord recoveryRecord) { return new BasicDBObject(ID_KEY, recoveryRecord.getId()); } public static DBObject updateAsFailed() { return new BasicDBObject("$set", new BasicDBObject(STATE_KEY, (Short)AsyncTaskState.FAILED.stateId()). append(LAST_TIMESTAMP_KEY, new Date())). append("$inc", new BasicDBObject(FAILED_COUNT, 1)); } public static DBObject updateAsAvailable() { return new BasicDBObject("$set", new BasicDBObject( STATE_KEY, (Short)AsyncTaskState.AVAILABLE.stateId()). append(LAST_TIMESTAMP_KEY, new Date())); } public static DBObject updateAsProcessing(String signature) { return new BasicDBObject("$set", new BasicDBObject( STATE_KEY, (Short)AsyncTaskState.PROCESSING.stateId()). append(WORKER_KEY, signature). append(LAST_TIMESTAMP_KEY, new Date())); } public static DBObject findEligible(short taskType, int maxFails) { // To qualify, the task needs : // 1) Not be in the processing state // 2) Less than failure limit // 3) The correct type return new BasicDBObject(TYPE_KEY, taskType). append(STATE_KEY, new BasicDBObject("$ne", (Short)AsyncTaskState.PROCESSING.stateId())). append(FAILED_COUNT, new BasicDBObject("$lt", maxFails)); } public static DBObject findTimedOut(short taskType, int timeout) { // Calculate the time stamp that would make a task eligible long timeoutPoint = (new Date()).getTime() - timeout; Date timeoutDate = new Date(timeoutPoint); return new BasicDBObject(TYPE_KEY, taskType). append(STATE_KEY,(Short)AsyncTaskState.PROCESSING.stateId()). append(LAST_TIMESTAMP_KEY, new BasicDBObject("$lt", timeoutDate)); } public static DBObject oldestFirst() { return new BasicDBObject(ID_KEY, 1); } }