Dietmar, I ran your code and so far I dont see a hang. I ran this code
multiple times on my 2-Core Thinkpad. Perhaps if you run this
on a machine with more CPUs the timing changes and causes a race condition
that results in a hang. I just dont see it.

I *am* getting a hang if I dont provide enough memory to the process.  I
tried to run your code with 200 threads
and 600M memory and I got OOM and eventual hang. There were a lot of
exceptions though which you say you dont see
when you run. I've noticed that your code uses log4j, perhaps the exceptions
are in the log?

JC

2010/12/10 Dietmar Gräbner <d.graeb...@gmail.com>

> Hi,
>
> I tested your example and worked for both configurations
> (MeetingDetectorTae with and without the <analysisEngine> part. The
> main difference between your client and mine is the separation of the
> initialize and the submit process in your example.
> Here is my code (Main class and Worker Thread):
>
> The main class:
>
>
> import org.apache.log4j.Logger;
> import org.apache.log4j.xml.DOMConfigurator;
>
> /**
>  *
>  * A multithreaded testClient calling a worker.
>  *
>  */
> public class MultithreadedTestClient {
>
>    //a server timeout not used in the current example
>    public static final int LINGREP_SERVER_CONNECTION_TIMEOUT = 600000;
>    public static final int TEST_NUMBEROFTHREADS = 100; // 10 threads
>
>
>    public static Logger theLog =
> Logger.getLogger(MultithreadedTestClient.class);
>    /**
>     * Main method for the test
>     *
>     * @param args no arguments are parsed
>     * @throws Exception some problem
>     */
>    public static void main(java.lang.String args[]) throws Exception {
>
>        // specify logfile settings
>        if (System.getProperty("log4j.configuration")==null){
>            DOMConfigurator.configure("resources/config/log4j.xml");
>        }
>
>        for (int i = 0; i < TEST_NUMBEROFTHREADS; i++) {
>            Runnable r = new MinimalWorkerThread(i);
>            new Thread(r).start();
>        }
>    }
>
> }
>
> And the Thread Worker:
>
> import java.util.HashMap;
> import java.util.Map;
>
> import org.apache.uima.aae.client.UimaAsynchronousEngine;
> import org.apache.uima.adapter.jms.client.BaseUIMAAsynchronousEngine_impl;
> import org.apache.uima.cas.CAS;
>
> /**
>  * a runnable initializing and calling the Webservice
>  */
> public class MinimalWorkerThread implements Runnable {
>
>    private int mId = 0;
>    /**
>     * Start time of the processing - used to compute elapsed time.
>     */
>    private UimaAsynchronousEngine uimaEEEngine = null;
>     Map<String, Object> appCtx = new HashMap<String, Object>();
>
>     /**
>     * Constructor for the class. Parses command line arguments and
> sets the values of fields in this
>     * instance. If command line is invalid prints a message and calls
> System.exit().
>     *
>     * @param args
>     *          command line arguments into the program - see class
> description
>     */
>    public MinimalWorkerThread(int id) throws Exception {
>        mId = id;
>        //Initzialize the AppContext
>        uimaEEEngine = new BaseUIMAAsynchronousEngine_impl();
>         // Add Broker URI
>        appCtx.put(UimaAsynchronousEngine.ServerUri,
> "tcp://143.205.174.93:61616");
>        // Add Endpoint
>        appCtx.put(UimaAsynchronousEngine.Endpoint,
> "MeetingDetectorTaeQueue");
>         appCtx.put(UimaAsynchronousEngine.CasPoolSize, 1);
>    }
>
>     public void run() {
>
>        try {
>            System.out.println("running " + mId);
>            //initialize the client
>            uimaEEEngine.initialize(appCtx);
>            String text = "Id " + mId +"This is a nice test sentence.
> And a second. Including a third.";
>            // send an empty CAS
>            CAS cas = uimaEEEngine.getCAS();
>            //cas.setDocumentLanguage("en");
>            cas.setDocumentText(text);
>            uimaEEEngine.sendAndReceiveCAS(cas);
>            uimaEEEngine.collectionProcessingComplete();
>            System.out.println("Thread id " + mId + " returned " +
> cas.getDocumentText().substring(0, 5));
>            cas.reset();
>            uimaEEEngine.stop();
>        } catch (Exception e) {
>            System.err.println("Exception during Processing!");
>            e.printStackTrace();
>         }
>    }
> }
>
>
>
>
>
>
>
>
>
> On Thu, Dec 9, 2010 at 5:21 PM, Jaroslaw Cwiklik <uim...@gmail.com> wrote:
> > For some reason attachment dont seem to work. Here is my code:
> >
> > /*
> >  * Licensed to the Apache Software Foundation (ASF) under one
> >  * or more contributor license agreements.  See the NOTICE file
> >  * distributed with this work for additional information
> >  * regarding copyright ownership.  The ASF licenses this file
> >  * to you under the Apache License, Version 2.0 (the
> >  * "License"); you may not use this file except in compliance
> >  * with the License.  You may obtain a copy of the License at
> >  *
> >  *   http://www.apache.org/licenses/LICENSE-2.0
> >  *
> >  * Unless required by applicable law or agreed to in writing,
> >  * software distributed under the License is distributed on an
> >  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
> >  * KIND, either express or implied.  See the License for the
> >  * specific language governing permissions and limitations
> >  * under the License.
> >  */
> >
> >
> > import java.util.HashMap;
> > import java.util.Map;
> > import java.util.concurrent.ArrayBlockingQueue;
> > import java.util.concurrent.CountDownLatch;
> > import java.util.concurrent.ThreadPoolExecutor;
> > import java.util.concurrent.TimeUnit;
> >
> > import org.apache.uima.aae.client.UimaAsynchronousEngine;
> > import
> org.apache.uima.adapter.jms.client.BaseUIMAAsynchronousEngine_impl;
> > import org.apache.uima.cas.CAS;
> >
> > /**
> >  * Example client application that can instantiate multiple UIMA AS
> clients
> > each running in
> >  * a separate thread.
> >  * <p>
> >  * Arguments: brokerUrl endpoint <howManyCASesToSend> <scaleup>
> >  * <p>
> >  * The application creates as many UIMA AS clients and threads as
> specified
> > in the "scaleup"
> >  * argument. Each instance runs in its own thread and has is its own temp
> > reply queue. It
> >  * uses a synchronous <i>sendAndReceive()</i> to send CASes to a remote
> > service. For this
> >  * a CAS Pool containing a single CAS is sufficient.
> >  * <p>
> >  * Each client sends as many CASes to a remote service as specified in
> the
> > "howManyCASesToSend"
> >  * argument.
> >  * <p>
> >  * The application initializes a CountDownLatch to the number of
> > clients/threads which is than
> >  * used to await completion. When a worker thread completes its run, it
> > sends a CPC and counts down the
> >  * latch reducing the number of busy threads. When all threads finish,
> the
> > application is notified
> >  * and can proceed to cleanup and shutdown.
> >  *
> >  */
> > public class MultithreadedClientApp {
> > public CountDownLatch latch = null;
> > public void initializeAndRun(String[] args) throws Exception {
> > try {
> > int howManyWorkers = Integer.parseInt(args[3]);  // how many threads
> > latch = new CountDownLatch(howManyWorkers);  // each worker counts down
> when
> > done
> > // Create Worker threads
> > ClientWorker[] workers = new ClientWorker[howManyWorkers];
> > final ArrayBlockingQueue<Runnable> queue = new
> ArrayBlockingQueue<Runnable>(
> > howManyWorkers);
> > // Thread Pool Executor to manages threads
> > ThreadPoolExecutor threadPool = new ThreadPoolExecutor(howManyWorkers,
> > howManyWorkers,
> >                Integer.MAX_VALUE, TimeUnit.SECONDS, queue);
> > // Start all threads
> > threadPool.prestartAllCoreThreads();
> > for( int i=0; i < howManyWorkers; i++ ) {
> > workers[i] = new ClientWorker();
> > // 0 - brokerURL, 1 - queue name, 2 - how many CASes to send
> > workers[i].initialize(args[0],args[1],Integer.parseInt(args[2]));
> > }
> >
> > for( int i=0; i < howManyWorkers; i++ ) {
> > threadPool.submit(workers[i]);  // start the workers
> > }
> > // Each worker counts down the latch after it is done sending CASes
> > latch.await();
> >  // All worker threads completed, now stop the clients
> > for( int i=0; i < howManyWorkers; i++ ) {
> > workers[i].stop();  // stop UIMA AS clients
> > }
> >
> > threadPool.shutdown();  // cleanup thread pool
> >  System.out.println("All UIMA AS Clients Finished Processing");
> > } catch( Exception e ) {
> > e.printStackTrace();
> > }
> >  }
> > public static void main(String[] args) {
> > MultithreadedClientApp client = new MultithreadedClientApp();
> > try {
> > if ( args.length != 4 ) {
> > System.out.println("Usage: ");
> > }
> > client.initializeAndRun(args);
> > } catch( Exception e ) {
> > e.printStackTrace();
> > }
> > }
> > public class ClientWorker implements Runnable {
> > private BaseUIMAAsynchronousEngine_impl uimaASClient = null;
> > private int howManyCASes = 0;
> > public void initialize(String brokerUrl, String endpoint, int
> howManyCASes )
> > throws Exception {
> >  uimaASClient = new BaseUIMAAsynchronousEngine_impl();
> > Map<String, Object> appCtx = new HashMap<String, Object>();
> >    // set server URI and Endpoint
> >    // Add Broker URI
> >    appCtx.put(UimaAsynchronousEngine.ServerUri, brokerUrl);
> >    // Add Queue Name
> >    appCtx.put(UimaAsynchronousEngine.Endpoint, endpoint);
> >    // Add the Cas Pool Size and initial FS heap size
> >    appCtx.put(UimaAsynchronousEngine.CasPoolSize, 1);
> >
> >    // initialize
> >    uimaASClient.initialize(appCtx);
> >    this.howManyCASes = howManyCASes;
> > }
> > public void stop() {
> > uimaASClient.stop();
> > }
> > public void run() {
> > try {
> >    int sentSoFar = 0;
> >             CAS cas = uimaASClient.getCAS();
> >             int count=1;
> >     while( sentSoFar < howManyCASes ) {
> >
> >          cas.setDocumentText("Some Text");
> >
> >          uimaASClient.sendAndReceiveCAS(cas);
> >          System.out.println("Thread:"+Thread.currentThread().getId()+":::
> > Success Calling sendAndReceiveCAS(). Sent "+count++ + " CASes so far");
> >          cas.reset();
> >          sentSoFar++;
> >     }
> >     uimaASClient.collectionProcessingComplete();
> >     System.out.println("Thread::"+Thread.currentThread().getId()+" Sent
> > CPC. Thread Done");
> >     latch.countDown();
> > } catch( Exception e) {
> > e.printStackTrace();
> > }
> > }
> > }
> > }
> >
> >
> >
> >
> > On Thu, Dec 9, 2010 at 11:04 AM, Jaroslaw Cwiklik <uim...@gmail.com>
> wrote:
> >
> >> Dietmar, I tried my example application with an Aggregate Service and
> see
> >> no problem. Your previous email had no source attached.
> >> Attached please find an example application code I use in my testing. To
> >> run it"
> >>
> >> java -cp <classpath> MultithreadedClientApp
> >>
> <brokerURL><serviceQueueName><howManyCASesEachThreadShouldSend><howManyThreads>
> >>
> >> The code adds a short text to each CAS before each call to
> >> sendAndReceive(). There are no app listeners attached to UIMA AS client.
> >>
> >> Jerry
> >>
> >> 2010/12/9 Dietmar Gräbner <d.graeb...@gmail.com>
> >>
> >> Hi Eddie,
> >>>
> >>> wouldn't the client requests be serialized in the szenario you propose?
> >>>
> >>> Dietmar
> >>>
> >>>
> >>>
> >>> On Tue, Dec 7, 2010 at 10:54 PM, Eddie Epstein <eaepst...@gmail.com>
> >>> wrote:
> >>> > 2010/12/7 Dietmar Gräbner <d.graeb...@gmail.com>:
> >>> >> I wrote a test client creating multiple threads. Each thread
> >>> >> instantiates a BaseUIMAAsynchronousEngine_impl and invokes a uima
> >>> >> aggregate with the sendAndReceiveCAS() call. When running the
> program
> >>> >> with e.g. 100 Threads the client gets stuck after processing X
> calls.
> >>> >
> >>> > FWIW, a similar multithreaded client scenario that has been used with
> >>> > no problems is to instantiate a single
> BaseUIMAAsynchronousEngine_impl
> >>> > with big enough casPool and have each thread call sendAndReceiveCAS()
> >>> > using the common API object.
> >>> >
> >>> > Eddie
> >>> >
> >>>
> >>
> >>
> >
>

Reply via email to