Author: jacopoc
Date: Sat Aug 30 09:17:07 2014 New Revision: 1621438 URL: http://svn.apache.org/r1621438 Log: Completely refactored the SequenceUtil class: * the class is now thread safe * the class is now cleaner (no references to delegator etc...) * replaced the collision detection algorithm with a simpler/reliable/efficient one based on: update with no changes (to get a lock) + select + update (to increase the last sequence id) * removed ugly special code for "clusters" that is no more needed Modified: ofbiz/trunk/framework/common/config/general.properties ofbiz/trunk/framework/entity/src/org/ofbiz/entity/GenericDelegator.java ofbiz/trunk/framework/entity/src/org/ofbiz/entity/test/EntityTestSuite.java ofbiz/trunk/framework/entity/src/org/ofbiz/entity/util/SequenceUtil.java Modified: ofbiz/trunk/framework/common/config/general.properties URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/common/config/general.properties?rev=1621438&r1=1621437&r2=1621438&view=diff ============================================================================== --- ofbiz/trunk/framework/common/config/general.properties (original) +++ ofbiz/trunk/framework/common/config/general.properties Sat Aug 30 09:17:07 2014 @@ -130,7 +130,3 @@ mail.spam.value=YES # -- Y if you want to display the multi-tenant textbox in the login page and install specify components which related to each tenant multitenant=N - -# -- Y if you use a cluster. Most of the time this should not be needed. Setting distributed-cache-clear-enabled="true" is enough -# -- to guarantee no sequenceIds duplicates. See OFBIZ-2353 and look for "DCC" in wiki for details -clustered=N Modified: ofbiz/trunk/framework/entity/src/org/ofbiz/entity/GenericDelegator.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/entity/src/org/ofbiz/entity/GenericDelegator.java?rev=1621438&r1=1621437&r2=1621438&view=diff ============================================================================== --- ofbiz/trunk/framework/entity/src/org/ofbiz/entity/GenericDelegator.java (original) +++ ofbiz/trunk/framework/entity/src/org/ofbiz/entity/GenericDelegator.java Sat Aug 30 09:17:07 2014 @@ -48,6 +48,7 @@ import org.ofbiz.base.util.UtilFormatOut import org.ofbiz.base.util.UtilGenerics; import org.ofbiz.base.util.UtilMisc; import org.ofbiz.base.util.UtilObject; +import org.ofbiz.base.util.UtilProperties; import org.ofbiz.base.util.UtilValidate; import org.ofbiz.base.util.UtilXml; import org.ofbiz.entity.cache.Cache; @@ -72,7 +73,6 @@ import org.ofbiz.entity.model.ModelRelat import org.ofbiz.entity.model.ModelViewEntity; import org.ofbiz.entity.serialize.SerializeException; import org.ofbiz.entity.serialize.XmlSerializer; -import org.ofbiz.entity.transaction.GenericTransactionException; import org.ofbiz.entity.transaction.TransactionUtil; import org.ofbiz.entity.util.DistributedCacheClear; import org.ofbiz.entity.util.EntityCrypto; @@ -2533,24 +2533,14 @@ public class GenericDelegator implements /* (non-Javadoc) * @see org.ofbiz.entity.Delegator#getNextSeqIdLong(java.lang.String, long) */ - @Override public Long getNextSeqIdLong(String seqName, long staggerMax) { - boolean beganTransaction = false; try { - if (alwaysUseTransaction) { - beganTransaction = TransactionUtil.begin(); - } - SequenceUtil sequencer = this.AtomicRefSequencer.get(); if (sequencer == null) { ModelEntity seqEntity = this.getModelEntity("SequenceValueItem"); - sequencer = new SequenceUtil(this, this.getEntityHelperInfo("SequenceValueItem"), seqEntity, "seqName", "seqId"); - try { - if (!AtomicRefSequencer.compareAndSet(null, sequencer)) { - sequencer = this.AtomicRefSequencer.get(); - } - } catch (Exception e) { - throw new IllegalStateException("Error thrown while creating AtomicReference<SequenceUtil> in getNextSeqIdLong()" + e); + sequencer = new SequenceUtil(this.getEntityHelperInfo("SequenceValueItem"), seqEntity, "seqName", "seqId"); + if (!AtomicRefSequencer.compareAndSet(null, sequencer)) { + sequencer = this.AtomicRefSequencer.get(); } } @@ -2558,16 +2548,10 @@ public class GenericDelegator implements ModelEntity seqModelEntity = this.getModelEntity(seqName); Long newSeqId = sequencer == null ? null : sequencer.getNextSeqId(seqName, staggerMax, seqModelEntity); - TransactionUtil.commit(beganTransaction); return newSeqId; } catch (Exception e) { String errMsg = "Failure in getNextSeqIdLong operation for seqName [" + seqName + "]: " + e.toString() + ". Rolling back transaction."; Debug.logError(e, errMsg, module); - try { - TransactionUtil.rollback(beganTransaction, errMsg, e); - } catch (GenericTransactionException e1) { - Debug.logError(e1, "Exception thrown while rolling back transaction: ", module); - } throw new GeneralRuntimeException(errMsg, e); } } Modified: ofbiz/trunk/framework/entity/src/org/ofbiz/entity/test/EntityTestSuite.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/entity/src/org/ofbiz/entity/test/EntityTestSuite.java?rev=1621438&r1=1621437&r2=1621438&view=diff ============================================================================== --- ofbiz/trunk/framework/entity/src/org/ofbiz/entity/test/EntityTestSuite.java (original) +++ ofbiz/trunk/framework/entity/src/org/ofbiz/entity/test/EntityTestSuite.java Sat Aug 30 09:17:07 2014 @@ -1093,7 +1093,7 @@ public class EntityTestSuite extends Ent } public void testSequenceValueItem() { - SequenceUtil sequencer = new SequenceUtil((GenericDelegator)delegator, delegator.getGroupHelperInfo(delegator.getEntityGroupName("SequenceValueItem")), + SequenceUtil sequencer = new SequenceUtil(delegator.getGroupHelperInfo(delegator.getEntityGroupName("SequenceValueItem")), delegator.getModelEntity("SequenceValueItem"), "seqName", "seqId"); UUID id = UUID.randomUUID(); @@ -1108,7 +1108,7 @@ public class EntityTestSuite extends Ent } public void testSequenceValueItemWithConcurrentThreads() { - final SequenceUtil sequencer = new SequenceUtil((GenericDelegator)delegator, delegator.getGroupHelperInfo(delegator.getEntityGroupName("SequenceValueItem")), + final SequenceUtil sequencer = new SequenceUtil(delegator.getGroupHelperInfo(delegator.getEntityGroupName("SequenceValueItem")), delegator.getModelEntity("SequenceValueItem"), "seqName", "seqId"); UUID id = UUID.randomUUID(); Modified: ofbiz/trunk/framework/entity/src/org/ofbiz/entity/util/SequenceUtil.java URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/entity/src/org/ofbiz/entity/util/SequenceUtil.java?rev=1621438&r1=1621437&r2=1621438&view=diff ============================================================================== --- ofbiz/trunk/framework/entity/src/org/ofbiz/entity/util/SequenceUtil.java (original) +++ ofbiz/trunk/framework/entity/src/org/ofbiz/entity/util/SequenceUtil.java Sat Aug 30 09:17:07 2014 @@ -22,14 +22,12 @@ import java.sql.Connection; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Statement; -import java.util.Hashtable; -import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; import javax.transaction.Transaction; import org.ofbiz.base.util.Debug; -import org.ofbiz.base.util.UtilProperties; -import org.ofbiz.entity.Delegator; import org.ofbiz.entity.GenericEntityException; import org.ofbiz.entity.datasource.GenericHelperInfo; import org.ofbiz.entity.model.ModelEntity; @@ -40,20 +38,18 @@ import org.ofbiz.entity.transaction.Tran /** * Sequence Utility to get unique sequences from named sequence banks - * Uses a collision detection approach to safely get unique sequenced ids in banks from the database */ public class SequenceUtil { public static final String module = SequenceUtil.class.getName(); - private final Map<String, SequenceBank> sequences = new Hashtable<String, SequenceBank>(); + private final ConcurrentMap<String, SequenceBank> sequences = new ConcurrentHashMap<String, SequenceBank>(); private final GenericHelperInfo helperInfo; private final String tableName; private final String nameColName; private final String idColName; - private final boolean clustered; - public SequenceUtil(Delegator delegator, GenericHelperInfo helperInfo, ModelEntity seqEntity, String nameFieldName, String idFieldName) { + public SequenceUtil(GenericHelperInfo helperInfo, ModelEntity seqEntity, String nameFieldName, String idFieldName) { this.helperInfo = helperInfo; if (seqEntity == null) { throw new IllegalArgumentException("The sequence model entity was null but is required."); @@ -73,7 +69,6 @@ public class SequenceUtil { throw new IllegalArgumentException("Could not find the field definition for the sequence id field " + idFieldName); } this.idColName = idField.getColName(); - clustered = delegator.useDistributedCacheClear() || "Y".equals(UtilProperties.getPropertyValue("general.properties", "clustered")); } public Long getNextSeqId(String seqName, long staggerMax, ModelEntity seqModelEntity) { @@ -95,18 +90,14 @@ public class SequenceUtil { SequenceBank bank = sequences.get(seqName); if (bank == null) { - synchronized(this) { - bank = sequences.get(seqName); - if (bank == null) { - long bankSize = SequenceBank.defaultBankSize; - if (seqModelEntity != null && seqModelEntity.getSequenceBankSize() != null) { - bankSize = seqModelEntity.getSequenceBankSize().longValue(); - if (bankSize > SequenceBank.maxBankSize) bankSize = SequenceBank.maxBankSize; - } - bank = new SequenceBank(seqName, bankSize); - sequences.put(seqName, bank); - } + long bankSize = SequenceBank.defaultBankSize; + if (seqModelEntity != null && seqModelEntity.getSequenceBankSize() != null) { + bankSize = seqModelEntity.getSequenceBankSize().longValue(); + if (bankSize > SequenceBank.maxBankSize) bankSize = SequenceBank.maxBankSize; } + bank = new SequenceBank(seqName, bankSize); + SequenceBank bankFromCache = sequences.putIfAbsent(seqName, bank); + bank = bankFromCache != null ? bankFromCache : bank; } return bank; @@ -116,43 +107,41 @@ public class SequenceUtil { public static final long defaultBankSize = 10; public static final long maxBankSize = 5000; public static final long startSeqId = 10000; - public static final long minWaitMillis = 5; - public static final long maxWaitMillis = 50; - public static final int maxTries = 5; - private long curSeqId; - private long maxSeqId; private final String seqName; private final long bankSize; + private long curSeqId; + private long maxSeqId; + private SequenceBank(String seqName, long bankSize) { this.seqName = seqName; curSeqId = 0; maxSeqId = 0; this.bankSize = bankSize; - fillBank(1); } - private synchronized Long getNextSeqId(long staggerMax) { + private Long getNextSeqId(long staggerMax) { long stagger = 1; if (staggerMax > 1) { - stagger = Math.round(Math.random() * staggerMax); + stagger = (long)Math.ceil(Math.random() * staggerMax); if (stagger == 0) stagger = 1; } - - if ((curSeqId + stagger) <= maxSeqId) { - Long retSeqId = Long.valueOf(curSeqId); - curSeqId += stagger; - return retSeqId; - } else { - fillBank(stagger); + synchronized (this) { if ((curSeqId + stagger) <= maxSeqId) { Long retSeqId = Long.valueOf(curSeqId); curSeqId += stagger; return retSeqId; } else { - Debug.logError("[SequenceUtil.SequenceBank.getNextSeqId] Fill bank failed, returning null", module); - return null; + fillBank(stagger); + if ((curSeqId + stagger) <= maxSeqId) { + Long retSeqId = Long.valueOf(curSeqId); + curSeqId += stagger; + return retSeqId; + } else { + Debug.logError("Fill bank failed, returning null", module); + return null; + } } } } @@ -162,9 +151,7 @@ public class SequenceUtil { this.fillBank(staggerMax); } - private synchronized void fillBank(long stagger) { - //Debug.logWarning("[SequenceUtil.SequenceBank.fillBank] Starting fillBank Thread Name is: " + Thread.currentThread().getName() + ":" + Thread.currentThread().toString(), module); - + private void fillBank(long stagger) { // no need to get a new bank, SeqIds available if ((curSeqId + stagger) <= maxSeqId) return; @@ -176,178 +163,120 @@ public class SequenceUtil { if (bankSize > maxBankSize) bankSize = maxBankSize; - long val1 = 0; - long val2 = 0; + Transaction suspendedTransaction = null; + try { + suspendedTransaction = TransactionUtil.suspend(); + + boolean beganTransaction = false; + try { + beganTransaction = TransactionUtil.begin(); + + Connection connection = null; + Statement stmt = null; + ResultSet rs = null; - // NOTE: the fancy ethernet type stuff is for the case where transactions not available, or something funny happens with really sensitive timing (between first select and update, for example) - int numTries = 0; - - while (val1 + bankSize != val2) { - if (Debug.verboseOn()) Debug.logVerbose("[SequenceUtil.SequenceBank.fillBank] Trying to get a bank of sequenced ids for " + - this.seqName + "; start of loop val1=" + val1 + ", val2=" + val2 + ", bankSize=" + bankSize, module); - - // not sure if this synchronized block is totally necessary, the method is synchronized but it does do a wait/sleep - // outside of this block, and this is the really sensitive block, so making sure it is isolated; there is some overhead - // to this, but very bad things can happen if we try to do too many of these at once for a single sequencer - synchronized (this) { - Transaction suspendedTransaction = null; try { - //if we can suspend the transaction, we'll try to do this in a local manual transaction - suspendedTransaction = TransactionUtil.suspend(); - - boolean beganTransaction = false; - try { - beganTransaction = TransactionUtil.begin(); - - Connection connection = null; - Statement stmt = null; - ResultSet rs = null; - - try { - connection = TransactionFactoryLoader.getInstance().getConnection(SequenceUtil.this.helperInfo); - } catch (SQLException sqle) { - Debug.logWarning("[SequenceUtil.SequenceBank.fillBank]: Unable to esablish a connection with the database... Error was:" + sqle.toString(), module); - throw sqle; - } catch (GenericEntityException e) { - Debug.logWarning("[SequenceUtil.SequenceBank.fillBank]: Unable to esablish a connection with the database... Error was: " + e.toString(), module); - throw e; - } - - if (connection == null) { - throw new GenericEntityException("[SequenceUtil.SequenceBank.fillBank]: Unable to esablish a connection with the database, connection was null..."); - } - - String sql = null; - - try { - // we shouldn't need this, and some TX managers complain about it, so not including it: connection.setAutoCommit(false); - - stmt = connection.createStatement(); - if (clustered) { - sql = "SELECT " + SequenceUtil.this.idColName + " FROM " + SequenceUtil.this.tableName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'" + " FOR UPDATE"; - } else { - sql = "SELECT " + SequenceUtil.this.idColName + " FROM " + SequenceUtil.this.tableName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; - } - rs = stmt.executeQuery(sql); - boolean gotVal1 = false; - if (rs.next()) { - val1 = rs.getLong(SequenceUtil.this.idColName); - gotVal1 = true; - } - rs.close(); + connection = TransactionFactoryLoader.getInstance().getConnection(SequenceUtil.this.helperInfo); + } catch (SQLException sqle) { + Debug.logWarning("Unable to esablish a connection with the database. Error was:" + sqle.toString(), module); + throw sqle; + } catch (GenericEntityException e) { + Debug.logWarning("Unable to esablish a connection with the database. Error was: " + e.toString(), module); + throw e; + } + if (connection == null) { + throw new GenericEntityException("Unable to esablish a connection with the database, connection was null..."); + } - if (!gotVal1) { - Debug.logWarning("[SequenceUtil.SequenceBank.fillBank] first select failed: will try to add new row, result set was empty for sequence [" + seqName + "] \nUsed SQL: " + sql + " \n Thread Name is: " + Thread.currentThread().getName() + ":" + Thread.currentThread().toString(), module); - sql = "INSERT INTO " + SequenceUtil.this.tableName + " (" + SequenceUtil.this.nameColName + ", " + SequenceUtil.this.idColName + ") VALUES ('" + this.seqName + "', " + startSeqId + ")"; - if (stmt.executeUpdate(sql) <= 0) { - throw new GenericEntityException("No rows changed when trying insert new sequence row with this SQL: " + sql); - } - continue; - } + String sql = null; + try { + stmt = connection.createStatement(); - sql = "UPDATE " + SequenceUtil.this.tableName + " SET " + SequenceUtil.this.idColName + "=" + SequenceUtil.this.idColName + "+" + bankSize + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; + // run an update with no changes to get a lock on the record + sql = "UPDATE " + SequenceUtil.this.tableName + " SET " + SequenceUtil.this.idColName + "=" + SequenceUtil.this.idColName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; + if (stmt.executeUpdate(sql) <= 0) { + Debug.logWarning("First select failed: will try to add new row, result set was empty for sequence [" + seqName + "] \nUsed SQL: " + sql + " \n ", module); + sql = "INSERT INTO " + SequenceUtil.this.tableName + " (" + SequenceUtil.this.nameColName + ", " + SequenceUtil.this.idColName + ") VALUES ('" + this.seqName + "', " + startSeqId + ")"; + if (stmt.executeUpdate(sql) <= 0) { + // insert failed: this means that another thread inserted the record; then retry to run an update with no changes to get a lock on the record + sql = "UPDATE " + SequenceUtil.this.tableName + " SET " + SequenceUtil.this.idColName + "=" + SequenceUtil.this.idColName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; if (stmt.executeUpdate(sql) <= 0) { - throw new GenericEntityException("[SequenceUtil.SequenceBank.fillBank] update failed, no rows changes for seqName: " + seqName); - } - if (clustered) { - sql = "SELECT " + SequenceUtil.this.idColName + " FROM " + SequenceUtil.this.tableName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'" + " FOR UPDATE"; - - } else { - sql = "SELECT " + SequenceUtil.this.idColName + " FROM " + SequenceUtil.this.tableName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; - } - rs = stmt.executeQuery(sql); - boolean gotVal2 = false; - if (rs.next()) { - val2 = rs.getLong(SequenceUtil.this.idColName); - gotVal2 = true; - } - - rs.close(); - - if (!gotVal2) { - throw new GenericEntityException("[SequenceUtil.SequenceBank.fillBank] second select failed: aborting, result set was empty for sequence: " + seqName); - } - - // got val1 and val2 at this point, if we don't have the right difference between them, force a rollback (with - //setRollbackOnly and NOT with an exception because we don't want to break from the loop, just err out and - //continue), then flow out to allow the wait and loop thing to happen - if (val1 + bankSize != val2) { - TransactionUtil.setRollbackOnly("Forcing transaction rollback in sequence increment because we didn't get a clean update, ie a conflict was found, so not saving the results", null); - } - } catch (SQLException sqle) { - Debug.logWarning(sqle, "[SequenceUtil.SequenceBank.fillBank] SQL Exception while executing the following:\n" + sql + "\nError was:" + sqle.getMessage(), module); - throw sqle; - } finally { - try { - if (stmt != null) stmt.close(); - } catch (SQLException sqle) { - Debug.logWarning(sqle, "Error closing statement in sequence util", module); - } - try { - if (connection != null) connection.close(); - } catch (SQLException sqle) { - Debug.logWarning(sqle, "Error closing connection in sequence util", module); + // This should never happen + throw new GenericEntityException("No rows changed when trying insert new sequence row with this SQL: " + sql); } } - } catch (Exception e) { - String errMsg = "General error in getting a sequenced ID"; - Debug.logError(e, errMsg, module); - try { - TransactionUtil.rollback(beganTransaction, errMsg, e); - } catch (GenericTransactionException gte2) { - Debug.logError(gte2, "Unable to rollback transaction", module); - } - - // error, break out of the loop to not try to continue forever - break; - } finally { - try { - TransactionUtil.commit(beganTransaction); - } catch (GenericTransactionException gte) { - Debug.logError(gte, "Unable to commit sequence increment transaction, continuing anyway though", module); - } } - } catch (GenericTransactionException e) { - Debug.logError(e, "System Error suspending transaction in sequence util", module); + // select the record (now locked) to get the curSeqId + sql = "SELECT " + SequenceUtil.this.idColName + " FROM " + SequenceUtil.this.tableName + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; + rs = stmt.executeQuery(sql); + boolean gotVal = false; + if (rs.next()) { + curSeqId = rs.getLong(SequenceUtil.this.idColName); + gotVal = true; + } + rs.close(); + if (!gotVal) { + throw new GenericEntityException("Failed to find the sequence record: " + sql); + } + // increment the sequence + sql = "UPDATE " + SequenceUtil.this.tableName + " SET " + SequenceUtil.this.idColName + "=" + SequenceUtil.this.idColName + "+" + bankSize + " WHERE " + SequenceUtil.this.nameColName + "='" + this.seqName + "'"; + if (stmt.executeUpdate(sql) <= 0) { + throw new GenericEntityException("Update failed, no rows changes for seqName: " + seqName); + } + + TransactionUtil.commit(beganTransaction); + + } catch (SQLException sqle) { + Debug.logWarning(sqle, "SQL Exception while executing the following:\n" + sql + "\nError was:" + sqle.getMessage(), module); + throw sqle; } finally { - if (suspendedTransaction != null) { - try { - TransactionUtil.resume(suspendedTransaction); - } catch (GenericTransactionException e) { - Debug.logError(e, "Error resuming suspended transaction in sequence util", module); - } + try { + if (stmt != null) stmt.close(); + } catch (SQLException sqle) { + Debug.logWarning(sqle, "Error closing statement in sequence util", module); + } + try { + if (connection != null) connection.close(); + } catch (SQLException sqle) { + Debug.logWarning(sqle, "Error closing connection in sequence util", module); } } - } - - if (val1 + bankSize != val2) { - if (numTries >= maxTries) { - String errMsg = "[SequenceUtil.SequenceBank.fillBank] maxTries (" + maxTries + ") reached for seqName [" + this.seqName + "], giving up."; - Debug.logError(errMsg, module); - return; + } catch (Exception e) { + // reset the sequence fields and return (note: it would be better to throw an exception) + curSeqId = 0; + maxSeqId = 0; + String errMsg = "General error in getting a sequenced ID"; + Debug.logError(e, errMsg, module); + try { + TransactionUtil.rollback(beganTransaction, errMsg, e); + } catch (GenericTransactionException gte2) { + Debug.logError(gte2, "Unable to rollback transaction", module); } - - // collision happened, wait a bounded random amount of time then continue - long waitTime = (long) (Math.random() * (maxWaitMillis - minWaitMillis) + minWaitMillis); - - Debug.logWarning("[SequenceUtil.SequenceBank.fillBank] Collision found for seqName [" + seqName + "], val1=" + val1 + ", val2=" + val2 + ", val1+bankSize=" + (val1 + bankSize) + ", bankSize=" + bankSize + ", waitTime=" + waitTime, module); - + return; + } + } catch (GenericTransactionException e) { + Debug.logError(e, "System Error suspending transaction in sequence util", module); + // reset the sequence fields and return (note: it would be better to throw an exception) + curSeqId = 0; + maxSeqId = 0; + return; + } finally { + if (suspendedTransaction != null) { try { - // using the Thread.sleep to more reliably lock this thread: this.wait(waitTime); - java.lang.Thread.sleep(waitTime); - } catch (Exception e) { - Debug.logWarning(e, "Error waiting in sequence util", module); + TransactionUtil.resume(suspendedTransaction); + } catch (GenericTransactionException e) { + Debug.logError(e, "Error resuming suspended transaction in sequence util", module); + // reset the sequence fields and return (note: it would be better to throw an exception) + curSeqId = 0; + maxSeqId = 0; return; } } - - numTries++; } - curSeqId = val1; - maxSeqId = val2; + maxSeqId = curSeqId + bankSize; if (Debug.infoOn()) Debug.logInfo("Got bank of sequenced IDs for [" + this.seqName + "]; curSeqId=" + curSeqId + ", maxSeqId=" + maxSeqId + ", bankSize=" + bankSize, module); - //Debug.logWarning("[SequenceUtil.SequenceBank.fillBank] Ending fillBank Thread Name is: " + Thread.currentThread().getName() + ":" + Thread.currentThread().toString(), module); } } } + |
Free forum by Nabble | Edit this page |