This is my Class. I am using a Quartz scheduler and in that once a job is toBeExecuted, I wanted to avoid concurrency..hence used Synchronize keyword.. and used wait for each thread but it seems that once job is executed..Notify doesnt call the waiting thread ..please help...stuck on this from last two days:
public class SJobListener implements JobListener {
public static final String LISTENER_NAME = "SchedulerJobListener";
ExecutingClass compSched = new ExecutingClass();
#Override
public String getName() {
return LISTENER_NAME; //must return a name
}
// Run this if job is about to be executed.
#Override
public void jobToBeExecuted(JobExecutionContext context) {
String jobName = context.getJobDetail().getKey().toString();
System.out.println("jobToBeExecuted");
System.out.println("Listener : Job : " + jobName + " is going to start...");
System.out.println("Thread running in jobToBeExecuted :"+Thread.currentThread().getName()+" "+Thread.currentThread().getId());
synchronized (compSched) {
if(!condition)
try {
System.out.println("Going to Wait");
Thread.currentThread().wait(200);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
//Run this after job has been executed
#Override
public void jobWasExecuted(JobExecutionContext context,
JobExecutionException jobException) {
System.out.println("jobWasExecuted");
String jobName = context.getJobDetail().getKey().toString();
System.out.println("Listener :Job : " + jobName + " is finished...");
System.out.println("Thread running in jobWasExecuted :"+Thread.currentThread().getName()+" "+Thread.currentThread().getId());
//synchronized (compSched) {
System.out.println("Notifying waiting threads");
//context.notifyAll();
Thread.currentThread().notifyAll();
if (!jobException.getMessage().equals("")) {
System.out.println("Exception thrown by: " + jobName
+ " Exception: " + jobException.getMessage());
jobException.printStackTrace();
}
System.out.println("Out Of jobWasExecuted");
}
}
Thanks in advance.
Please read on java concurrency:
Threads wait on a lock. This lock is what is used to notify other threads waiting on the same lock.
Consider:
public class SynchronizedExample{
private final Object LOCK = new Object();
public void doSomethingOr() {
if(somethingIsNotDone()) {
synchronize(LOCK) {
LOCK.wait(); //trycatch here
}
}
}
public void somethingSone() {
somethingIsDone = true;
synchronized(LOCK) {
LOCK.notifyAll(); //trycatch
}
}
}
Replace Thread.currentThread().wait(200); with compSched.wait(200).
And in jobWasExecuted you should call notify on compSched
The methods jobToBeExecuted and jobWasExecuted are running in different threads so you are waiting on a different object and expecting notifications on a different object. That is why it does not work.
If you explained your requirements a bit more succinctly, a different solution could be provided other than wait notify mechanism.
Related
I have an executor service that submits x amount of threads concurrently to do a long task. I need to be able to stop all the current threads that are running and prevent queued tasks from starting. I am trying to implement a way to handle stopping threads that are waiting for a synchronized method in which the runnable passes a list of strings back to the interface that called it.
#Override
public synchronized void FilterResults(List<String> Results) {
//System.out.println("Result found: " + Results.size());
try {
Set<String> hs = new HashSet<>();
hs.addAll(Results);
Results.clear();
Results.addAll(hs);
for (String tempURL : Results) {
//System.out.println("Found url: " + tempURL);
if (!isCompleted(tempURL) && !isQueued(tempURL) && !isRunning(tempURL)) {
System.out.println("Added: " + tempURL + " to queue.");
queueLink(tempURL);
startNewThread(tempURL);
}
}
}catch(Exception e) {
}
return;
}
private synchronized void startNewThread(String seedURL) {
if (!isCompleted(seedURL) && !isRunning(seedURL) ) {
if (completedSize("") + runningSize() > 99) {
Stop();
}
String tempProxy = "";
String tempPort = "";
if (UseProxies) {
String Proxy = grabFreeProxy();
String[] splitProxy = Proxy.split(":");
tempProxy = splitProxy[0]; // 004
tempPort = splitProxy[1]; // 034556
}
//System.out.println("Proxy: " + tempProxy);
//System.out.println("Port: " + tempPort);
execService.submit(new Crawl(seedURL, this, tempProxy, tempPort, UseProxies));
removeFromQueue(url);
}
}
#Override
public Collection<String> Stop() {
try {
execService.shutdown();
if (execService.awaitTermination(45, TimeUnit.SECONDS)) {
System.out.println("task completed");
} else {
execService.shutdownNow();
}
} catch (InterruptedException e) {
}
return PROFILES;
}
The Runnable
public class Crawl implements Runnable{
public void run() {
while(!Thread.currentThread().isInterrupted() && shutdown == false) {
try {
//System.out.println(crawler.queueSize());
Thread.sleep(100);
Crawl(url);
}catch (InterruptedException e) {
Thread.currentThread().interrupt(); // set interrupt flag
}
}
public void crawl(){
try {
submitResults(urls); //Calls FilterResults()
} catch (InterruptedException e) {
// TODO Auto-generated catch block
//e.printStackTrace();
Thread.currentThread().interrupt();
}
crawler.removeUsedProxy(Proxy + ":" + Port);
this.shutdown();
}
}
When I call my shutdown method it takes 45 seconds+ is there anyway to reliably cancel the task without the long wait? This number grows as I have more threads, and since all the threads are blocking waiting to submit the results, it can take some time. If I cancel the task manually I do not care if the results are stored, I just need to be able to cancel. Any ideas?
Update I've tried ExecutorService#shutdownNow. It has not been reliable
when it comes to killing the tasks that are still blocked on the synchronized method.
Looks like you need to use ExecutorService#shutdownNow in case you don't want to wait and finish all the work and you'll receive a list with the tasks that weren't executed. You may use ExecutionService#awaitTermination (with different parameters than 45 seconds) if you want/need to provide a time to wait for the tasks to finish.
I am trying to execute 2 jobs parallel from main thread but if a callback method take long time to give response rest of requests are pause and wait to complete first.
Here is my code:
private final ExecutorService executorService = Executors.newFixedThreadPool(10);
private void executeService(String uuid) {
System.out.println("query executed done: " + uuid);
}
private String getAsynchTest(final String uuid) throws Exception {
testAsynchF = executorService.submit(
new Callable<String>() {
public String call() throws Exception {
executeService(uuid);
return getFutuerResult(uuid, Thread.currentThread()); // long processing
}
});
return testAsynchF.get();
}
public String getFutuerResult(String uuid, Thread t) {
String dummy = "your result for request: "+uuid;
if (uuid.equalsIgnoreCase("112")) {
try {
t.join();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
return dummy;
}
public static void main(String[] args) {
SynchronousTimeoutTester tester = new SynchronousTimeoutTester();
try {
String one = "112"
System.out.println("Result sync call:*** " + tester.getAsynchTest(one));
String two = "115";
System.out.println("Result sync call:**** " + tester.getAsynchTest(two));
} catch (Exception e) {
System.out.println("catched as Exception: " + e);
}
}
Why is this stopping to execute request 115 if request 112 thread is pause?
Since you pass Thread.currentThread() to getFutureResult and that method calls join() on its thread argument (in case uuid is "112"), the method will wait for its own thread to end, which it can't since it's waiting.
I want to have the main thread command a separate running thread to execute a method. The important part is that the separate thread is the one calling the method, it can not be executed on the main thread.
I have made a test-program doing what I want, but I highly doubt it's stable and would like to know if there is a better or rather right way to do this.
Below is the code:
Class Main.java
public class Main
{
public static void main(String[] args)
{
SomeThread thread = new SomeThread();
thread.start();
try { Thread.sleep(100); } catch (InterruptedException e) {}
// Manual wait ^, simulating that something should be done at a specific time
thread.somethingShouldBeDone();
thread.interrupt();
// The thread is interrupted, nothing should be done
thread.nothingShouldBeDone();
}
}
Class SomeThread.java
public class SomeThread extends Thread
{
private boolean doSomething = false;
private boolean safeInterrupted = false;
#Override
public void run()
{
while (!safeInterrupted)
{
// System.out.println(new Date().getTime() + " - " + doSomething);
if (doSomething)
{
doSomething();
doSomething = false;
}
try { sleep(10); } catch (InterruptedException e) {}
}
}
private void doSomething()
{
System.out.println(new Date().getTime() + " - Thread did something - " + Thread.currentThread().getId());
}
void somethingShouldBeDone()
{
System.out.println(new Date().getTime() + " - Something should be done");
doSomething = true;
}
void nothingShouldBeDone()
{
doSomething = true;
}
#Override
public void interrupt()
{
System.out.println(new Date().getTime() + " - Interrupting");
try { sleep(11); } catch (InterruptedException e) {}
safeInterrupted = true;
super.interrupt();
System.out.println(new Date().getTime() + " - Interrupted");
}
}
(I have experiened problems with isInterrupted(), which is why I use the variable safeInterrupted here..)
Thanks in advance for any answers or guidance.
You can use a android handler for this task.
Handler handler = new Handler(context.getMainLooper());
handler.post<Your runnable>
I have following sample created to mimic the situation i am encountering related to ExecutionService shutdown process. It seems that it terminates only one thread out of 3 something... and i get error messages on tomcat server.
public class Test {
static final ExecutorService threadExecutor = Executors.newCachedThreadPool();
static Runnable getTask(final String name) {
return new Thread() {
#Override
public void run() {
this.setName("Thread-" + name);
while (true) {
try {
System.out.println(name + " running...[" + this.getName() + "]");
Thread.sleep(10000);
} catch (InterruptedException e) {
System.out.println("InterruptedException..." + this.getName());
throw new Exception(e);
}
}
}
};
}
public static void main(String... strings) {
threadExecutor.submit(getTask("Task-1"));
threadExecutor.submit(getTask("Task-2"));
threadExecutor.submit(getTask("Task-3"));
//--
Runtime.getRuntime().addShutdownHook(new Thread() {
#Override
public void run() {
ThreadPoolExecutor tpe = (ThreadPoolExecutor) threadExecutor;
System.out.println("Active Threads=====>" + tpe.getActiveCount());
tpe.shutdown();
try {
if (!threadExecutor.awaitTermination(1000, TimeUnit.MILLISECONDS)) {
System.out.println("Executor did not terminate in the specified time.");
List<Runnable> droppedTasks = tpe.shutdownNow();
System.out.println("Shutdown thread pool forecibly. " + droppedTasks.size() + " tasks will not be executed.");
}
System.out.println("Active Threads=====>" + tpe.getActiveCount());
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
}
}
shutdown() initiates the shutdown process within the thread pool but allows current running tasks to finish. In your example the task does not finish because of while(true).
shutdownNow() initiates the shutdown and also interrupts the currently running threads. But again your task is handling that interrupted exception and running the while(true) loop.
I think you can simply share a common boolean between your tasks and caller code from where you are calling the threadPoolExecuror.shutdown(). Use that boolean in task instead of while(true).
I have 4 threads witch are printing numbers from 15 to 0.I want to control executing of my threads for example I want first to thread D to finish and after him thread C and after him thread B and finally thread A. For now they are doing it all parallel.
How can I change that? any suggestions?
Here is my code:
// Suspending and resuming a thread for Java 2
class NewThread implements Runnable {
String name; // name of thread
Thread t;
boolean suspendFlag;
NewThread(String threadname) {
name = threadname;
t = new Thread(this, name);
System.out.println("New thread: " + t);
suspendFlag = false;
t.start(); // Start the thread
}
// This is the entry point for thread.
public void run() {
try {
for(int i = 15; i > 0; i--) {
System.out.println(name + ": " + i);
Thread.sleep(200);
synchronized(this) {
while(suspendFlag) {
wait();
}
}
}
} catch (InterruptedException e) {
System.out.println(name + " interrupted.");
}
System.out.println(name + " exiting.");
}
void mysuspend() {
suspendFlag = true;
}
synchronized void myresume() {
suspendFlag = false;
notify();
}
}
public class SuspendResume {
public static void main(String args[]) {
NewThread A = new NewThread("A");
NewThread B = new NewThread("B");
NewThread C = new NewThread("C");
NewThread D = new NewThread("D");
// try {
// System.out.println("****************************************************************");
// System.out.println(A.t.getState());
// System.out.println(B.t.getState());
// System.out.println(C.t.getState());
// System.out.println(D.t.getState());
//
// if(D.t.isAlive())
// {
// System.out.println("Bla bla bla");
// }
//
// Thread.sleep(1000);
// A.mysuspend();
// System.out.println("Suspending thread One");
// Thread.sleep(1000);
// A.myresume();
// System.out.println("Resuming thread One");
// B.mysuspend();
// System.out.println("Suspending thread Two");
// Thread.sleep(1000);
// B.myresume();
// System.out.println("Resuming thread Two");
//
//
//
// } catch (InterruptedException e) {
// System.out.println("Main thread Interrupted");
// }
// wait for threads to finish
try {
System.out.println("Waiting for threads to finish.");
A.t.join();
B.t.join();
C.t.join();
D.t.join();
} catch (InterruptedException e) {
System.out.println("Main thread Interrupted");
}
System.out.println("Main thread exiting.");
}
}
I think you should design structure of you service class first. I can suggest following:
public class Service {
private List<Service> dependencies;
// Starts service.
// It should wait until all dependencies started using awaitStart method and then start itself
public void start();
// Blocks current thread until service is started.
// If it is started returns immediately.
public void awaitStart();
// Stops service.
// Awaits until all dependencies are stopped using awaitStop.
public void stop();
// Blocks current thread until service is stopped.
// If it is already stops returns immediately
public void awaitStop();
// Actual code that has service specific code.
// This method may be invoked as last line in 'start' method.
public void run();
}
Next problem is to implement start and awaitStart (stop methods implemented similar). I recommend to use tools from java.util.concurrent for implementing awaitStart method. E.g. CountDownLatch. Each service has it's own latch that indicates that server is started. So code for awaitStart and start is following:
private CountDownLatch started = new CountDownLatch(1);
public void awaitStart() {
started.await();
}
public void start() {
for (Service service : dependencies) {
service.awaitStart();
}
System.out.println("Service " + name + " is started");
started.countDown();
run();
}