### Question:
SeqNo extends Cloneable implements Serializable { public long next (long wrapAt) { synchronized (this) { if (++value > wrapAt) value = 1; } return value; } SeqNo(String id);  SeqNo(); String getId(); void setId(String id); long getValue(); void setValue(long value); long next(long wrapAt); long getLockedBy(); void setLockedBy(long lockedBy); long getLockUntil(); void setLockUntil(long lockUntil); @Override boolean equals(Object o); @Override int hashCode(); @Override String toString();  }### Answer:
@Test public void testSyncLock() throws InterruptedException { int runs = 20; List<Thread> tl = new ArrayList<>(); Random r = new Random(); for (int i=0; i<runs; i++) { Thread t = new Thread(() -> { next(10 + Math.abs(r.nextLong()) % 100); }); tl.add(t); t.start(); } for (Thread t : tl) { t.join(); } assertEquals(++runs, next(1L), "seq value incorrect"); reset(); assertEquals(1L, next(1L), "reset failed"); reset(); }
@Test public void testAsyncLock() throws InterruptedException { int runs = 20; List<Thread> tl = new ArrayList<>(); Random r = new Random(); for (int i=0; i<runs; i++) { final int lockId = i; Thread t = new Thread(() -> { nextAsync(lockId, 10 + Math.abs(r.nextLong()) % 100); }); tl.add(t); t.start(); } for (Thread t : tl) { t.join(); } assertEquals(++runs, next(1L), "seq value incorrect"); }