jakarta-cactus-user mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Jayaraman.Do...@transplace.com
Subject Re: Testing a MDB on its own
Date Tue, 25 May 2004 20:12:41 GMT

Thanks for your reply. Now I understand what and how the MDB's need to be
unit tested.

But, I would like to "integrate test" to ensure all the components MDB1,
session ejb and MDB2 combined together works fine.  This will give me the
confidence that the functional unit  works together fine.

<quote from cactus home page>
                                                                                         
                            
      There are several kinds of unit testing frameworks. We categorize them in 3 types: 
                            
         1. Type 1: code logic unit testing. Probably the best strategy for these tests is
to use a Mock Objects type 
            framework.                                                                   
                            
         2. Type 2: integration unit testing. Cactus is typically in this category (we'll
let you judge if it is the  
            best or not :)). These tests will exercise the interactions with the container.
                          
         3. Type 3: functional unit testing. These unit tests will let you test the returned
values from your server  
            code. This is for example HttpUnit (Note that HttpUnit also performs standard
functional testing - as     
            opposed to functional unit testing -, which let you test full use cases - a login
use case for example,   
            which is comprised of several requests/responses).                           
                            
                                                                                         
                            
                                                                                         
                            
      Ideally you would use 3 different frameworks just to unit test your code ! Then you
have to think about         
      acceptance testing, system integration testing, ...                                
                            
                                                                                         
                            
                                                                                         
                            
      Cactus was developed to fit Type 2 but also to be a very good compromise for types 1
and 3, with the idea that  
      it is much easier to have to write tests for a single framework than for several ! Moreover,
you can never      
      fully test your code. We believe Cactus provides a middle ground that provides a high
confidence that your code 
      will run when deployed. However, it is your choice and you can use Cactus only for type
2 if you wish.          
                                                                                         
                            


</quote>

Does my problem come under functional unit testing? If so, does/will the
cactus framework help do the "functional test" consisting of several server
components put together.

If there are no suggested approach to"integrate test", I would like to use
Thread.sleep() till the MDB1, session ejb and MDB2 completes and then test
the records created. It also tests that all the components completes within
the stipulated time, which also works fine for me. Do you see any problems
with this?

Thanks  again
Jayaraman





                                                                                         
                                             
                      "J. B.                                                             
                                             
                      Rainsberger"             To:       Cactus Users List <cactus-user@jakarta.apache.org>
                           
                      <jbrains@rogers.c        cc:                                    
                                                
                      om>                      Subject:  Testing a MDB on its own     
                                                
                                                                                         
                                             
                      05/25/2004 12:58                                                   
                                             
                      PM                                                                 
                                             
                      Please respond to                                                  
                                             
                      "Cactus Users                                                      
                                             
                      List"                                                              
                                             
                                                                                         
                                             
                                                                                         
                                             




Jayaraman.Dorai@transplace.com wrote:

> I am not sure I understood the solution completely, let me explain my
> problem again.  May be I should read the books suggested.
>
> There are 3 components a) the MDB (lets say MDB1)  which I want to test,
b)
> the session ejb,  and c) another MDB  (lets say MDB2)  which the session
> ejb calls.
>
> Now, if I call the extracted method in the MDB1 directly, it will make a
> further call to session ejb which in turns asynchronously calls MDB2.
Both
> session ejb and MDB2 create records in the database. Now I want to test
> that the records are being properly created. The testXXX() method will
> succeed  for only the records created in the session ejb and will fail
for
> the tests of  records created in MDB2 as the MDB2 may not have been
> completed. Now I have a situation where MDB1 did not fail but the test
> cases shows it has failed.
>
> Will mock objects or the suggested techniques, help me test the MDB1
> completely?

To summarize:

MDB1 -> SessionEJB -> MDB2

You define success for MDB1 as "the right records are created in the
database."

Now, it is possible for MDB1 to succeed, but your success condition not
to occur: if, say, MDB2 fails.

Do you want your test for MDB1 to fail if only MDB2 fails? I say "no,"
because then it's not a test for MDB1, but rather an integration test.

NOTE: I AM NOT SAYING THAT INTEGRATION TESTS ARE BAD. I /am/ saying that
you seem only to want to test MDB1, and so you do not want to write an
integration test, as that test might fail even through MDB1 works.

THEREFORE, we need to redesign so that MDB1 can run without MDB2. This
way we can test MDB1 separately without relying on the correctness of MDB2.

NOW, MDB1 uses JNDI to retrieve a component interface for SessionEJB. At
some point, MDB1 invokes a method on SessionEJB /which is expected
eventually to result in records being created in the database/. I don't
know what that method is, but let's say it's doWork().

interface SessionComponent {
     void doWork() throws Exception;
}

The idea is that the SessionBean implements doWork() to send a message
that you expect MDB2 to handle, leading it then to create records in the
database.

THEREFORE, ASSUME THAT WHEN YOU INVOKE doWork(), THAT IT WILL CORRECTLY
CREATE RECORDS IN THE DATABASE. You're not testing this right now.
You're testing whether MDB1 does the right thing, which includes
invoking SessionComponent.doWork().

My definition of success is now this: MDB1 should invoke
SessionComponent.doWork() exactly once.

With mock objects, I can write that test:

[pseudocode, similar to jMock]
testMdb1 {
     sessionComponent = create mock for SessionComponent

     sessionComponent.expect("doWork" invoked 1 time with no parameters,
returning nothing)
     sessionComponent.readyToGo()

     message = create mock for Message
     message.expect(whatever methods you need to invoke to retrieve
data, returning fake data)
     message.readyToGo()

     mdb1 = new MessageDrivenBean1()
     mdb1.processMessage(message, sessionComponent)

     sessionComponent.verify()
}

To make this test pass, I need to redesign MDB1 the way I discussed
earlier.

[pseudocode]
class MessageDrivenBean1 ... {
     public void onMessage(Message message) {
         sessionComponent = lookup session EJB with JNDI
         processMessage(message, sessionComponent)
     }

     public void processMessage(Message message, SessionComponent
sessionComponent) {
         do the real work
     }
}

Now you don't have to drag JNDI, the database or the EJB container into
the test: you can test MDB1 on its own! As far as the JNDI lookup goes,
that's still untested, but the majority of the real work /is/ tested,
and that's a very good start. Once you're comfortable with this, we can
talk about good strategies for testing the JNDI lookup. (Hint:
www.mockejb.org)

Better?

[BTW: This is /almost/ an excerpt from my book, so that gives you an
idea what's in there.]
--
J. B. Rainsberger,
Diaspar Software Services
http://www.diasparsoftware.com :: +1 416 791-8603
Let's write software that people understand

---------------------------------------------------------------------
To unsubscribe, e-mail: cactus-user-unsubscribe@jakarta.apache.org
For additional commands, e-mail: cactus-user-help@jakarta.apache.org







Mime
View raw message