use of org.eclipse.scout.rt.platform.job.IFuture in project scout.rt by eclipse.
the class ServiceTunnelServletTest method testLookupScoutServerSessionOnHttpSessionMultipleThreads.
/**
* Calls {@link ServiceTunnelServlet#lookupServerSessionOnHttpSession(ServerRunContext) in 4 different threads within
* the same HTTP session. Test ensures that the same server session is returned in all threads and that
* {@link ServerSessionProvider#provide(ServerRunContext)}} is called only once.
*/
@Test
public void testLookupScoutServerSessionOnHttpSessionMultipleThreads() throws ServletException {
final Map<String, IServerSession> cache = new HashMap<>();
final TestServerSession testServerSession = new TestServerSession();
testServerSession.start("testSessionId");
testServerSession.setSharedContextVariable("userId", String.class, "testUser");
HttpServletRequest requestMock = mock(HttpServletRequest.class);
HttpSession testHttpSession = mock(HttpSession.class);
when(requestMock.getSession()).thenReturn(testHttpSession);
when(requestMock.getSession(true)).thenReturn(testHttpSession);
ICacheEntry cacheEntryMock = mock(ICacheEntry.class);
when(cacheEntryMock.getValue()).thenReturn(testServerSession);
when(cacheEntryMock.isActive()).thenReturn(true);
doAnswer(putValueInCache(cache)).when(testHttpSession).setAttribute(ArgumentMatchers.eq(IServerSession.class.getName()), ArgumentMatchers.any());
when(testHttpSession.getAttribute(IServerSession.class.getName())).thenAnswer(getCachedValue(cache));
doAnswer(slowCreateTestsession(testServerSession)).when(m_serverSessionProviderSpy).provide(ArgumentMatchers.anyString(), ArgumentMatchers.any(ServerRunContext.class));
List<HttpSessionLookupCallable> jobs = new ArrayList<>();
for (int i = 0; i < 4; i++) {
jobs.add(new HttpSessionLookupCallable(m_testServiceTunnelServlet, requestMock, m_responseMock));
}
List<IFuture<?>> futures = scheduleAndJoinJobs(jobs);
Set<IServerSession> serverSessions = new HashSet<IServerSession>();
for (IFuture<?> future : futures) {
serverSessions.add((IServerSession) future.awaitDoneAndGet());
}
assertEquals(CollectionUtility.hashSet(testServerSession), serverSessions);
verify(m_serverSessionProviderSpy, times(1)).provide(ArgumentMatchers.anyString(), ArgumentMatchers.any(ServerRunContext.class));
}
use of org.eclipse.scout.rt.platform.job.IFuture in project scout.rt by eclipse.
the class BlockingTestUtility method runBlockingAction.
/**
* Helper method to test code which will enter a blocking condition.
* <p>
* If <code>runnableOnceBlocked</code> throws an exception, it is given to {@link JUnitExceptionHandler} to make the
* JUnit test fail.
*
* @param runnableGettingBlocked
* {@code IRunnable} that will enter a blocking condition.
* @param runnableOnceBlocked
* {@code IRunnable} to be executed once the 'runnableGettingBlocked' enters a blocking condition.
* @param awaitBackgroundJobs
* true waits for background jobs running in the same session to complete before runnableOnceBlocked is
* called
*/
public static void runBlockingAction(final IRunnable runnableGettingBlocked, final IRunnable runnableOnceBlocked, final boolean awaitBackgroundJobs) {
final ClientRunContext runContext = ClientRunContexts.copyCurrent();
final IBlockingCondition onceBlockedDoneCondition = Jobs.newBlockingCondition(true);
// remember the list of client jobs before blocking
final Set<IFuture<?>> jobsBefore = new HashSet<>();
jobsBefore.addAll(BEANS.get(IJobManager.class).getFutures(new IFilter<IFuture<?>>() {
@Override
public boolean accept(IFuture<?> cand) {
final RunContext candContext = cand.getJobInput().getRunContext();
return candContext instanceof ClientRunContext && ((ClientRunContext) candContext).getSession() == runContext.getSession();
}
}));
final IRegistrationHandle listenerRegistration = IFuture.CURRENT.get().addListener(Jobs.newEventFilterBuilder().andMatchEventType(JobEventType.JOB_STATE_CHANGED).andMatchState(JobState.WAITING_FOR_BLOCKING_CONDITION).andMatchExecutionHint(ModelJobs.EXECUTION_HINT_UI_INTERACTION_REQUIRED).toFilter(), new IJobListener() {
@Override
public void changed(final JobEvent event) {
// waitFor was entered
final IRunnable callRunnableOnceBlocked = new IRunnable() {
@Override
public void run() throws Exception {
try {
runnableOnceBlocked.run();
} finally {
event.getData().getBlockingCondition().setBlocking(false);
onceBlockedDoneCondition.setBlocking(false);
}
}
};
final JobInput jobInputForRunnableOnceBlocked = ModelJobs.newInput(runContext).withExceptionHandling(BEANS.get(JUnitExceptionHandler.class), true).withName("JUnit: Handling blocked thread because waiting for a blocking condition");
if (awaitBackgroundJobs) {
// wait until all background jobs finished
Jobs.schedule(new IRunnable() {
@Override
public void run() throws Exception {
jobsBefore.add(IFuture.CURRENT.get());
BEANS.get(IJobManager.class).awaitFinished(new IFilter<IFuture<?>>() {
@Override
public boolean accept(IFuture<?> f) {
RunContext candContext = f.getJobInput().getRunContext();
return candContext instanceof ClientRunContext && ((ClientRunContext) candContext).getSession() == runContext.getSession() && !jobsBefore.contains(f);
}
}, 5, TimeUnit.MINUTES);
// call runnableOnceBlocked
ModelJobs.schedule(callRunnableOnceBlocked, jobInputForRunnableOnceBlocked);
}
}, Jobs.newInput().withName("wait until background jobs finished"));
} else {
// call runnableOnceBlocked directly
ModelJobs.schedule(callRunnableOnceBlocked, jobInputForRunnableOnceBlocked);
}
}
});
try {
// this action will enter a blocking condition which causes the 'runnableOnceBlocked' to be executed.
runnableGettingBlocked.run();
} catch (final Exception e) {
throw BEANS.get(DefaultRuntimeExceptionTranslator.class).translate(e);
} finally {
listenerRegistration.dispose();
}
// we need to wait until the runnableOnceBlocked is completed.
// runnableOnceBlocked may, during its execution, set the original blocking condition to non-blocking but still execute
// important code afterwards. Therefore, the original blocking condition that starts runnableOnceBlocked is only used
// to indicate the start of the runnableOnceBlocked, but this method returns only AFTER runnableOnceBlocked completes execution.
onceBlockedDoneCondition.waitForUninterruptibly(120, TimeUnit.SECONDS);
}
use of org.eclipse.scout.rt.platform.job.IFuture in project scout.rt by eclipse.
the class JmsMomImplementorTest method after.
@After
public void after() throws Exception {
// Dispose resources
dispose(m_disposables);
// Cancel jobs
IFilter<IFuture<?>> testJobsFilter = Jobs.newFutureFilterBuilder().andMatchExecutionHint(m_testJobExecutionHint).toFilter();
Set<IFuture<?>> futures = Jobs.getJobManager().getFutures(testJobsFilter);
if (futures.size() > 0) {
LOG.info("Cancelling {} jobs: {}", futures.size(), futures);
Jobs.getJobManager().cancel(Jobs.newFutureFilterBuilder().andMatchFuture(futures).andMatchNotState(JobState.DONE).toFilter(), true);
long t0 = System.nanoTime();
try {
Jobs.getJobManager().awaitDone(testJobsFilter, 10, TimeUnit.SECONDS);
LOG.info("All jobs have finished after {} ms", StringUtility.formatNanos(System.nanoTime() - t0));
} catch (TimedOutError e) {
LOG.warn("Some cancelled jobs are still running after {} ms! Please check their implementation.", StringUtility.formatNanos(System.nanoTime() - t0));
}
}
uninstallTestMom();
// ensure activeMQ is stopped
BrokerService brokerService = BrokerRegistry.getInstance().findFirst();
if (brokerService != null) {
brokerService.stop();
brokerService.waitUntilStopped();
}
LOG.info("Finished test in {} ms", StringUtility.formatNanos(System.nanoTime() - m_t0));
LOG.info("</{}>", m_testName.getMethodName());
}
use of org.eclipse.scout.rt.platform.job.IFuture in project scout.rt by eclipse.
the class ExecutionHintFutureFilterTest method test.
@Test
public void test() {
// job1
IFuture<Void> future1 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint("ui-interaction-required"));
// job2
IFuture<Void> future2 = Jobs.schedule(new IRunnable() {
@Override
public void run() throws Exception {
IFuture.CURRENT.get().removeExecutionHint("ui-interaction-required");
}
}, Jobs.newInput().withExecutionHint("ui-interaction-required"));
// job3
IFuture<Void> future3 = Jobs.schedule(new IRunnable() {
@Override
public void run() throws Exception {
IFuture.CURRENT.get().addExecutionHint("ui-interaction-required");
}
}, Jobs.newInput());
// job4
IFuture<Void> future4 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput());
Jobs.getJobManager().awaitDone(Jobs.newFutureFilterBuilder().andMatchFuture(future1, future2, future3, future4).toFilter(), 10, TimeUnit.SECONDS);
IFilter<IFuture<?>> filter = new ExecutionHintFutureFilter("ui-interaction-required");
// hint added by job input
assertTrue(filter.accept(future1));
// hint is removed while running
assertFalse(filter.accept(future2));
// hint added while running
assertTrue(filter.accept(future3));
assertFalse(filter.accept(future4));
}
use of org.eclipse.scout.rt.platform.job.IFuture in project scout.rt by eclipse.
the class FutureFilterBuilderTest method testFutureExclusion.
@Test
public void testFutureExclusion() {
IExecutionSemaphore mutex = Jobs.newExecutionSemaphore(1);
IFuture<?> future1 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER));
IFuture<?> future2 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER));
IFuture<?> future3 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER));
IFuture<?> future4 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER));
IFuture<?> future5 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER));
IFuture<?> future6 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER).withExecutionSemaphore(mutex));
IFuture<?> future7 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER).withExecutionSemaphore(mutex));
IFuture<?> future8 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER).withExecutionSemaphore(mutex));
IFuture<?> future9 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER).withExecutionSemaphore(mutex));
IFuture<?> future10 = Jobs.schedule(mock(IRunnable.class), Jobs.newInput().withExecutionHint(JOB_IDENTIFIER).withExecutionSemaphore(mutex));
// One future exclusion with not other criteria
IFilter<IFuture<?>> filter = Jobs.newFutureFilterBuilder().andMatchNotFuture(future8).toFilter();
assertTrue(filter.accept(future1));
assertTrue(filter.accept(future2));
assertTrue(filter.accept(future3));
assertTrue(filter.accept(future4));
assertTrue(filter.accept(future5));
assertTrue(filter.accept(future6));
assertTrue(filter.accept(future7));
assertFalse(filter.accept(future8));
assertTrue(filter.accept(future9));
assertTrue(filter.accept(future10));
// Multiple future exclusions with not other criteria
filter = Jobs.newFutureFilterBuilder().andMatchNotFuture(future8, future9).toFilter();
assertTrue(filter.accept(future1));
assertTrue(filter.accept(future2));
assertTrue(filter.accept(future3));
assertTrue(filter.accept(future4));
assertTrue(filter.accept(future5));
assertTrue(filter.accept(future6));
assertTrue(filter.accept(future7));
assertFalse(filter.accept(future8));
assertFalse(filter.accept(future9));
assertTrue(filter.accept(future10));
// One future exclusion with other criterion (mutex)
filter = Jobs.newFutureFilterBuilder().andMatchExecutionSemaphore(mutex).andMatchNotFuture(future8).toFilter();
assertFalse(filter.accept(future1));
assertFalse(filter.accept(future2));
assertFalse(filter.accept(future3));
assertFalse(filter.accept(future4));
assertFalse(filter.accept(future5));
assertTrue(filter.accept(future6));
assertTrue(filter.accept(future7));
assertFalse(filter.accept(future8));
assertTrue(filter.accept(future9));
assertTrue(filter.accept(future10));
// Multiple future exclusion with other criterion (mutex)
filter = Jobs.newFutureFilterBuilder().andMatchExecutionSemaphore(mutex).andMatchNotFuture(future8, future9).toFilter();
assertFalse(filter.accept(future1));
assertFalse(filter.accept(future2));
assertFalse(filter.accept(future3));
assertFalse(filter.accept(future4));
assertFalse(filter.accept(future5));
assertTrue(filter.accept(future6));
assertTrue(filter.accept(future7));
assertFalse(filter.accept(future8));
assertFalse(filter.accept(future9));
assertTrue(filter.accept(future10));
}
Aggregations