2

I want to start max 40 http requests each second and after 1 second, I want it to run another 40 from its own queue(like threadpooltaskexecutor's blocking queue). I am looking for an executor or thread pool implementation for this requirement.

Any recommendations?

Thx

Ali

EDIT: Fix rate is not efficient for the obvious reasons. As the queue items start one by one, the ones on the back of the queue will be just started but ones that has been started for a while may be finished.

Extra EDIT: The problem is to call only 40 request in a second, not have max 40 active. It can be 80 at other second but in 1 second there should only 40 newly created connections.

Neron
  • 1,500
  • 7
  • 30
  • 52
  • In general, Do you want to schedule some tasks any invoke them after fixed intervals ? – sol4me Sep 18 '14 at 15:50
  • I think the problem is clear. fixed interval is a solution but not efficient because you will say that each 25 milliseconds I need to start one but as you can see my 40th thread will be started nearly after 1 second. But with bulk start, this will not happen – Neron Sep 18 '14 at 16:11

2 Answers2

0

One way to do this is to use another architecture, it will make the process that much easiser.

1) Create a Thread class that implements the runnable. 2) It takes as parameters a list<>() of http requests that you want to make 3) Make the run() function loop the entire list (size 40) 4) Let the thread live for one second.

Here is a sample example:

class MyClass extends Thread

private ArrayList<...> theList;

public MyClass(ArrayList<..> theList){
    this.theList = theList;
}

public void run(){
    //Here, you simply want to loop for the entier list (max 40)
    for(Req r: theList){
        r.sendRequest()
    )
}

public statc void main(String args[]){
  //Create an instance of your thread:
  MyClass t = new MyClass(ReqList<..>());

  //Now that you have your thread, simply do the following:

  while(true){
     t = new MyClass( (insert your new list));
     t.start();
     try{
       Thread.sleep(1000);
     }catch(Exception e){

     }
  )



}
}

And there you have it

Ahmed Elmir
  • 163
  • 6
  • 1
    No, not correct. You just forgot to return the responses to the caller! And there is also no thread queue, or restriction of 40 etc. – Neron Sep 18 '14 at 16:13
0

First define a class that implements Callable which will do your thread's treatment :

class MyClass implements Callable<String>
{
    /**
     * Consider this as a new Thread.
    */
    @Override
    public String call()
    {
        //Treatment...

        return "OK"; //Return whatever the thread's result you want to be then you can access it and do the desired treatment.
    }
}

Next step is to create an ExecutorService in my example, a Thread pool and throw in some tasks.

int nbThreadToStart = 40;

ExecutorService executor = Executors.newFixedThreadPool(/* Your thread pool limit */);

List<Future<String>> allTasks = new ArrayList<Future<String>>(/* Specify a number here if you want to limit your thread pool */);

for(int i = 0; i < 10; i++)//Number of iteration you want
{
    for(int i = 0; i < nbThreadToStart; i++)
    {
        try
        {
            allTasks.add(executor.submit(new MyClass()));
        }
        catch(Exception e)
        {
            e.printStackTrace();
        }
    }

    try
    {
        Thread.sleep(1000);
    }
    catch(Exception e)
    {
      e.printStackTrace();
    }
}

executor.shutdown();

//You can then access all your thread(Tasks) and see if they terminated and even add a timeout :

try
{
    for(Future<String> task : allTasks)
        task.get(60, TimeUnit.SECONDS);//Timeout of 1 seconds. The get will return what you specified in the call method.
}
catch (TimeOutException te)
{
    ...
}
catch(InterruptedException ie)
{
    ...
}
catch(ExecutionException ee)
{
    ...
}

I'm not sure what you really want, but I think you should handle multi-threading with a thread pool specially if you're planning on receiving a lot of requests to avoid any undesired memory leak etc.

If my example is not clear enough, note that there is many other methods offered by ExexutorService,Future etc. that are very usefull when dealing with Thread.

Check this out :

http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/Executors.html http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/Executor.html http://docs.oracle.com/javase/7/docs/api/java/util/concurrent/Future.html

That's it for my recommandations.

Jean-François Savard
  • 20,626
  • 7
  • 49
  • 76
  • I know I have checked out the types on spring, java core etc. YOur solution is close but not flexible. The iteration countshould be unnecessary because there are maybe incoming callables on the way so, the list is not fixed – Neron Sep 19 '14 at 07:17