Source Code Cross Referenced for InviteClientTransactionsStateMachineTest.java in  » 6.0-JDK-Modules » Java-Advanced-Imaging » test » tck » msgflow » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » 6.0 JDK Modules » Java Advanced Imaging » test.tck.msgflow 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


0001:        /*
0002:         * Conditions Of Use 
0003:         * 
0004:         * This software was developed by employees of the National Institute of
0005:         * Standards and Technology (NIST), and others. 
0006:         * This software is has been contributed to the public domain. 
0007:         * As a result, a formal license is not needed to use the software.
0008:         * 
0009:         * This software is provided "AS IS."  
0010:         * NIST MAKES NO WARRANTY OF ANY KIND, EXPRESS, IMPLIED
0011:         * OR STATUTORY, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTY OF
0012:         * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, NON-INFRINGEMENT
0013:         * AND DATA ACCURACY.  NIST does not warrant or make any representations
0014:         * regarding the use of the software or the results thereof, including but
0015:         * not limited to the correctness, accuracy, reliability or usefulness of
0016:         * the software.
0017:         * 
0018:         * 
0019:         */
0020:        package test.tck.msgflow;
0021:
0022:        import java.util.TooManyListenersException;
0023:
0024:        import javax.sip.*;
0025:        import javax.sip.header.ContactHeader;
0026:        import javax.sip.header.ToHeader;
0027:        import javax.sip.message.Request;
0028:        import javax.sip.message.Response;
0029:
0030:        import org.apache.log4j.Logger;
0031:
0032:        import junit.framework.Test;
0033:        import junit.framework.TestSuite;
0034:        import test.tck.TckInternalError;
0035:        import test.tck.TiUnexpectedError;
0036:
0037:        /**
0038:         * The test tries to verify that Invite Client Transactions correctly change
0039:         * states as specified by the rfc3261. The Tested Implementation is used to send
0040:         * requests and the ReferenceImplementation issues (or not) corresponding
0041:         * responses. ClientTransaction states are constantly queried and compared to
0042:         * those in the state machine described in section 17.1.1 of rfc3261
0043:         * 
0044:         * <pre>
0045:         * 
0046:         *                               |INVITE from TU
0047:         *             Timer A fires     |INVITE sent
0048:         *             Reset A,          V                      Timer B fires
0049:         *             INVITE sent +-----------+                or Transport Err.
0050:         *               +---------|           |---------------+inform TU
0051:         *               |         |  Calling  |               |
0052:         *               +--------&gt;|           |--------------&gt;|
0053:         *                         +-----------+ 2xx           |
0054:         *                            |  |       2xx to TU     |
0055:         *                            |  |1xx                  |
0056:         *    300-699 +---------------+  |1xx to TU            |
0057:         *   ACK sent |                  |                     |
0058:         * esp. to TU |  1xx             V                     |
0059:         *            |  1xx to TU  -----------+               |
0060:         *            |  +---------|           |               |
0061:         *            |  |         |Proceeding |--------------&gt;|
0062:         *            |  +--------&gt;|           | 2xx           |
0063:         *            |            +-----------+ 2xx to TU     |
0064:         *            |       300-699    |                     |
0065:         *            |       ACK sent,  |                     |
0066:         *            |       resp. to TU|                     |
0067:         *            |                  |                     |      NOTE:
0068:         *            |  300-699         V                     |
0069:         *            |  ACK sent  +-----------+Transport Err. |  transitions
0070:         *            |  +---------|           |Inform TU      |  labeled with
0071:         *            |  |         | Completed |--------------&gt;|  the event
0072:         *            |  +--------&gt;|           |               |  over the action
0073:         *            |            +-----------+               |  to take
0074:         *            |              &circ;   |                     |
0075:         *            |              |   | Timer D fires       |
0076:         *            +--------------+   | -                   |
0077:         *                               |                     |
0078:         *                               V                     |
0079:         *                         +-----------+               |
0080:         *                         |           |               |
0081:         *                         | Terminated|&lt;--------------+
0082:         *                         |           |
0083:         *                         +-----------+
0084:         * 
0085:         *                 Figure 5: INVITE client transaction
0086:         * 
0087:         * 
0088:         * </pre>
0089:         * 
0090:         * TODO Currently, transactions' behaviour is not tested for misappropriation of
0091:         * incoming messages.
0092:         * 
0093:         * TODO Currently, invite transactions are not tested for proper termination
0094:         * upon respective timeouts.
0095:         * 
0096:         * @author Emil Ivov Network Research Team, Louis Pasteur University,
0097:         *         Strasbourg, France. This code is in the public domain.
0098:         * @version 1.0
0099:         */
0100:        public class InviteClientTransactionsStateMachineTest extends
0101:                MessageFlowHarness {
0102:
0103:            private static Logger logger = Logger
0104:                    .getLogger(InviteClientTransactionsStateMachineTest.class);
0105:
0106:            public InviteClientTransactionsStateMachineTest(String name) {
0107:                super (name, false); // disable auto-dialog for the RI, else ACKs get
0108:                // filtered out
0109:            }
0110:
0111:            // ==================== tests ==============================
0112:
0113:            /**
0114:             * Tries to steer a TI client transaction through the following scenario
0115:             * Calling-->Proceeding-->Completed-->Terminated. Apart from state
0116:             * transitions, we also test, retransmissions and proper hiding/passing of
0117:             * messages to the TU.
0118:             */
0119:            public void testCallingProceedingCompletedTerminatedScenario() {
0120:                try {
0121:                    Request invite = createTiInviteRequest(null, null, null);
0122:                    ClientTransaction tran = null;
0123:                    try {
0124:                        eventCollector.collectRequestEvent(riSipProvider);
0125:                        tran = tiSipProvider.getNewClientTransaction(invite);
0126:                        tran.sendRequest();
0127:                    } catch (SipException ex) {
0128:                        throw new TiUnexpectedError(
0129:                                "A SipExceptionOccurred while trying to send request!",
0130:                                ex);
0131:                    } catch (TooManyListenersException ex) {
0132:                        throw new TckInternalError(
0133:                                "Failed to regiest a SipListener with an RI SipProvider",
0134:                                ex);
0135:                    }
0136:                    waitForMessage();
0137:                    RequestEvent inviteReceivedEvent = eventCollector
0138:                            .extractCollectedRequestEvent();
0139:                    if (inviteReceivedEvent == null
0140:                            || inviteReceivedEvent.getRequest() == null)
0141:                        throw new TiUnexpectedError(
0142:                                "The invite request was not received by the RI!");
0143:                    // At this point the ClientTransaction should be CALLING!
0144:                    assertEquals(TransactionState.CALLING, tran.getState());
0145:                    // Check Request retransmission
0146:                    try {
0147:                        eventCollector.collectRequestEvent(riSipProvider);
0148:                    } catch (TooManyListenersException ex) {
0149:                        throw new TckInternalError(
0150:                                "Failed to regiest a SipListener with an RI SipProvider",
0151:                                ex);
0152:                    }
0153:                    // Wait for the retransmission timer to fire if it had not already
0154:                    // done so.
0155:                    if (tran.getRetransmitTimer() > MESSAGES_ARRIVE_FOR)
0156:                        sleep((long) tran.getRetransmitTimer()
0157:                                - MESSAGES_ARRIVE_FOR); // subtract
0158:                    // the
0159:                    // time
0160:                    // we
0161:                    // waited
0162:                    // for
0163:                    // the
0164:                    // invite
0165:                    // Wait for the retransmitted request to arrive
0166:                    waitForMessage();
0167:                    inviteReceivedEvent = eventCollector
0168:                            .extractCollectedRequestEvent();
0169:                    assertNotNull("The invite request was not retransmitted!",
0170:                            inviteReceivedEvent);
0171:                    assertNotNull("The invite request was not retransmitted!",
0172:                            inviteReceivedEvent.getRequest());
0173:                    assertEquals(Request.INVITE, inviteReceivedEvent
0174:                            .getRequest().getMethod());
0175:                    // At this point the ClientTransaction should STILL be CALLING!
0176:                    assertEquals(TransactionState.CALLING, tran.getState());
0177:                    // Send a TRYING response
0178:                    try {
0179:                        eventCollector.collectResponseEvent(tiSipProvider);
0180:                    } catch (TooManyListenersException ex) {
0181:                        throw new TiUnexpectedError(
0182:                                "Failed to register a SipListener with TI", ex);
0183:                    }
0184:                    try {
0185:                        Response resp = riMessageFactory.createResponse(
0186:                                Response.TRYING, inviteReceivedEvent
0187:                                        .getRequest());
0188:                        addStatus(inviteReceivedEvent.getRequest(), resp);
0189:                        riSipProvider.sendResponse(resp);
0190:                    } catch (Throwable ex) {
0191:                        throw new TckInternalError(
0192:                                "The TCK could not send a trying response back to the TI",
0193:                                ex);
0194:                    }
0195:
0196:                    waitForMessage();
0197:                    // Analyze the TRYING response and Tran state back at the TI
0198:                    ResponseEvent responseEvent = eventCollector
0199:                            .extractCollectedResponseEvent();
0200:                    assertNotNull(
0201:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0202:                            responseEvent);
0203:                    assertNotNull(
0204:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0205:                            responseEvent.getResponse());
0206:                    assertTrue(
0207:                            "A response different from TYING was passed to the TU!",
0208:                            responseEvent.getResponse().getStatusCode() == Response.TRYING);
0209:                    assertSame(
0210:                            "The TRYING response was not associated with the right transaction.",
0211:                            tran, responseEvent.getClientTransaction());
0212:                    // verify the the tran state is now PROCEEDING
0213:                    assertEquals(
0214:                            "The ClientTransaction did not pass in the PROCEEDING state after "
0215:                                    + "receiving 1xx provisional response",
0216:                            tran.getState(), TransactionState.PROCEEDING);
0217:                    // Send a 486 BUSY HERE (final) response from the RI
0218:                    try {
0219:                        eventCollector.collectResponseEvent(tiSipProvider);
0220:                    } catch (TooManyListenersException ex) {
0221:                        throw new TiUnexpectedError(
0222:                                "Failed to register a SipListener with TI", ex);
0223:                    }
0224:                    // The BUSY_HERE response should trigger some ACKs so let's register
0225:                    // a listener with the RI
0226:                    SipEventCollector ackCollector = new SipEventCollector();
0227:                    try {
0228:                        ackCollector.collectRequestEvent(riSipProvider);
0229:                    } catch (TooManyListenersException ex) {
0230:                        throw new TckInternalError(
0231:                                "Failed to regiest a SipListener with an RI SipProvider",
0232:                                ex);
0233:                    }
0234:                    Response busyHere = null;
0235:                    try {
0236:                        busyHere = riMessageFactory.createResponse(
0237:                                Response.BUSY_HERE, inviteReceivedEvent
0238:                                        .getRequest());
0239:                        addStatus(inviteReceivedEvent.getRequest(), busyHere);
0240:
0241:                        // JvB: set to-tag too, mandatory and tests that ACK is properly
0242:                        // formatted
0243:                        ((ToHeader) busyHere.getHeader("to"))
0244:                                .setTag("busy-here");
0245:
0246:                        riSipProvider.sendResponse(busyHere);
0247:                    } catch (Throwable ex) {
0248:                        throw new TckInternalError(
0249:                                "The TCK could not send a BUSY HERE response back to the TI",
0250:                                ex);
0251:                    }
0252:                    waitForMessage();
0253:
0254:                    // Analyze the BUSY_HERE response and Tran state back at the TI
0255:                    responseEvent = eventCollector
0256:                            .extractCollectedResponseEvent();
0257:                    assertNotNull(
0258:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0259:                            responseEvent);
0260:                    assertNotNull(
0261:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0262:                            responseEvent.getResponse());
0263:                    assertSame(
0264:                            "The BUSY_HERE response was not associated with the right transaction",
0265:                            tran, responseEvent.getClientTransaction());
0266:                    assertEquals(
0267:                            "A response different from BUSY_HERE was passed to the TU",
0268:                            Response.BUSY_HERE, responseEvent.getResponse()
0269:                                    .getStatusCode());
0270:                    assertEquals(
0271:                            "The ClientTransaction did not pass in the COMPLETED state after "
0272:                                    + "receiving 300-699 final response", tran
0273:                                    .getState(), TransactionState.COMPLETED);
0274:                    // check whether the ackCollector has caught any fish
0275:                    RequestEvent ackReceivedEvent = ackCollector
0276:                            .extractCollectedRequestEvent();
0277:
0278:                    // JvB: With auto-dialog-support enabled, the ACK should be filtered
0279:                    // by the RI
0280:                    assertNotNull("The TI did not send an ACK request",
0281:                            ackReceivedEvent);
0282:                    assertNotNull("The TI did not send an ACK request",
0283:                            ackReceivedEvent.getRequest());
0284:                    assertEquals(Request.ACK, ackReceivedEvent.getRequest()
0285:                            .getMethod());
0286:
0287:                    // Try to kill remaining ACK retransmissions
0288:                    // TODO this may not always work .. should give it a specific
0289:                    // timeout value
0290:                    waitForMessage();
0291:                    // Now let's retransmit the final response. This time it shouldn't
0292:                    // be
0293:                    // passed to the TU but an ACK should still be sent
0294:                    try {
0295:                        eventCollector.collectResponseEvent(tiSipProvider);
0296:                    } catch (TooManyListenersException ex) {
0297:                        throw new TiUnexpectedError(
0298:                                "Failed to register a SipListener with TI", ex);
0299:                    }
0300:                    // go fish the ack
0301:                    try {
0302:                        ackCollector.collectRequestEvent(riSipProvider);
0303:                    } catch (TooManyListenersException ex) {
0304:                        throw new TckInternalError(
0305:                                "Failed to regiest a SipListener with an RI SipProvider",
0306:                                ex);
0307:                    }
0308:                    try {
0309:                        riSipProvider.sendResponse((Response) busyHere.clone());
0310:                    } catch (Throwable ex) {
0311:                        throw new TckInternalError(
0312:                                "The TCK could not send a BUSY HERE response back to the TI",
0313:                                ex);
0314:                    }
0315:                    waitForMessage();
0316:                    // The TU shouldn't see the retransmitted BUSY_HERE response
0317:                    responseEvent = eventCollector
0318:                            .extractCollectedResponseEvent();
0319:                    assertNull(
0320:                            "The Tested Implementation passed a retransmitted 300-699 response "
0321:                                    + "to the TU instead of just silently acknowledging it!",
0322:                            responseEvent);
0323:                    // We must still be in the completed state.
0324:                    assertEquals(
0325:                            "The ClientTransaction did not stay long enough in the COMPLETED "
0326:                                    + "state.", tran.getState(),
0327:                            TransactionState.COMPLETED);
0328:                    // check whether the ackCollector has caught any fish
0329:                    ackReceivedEvent = ackCollector
0330:                            .extractCollectedRequestEvent();
0331:                    assertNotNull(
0332:                            "The TI did not send an ACK request to the second response",
0333:                            ackReceivedEvent);
0334:                    assertNotNull(
0335:                            "The TI did not send an ACK request to the second response",
0336:                            ackReceivedEvent.getRequest());
0337:                    assertEquals(Request.ACK, ackReceivedEvent.getRequest()
0338:                            .getMethod());
0339:                } catch (Throwable exc) {
0340:                    exc.printStackTrace();
0341:                    fail(exc.getClass().getName() + ": " + exc.getMessage());
0342:                }
0343:                assertTrue(new Exception().getStackTrace()[0].toString(), true);
0344:
0345:                // Unfortunately we can't assert the TERMINATED state as TIMER_K TIMER_D
0346:                // is not exported by JAIN SIP
0347:
0348:            }
0349:
0350:            /**
0351:             * JvB: Tests transmission of an INVITE followed by CANCELlation of that
0352:             * request
0353:             *  -> INVITE <- 100 -> CANCEL <- OK <- 487 -> ACK
0354:             */
0355:            public void testInviteCancel() {
0356:                doCancelTest(true);
0357:            }
0358:
0359:            /**
0360:             * Same as above, but for non-RFC3261 client (i.e. no Via branch, no from/to
0361:             * tags
0362:             * 
0363:             * Cannot do this on 1.2 stack
0364:             * 
0365:             * public void testInviteCancelNonRFC3261() { doCancelTest(false); }
0366:             */
0367:
0368:            /**
0369:             * JvB: Tests transmission of an INVITE followed by CANCELlation of that
0370:             * request
0371:             *  -> INVITE <- 100 -> CANCEL <- OK <- 487 -> ACK
0372:             * 
0373:             * Note: for 1.2 it is impossible to manually set the top via branch to
0374:             * something not RFC3261-compliant
0375:             */
0376:            private void doCancelTest(boolean rfc3261Compliant) {
0377:                try {
0378:                    Request invite = createTiInviteRequest(null, null, null);
0379:                    ClientTransaction tran = null;
0380:                    try {
0381:                        eventCollector.collectRequestEvent(riSipProvider);
0382:
0383:                        // This call overwrites any branch we set
0384:                        tran = tiSipProvider.getNewClientTransaction(invite);
0385:
0386:                        // And this call too
0387:                        tran.sendRequest();
0388:                    } catch (SipException ex) {
0389:                        throw new TiUnexpectedError(
0390:                                "A SipExceptionOccurred while trying to send request!",
0391:                                ex);
0392:                    } catch (TooManyListenersException ex) {
0393:                        throw new TckInternalError(
0394:                                "Failed to regiest a SipListener with an RI SipProvider",
0395:                                ex);
0396:                    }
0397:                    waitForMessage();
0398:                    RequestEvent inviteReceivedEvent = eventCollector
0399:                            .extractCollectedRequestEvent();
0400:
0401:                    if (inviteReceivedEvent == null
0402:                            || inviteReceivedEvent.getRequest() == null)
0403:                        throw new TiUnexpectedError(
0404:                                "The invite request was not received by the RI!");
0405:
0406:                    // At this point the ClientTransaction should be CALLING!
0407:                    assertEquals(TransactionState.CALLING, tran.getState());
0408:
0409:                    // Send a TRYING response
0410:                    try {
0411:                        eventCollector.collectResponseEvent(tiSipProvider);
0412:                    } catch (TooManyListenersException ex) {
0413:                        throw new TiUnexpectedError(
0414:                                "Failed to register a SipListener with TI", ex);
0415:                    }
0416:                    try {
0417:                        Response resp = riMessageFactory.createResponse(
0418:                                Response.TRYING, inviteReceivedEvent
0419:                                        .getRequest());
0420:                        addStatus(inviteReceivedEvent.getRequest(), resp);
0421:                        riSipProvider.sendResponse(resp);
0422:                    } catch (Throwable ex) {
0423:                        throw new TckInternalError(
0424:                                "The TCK could not send a trying response back to the TI",
0425:                                ex);
0426:                    }
0427:
0428:                    waitForMessage();
0429:                    // Analyze the TRYING response and Tran state back at the TI
0430:                    ResponseEvent responseEvent = eventCollector
0431:                            .extractCollectedResponseEvent();
0432:                    assertNotNull(
0433:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0434:                            responseEvent);
0435:                    assertNotNull(
0436:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0437:                            responseEvent.getResponse());
0438:                    assertTrue(
0439:                            "A response different from TYING was passed to the TU!",
0440:                            responseEvent.getResponse().getStatusCode() == Response.TRYING);
0441:                    assertSame(
0442:                            "The TRYING response was not associated with the right transaction.",
0443:                            tran, responseEvent.getClientTransaction());
0444:                    // verify the the tran state is now PROCEEDING
0445:                    assertEquals(
0446:                            "The ClientTransaction did not pass in the PROCEEDING state after "
0447:                                    + "receiving 1xx provisional response",
0448:                            tran.getState(), TransactionState.PROCEEDING);
0449:
0450:                    // Send a CANCEL from the TI
0451:                    Request tiCancel = tran.createCancel();
0452:
0453:                    /*
0454:                     * this works, but since we cannot patch the INVITE the test fails
0455:                     * if (!rfc3261Compliant) { ((ViaHeader)
0456:                     * tiCancel.getHeader("Via")).setBranch( "xxx" ); // Not allowed by
0457:                     * RI // ((FromHeader) tiCancel.getHeader("From")).setTag( "" ); }
0458:                     */
0459:
0460:                    ClientTransaction tiCancelTrans;
0461:                    try {
0462:                        eventCollector.collectRequestEvent(riSipProvider);
0463:                        tiCancelTrans = tiSipProvider
0464:                                .getNewClientTransaction(tiCancel);
0465:                        tiCancelTrans.sendRequest();
0466:                    } catch (SipException ex) {
0467:                        throw new TiUnexpectedError(
0468:                                "A SipExceptionOccurred while trying to send CANCEL!",
0469:                                ex);
0470:                    }
0471:                    waitForMessage();
0472:                    RequestEvent cancelReceivedEvent = eventCollector
0473:                            .extractCollectedRequestEvent();
0474:                    if (cancelReceivedEvent == null
0475:                            || cancelReceivedEvent.getRequest() == null)
0476:                        throw new TiUnexpectedError(
0477:                                "The CANCEL request was not received by the RI!");
0478:
0479:                    // Send 200 OK to the CANCEL
0480:                    try {
0481:                        eventCollector.collectResponseEvent(tiSipProvider);
0482:                    } catch (TooManyListenersException ex) {
0483:                        throw new TiUnexpectedError(
0484:                                "Failed to register a SipListener with TI", ex);
0485:                    }
0486:                    Response riCancelOk = null;
0487:                    try {
0488:                        riCancelOk = riMessageFactory.createResponse(
0489:                                Response.OK, cancelReceivedEvent.getRequest());
0490:                        addStatus(cancelReceivedEvent.getRequest(), riCancelOk);
0491:                        riSipProvider.sendResponse(riCancelOk);
0492:                    } catch (Throwable ex) {
0493:                        throw new TckInternalError(
0494:                                "The TCK could not send a CANCEL OK response back to the TI",
0495:                                ex);
0496:                    }
0497:                    waitForMessage();
0498:
0499:                    // Analyze the OK response and Tran state back at the TI
0500:                    responseEvent = eventCollector
0501:                            .extractCollectedResponseEvent();
0502:                    if (responseEvent == null
0503:                            || responseEvent.getResponse() == null) {
0504:                        throw new TiUnexpectedError(
0505:                                "The CANCEL OK response was not received by the TI!");
0506:                    }
0507:
0508:                    // Send 487 to the INVITE, expect ACK
0509:                    try {
0510:                        eventCollector.collectResponseEvent(tiSipProvider);
0511:                    } catch (TooManyListenersException ex) {
0512:                        throw new TiUnexpectedError(
0513:                                "Failed to register a SipListener with TI", ex);
0514:                    }
0515:                    SipEventCollector ackCollector = new SipEventCollector();
0516:                    try {
0517:                        ackCollector.collectRequestEvent(riSipProvider);
0518:                    } catch (TooManyListenersException ex) {
0519:                        throw new TckInternalError(
0520:                                "Failed to regiest a SipListener with an RI SipProvider",
0521:                                ex);
0522:                    }
0523:
0524:                    Response riInviteTerminated = null;
0525:                    try {
0526:                        riInviteTerminated = riMessageFactory.createResponse(
0527:                                Response.REQUEST_TERMINATED,
0528:                                inviteReceivedEvent.getRequest());
0529:                        addStatus(inviteReceivedEvent.getRequest(),
0530:                                riInviteTerminated);
0531:                        riSipProvider.sendResponse(riInviteTerminated);
0532:                    } catch (Throwable ex) {
0533:                        throw new TckInternalError(
0534:                                "The TCK could not send a INVITE 487 response back to the TI",
0535:                                ex);
0536:                    }
0537:                    waitForMessage();
0538:
0539:                    // Analyze the REQUEST_TERMINATED response and Tran state back at
0540:                    // the TI
0541:                    responseEvent = eventCollector
0542:                            .extractCollectedResponseEvent();
0543:                    assertNotNull(
0544:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0545:                            responseEvent);
0546:                    assertNotNull(
0547:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0548:                            responseEvent.getResponse());
0549:                    assertSame(
0550:                            "The 487 response was not associated with the right transaction",
0551:                            tran, responseEvent.getClientTransaction());
0552:                    assertEquals(
0553:                            "A response different from 487 was passed to the TU",
0554:                            Response.REQUEST_TERMINATED, responseEvent
0555:                                    .getResponse().getStatusCode());
0556:                    assertEquals(
0557:                            "The ClientTransaction did not pass in the COMPLETED state after "
0558:                                    + "receiving 300-699 final response", tran
0559:                                    .getState(), TransactionState.COMPLETED);
0560:                    // check whether the ackCollector has caught any fish
0561:                    RequestEvent ackReceivedEvent = ackCollector
0562:                            .extractCollectedRequestEvent();
0563:                    assertNotNull("The TI did not send an ACK request event",
0564:                            ackReceivedEvent);
0565:                    assertNotNull("The TI did not send an ACK request",
0566:                            ackReceivedEvent.getRequest());
0567:                    assertEquals(Request.ACK, ackReceivedEvent.getRequest()
0568:                            .getMethod());
0569:
0570:                    // Try to kill remaining ACK retransmissions?
0571:                } catch (Throwable exc) {
0572:                    exc.printStackTrace();
0573:                    fail(exc.getClass().getName() + ": " + exc.getMessage());
0574:                }
0575:                assertTrue(new Exception().getStackTrace()[0].toString(), true);
0576:
0577:                // Unfortunately we can't assert the TERMINATED state as TIMER_K TIMER_D
0578:                // is not exported by JAIN SIP
0579:            }
0580:
0581:            /**
0582:             * Tries to steer a TI client transaction through the following scenario
0583:             * Calling-->Completed-->Terminated. Apart from state transitions, we also
0584:             * test, retransmissions and proper hiding/passing of messages to the TU.
0585:             */
0586:            public void testCallingCompletedTerminatedScenario() {
0587:                try {
0588:                    Request invite = createTiInviteRequest(null, null, null);
0589:
0590:                    // JvB: test
0591:                    // ((MessageExt) invite).getFirstViaHeader().setParameter( "rport",
0592:                    // null );
0593:
0594:                    ClientTransaction tran = null;
0595:                    try {
0596:                        eventCollector.collectRequestEvent(riSipProvider);
0597:                        tran = tiSipProvider.getNewClientTransaction(invite);
0598:                        tran.sendRequest();
0599:                    } catch (SipException ex) {
0600:                        throw new TiUnexpectedError(
0601:                                "A SipExceptionOccurred while trying to send request!",
0602:                                ex);
0603:                    } catch (TooManyListenersException ex) {
0604:                        throw new TckInternalError(
0605:                                "Failed to regiest a SipListener with an RI SipProvider",
0606:                                ex);
0607:                    }
0608:                    waitForMessage();
0609:                    RequestEvent inviteReceivedEvent = eventCollector
0610:                            .extractCollectedRequestEvent();
0611:                    if (inviteReceivedEvent == null
0612:                            || inviteReceivedEvent.getRequest() == null)
0613:                        throw new TiUnexpectedError(
0614:                                "The invite request was not received by the RI!");
0615:                    // At this point the ClientTransaction should be CALLING!
0616:                    assertEquals(TransactionState.CALLING, tran.getState());
0617:                    // Check Request retransmission
0618:                    try {
0619:                        eventCollector.collectRequestEvent(riSipProvider);
0620:                    } catch (TooManyListenersException ex) {
0621:                        throw new TckInternalError(
0622:                                "Failed to regiest a SipListener with an RI SipProvider",
0623:                                ex);
0624:                    }
0625:                    // Wait for the retransmission timer to fire if it had not already
0626:                    // done so.
0627:                    if (tran.getRetransmitTimer() > MESSAGES_ARRIVE_FOR)
0628:                        sleep((long) tran.getRetransmitTimer()
0629:                                - MESSAGES_ARRIVE_FOR); // subtract
0630:                    // the
0631:                    // time
0632:                    // we
0633:                    // waited
0634:                    // for
0635:                    // the
0636:                    // invite
0637:                    // Wait for the retransmitted request to arrive
0638:                    waitForMessage();
0639:                    inviteReceivedEvent = eventCollector
0640:                            .extractCollectedRequestEvent();
0641:                    assertNotNull("The invite request was not retransmitted!",
0642:                            inviteReceivedEvent);
0643:                    assertNotNull("The invite request was not retransmitted!",
0644:                            inviteReceivedEvent.getRequest());
0645:                    assertEquals(Request.INVITE, inviteReceivedEvent
0646:                            .getRequest().getMethod());
0647:                    // At this point the ClientTransaction should STILL be CALLING!
0648:                    assertEquals(TransactionState.CALLING, tran.getState());
0649:                    // Send a 486 BUSY HERE (final) response from the RI
0650:                    try {
0651:                        eventCollector.collectResponseEvent(tiSipProvider);
0652:                    } catch (TooManyListenersException ex) {
0653:                        throw new TiUnexpectedError(
0654:                                "Failed to register a SipListener with TI", ex);
0655:                    }
0656:                    // The BUSY_HERE response should trigger some ACKs so let's register
0657:                    // a listener with the RI
0658:                    SipEventCollector ackCollector = new SipEventCollector();
0659:                    try {
0660:                        ackCollector.collectRequestEvent(riSipProvider);
0661:                    } catch (TooManyListenersException ex) {
0662:                        throw new TckInternalError(
0663:                                "Failed to regiest a SipListener with an RI SipProvider",
0664:                                ex);
0665:                    }
0666:                    Response busyHere = null;
0667:                    try {
0668:                        busyHere = riMessageFactory.createResponse(
0669:                                Response.BUSY_HERE, inviteReceivedEvent
0670:                                        .getRequest());
0671:                        addStatus(inviteReceivedEvent.getRequest(), busyHere);
0672:
0673:                        // JvB: set to-tag, check it against the ACK generated
0674:                        ((ToHeader) busyHere.getHeader("to"))
0675:                                .setTag("ack-to-test");
0676:
0677:                        riSipProvider.sendResponse((Response) busyHere.clone());
0678:                    } catch (Throwable ex) {
0679:                        throw new TckInternalError(
0680:                                "The TCK could not send a BUSY HERE response back to the TI",
0681:                                ex);
0682:                    }
0683:                    waitForMessage();
0684:                    // Analyze the BUSY_HERE response and Tran state back at the TI
0685:                    ResponseEvent responseEvent = eventCollector
0686:                            .extractCollectedResponseEvent();
0687:                    assertNotNull(
0688:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0689:                            responseEvent);
0690:                    assertNotNull(
0691:                            "The Tested Implementation did not pass a 300-699 response to the TU!",
0692:                            responseEvent.getResponse());
0693:                    assertSame(
0694:                            "The BUSY_HERE response was not associated with the right transaction",
0695:                            tran, responseEvent.getClientTransaction());
0696:                    assertSame(
0697:                            "A response different from BUSY_HERE was passed to the TU",
0698:                            tran, responseEvent.getClientTransaction());
0699:                    assertEquals(
0700:                            "The ClientTransaction did not pass in the COMPLETED state after "
0701:                                    + "receiving 300-699 final response", tran
0702:                                    .getState(), TransactionState.COMPLETED);
0703:                    // check whether the ackCollector has caught any fish
0704:                    RequestEvent ackReceivedEvent = ackCollector
0705:                            .extractCollectedRequestEvent();
0706:                    assertNotNull("The TI did not send an ACK request",
0707:                            ackReceivedEvent);
0708:                    assertNotNull("The TI did not send an ACK request",
0709:                            ackReceivedEvent.getRequest());
0710:                    assertEquals(Request.ACK, ackReceivedEvent.getRequest()
0711:                            .getMethod());
0712:                    // Try to kill remaining ACK retransmissions
0713:                    // TODO this may not always work .. should give it a specific
0714:                    // timeout value
0715:                    waitForMessage();
0716:                    // Now let's retransmit the final response. This time it shouldn't
0717:                    // be
0718:                    // passed to the TU but an ACK should still be sent
0719:                    try {
0720:                        eventCollector.collectResponseEvent(tiSipProvider);
0721:                    } catch (TooManyListenersException ex) {
0722:                        throw new TiUnexpectedError(
0723:                                "Failed to register a SipListener with TI", ex);
0724:                    }
0725:                    // go fish the ack
0726:                    try {
0727:                        ackCollector.collectRequestEvent(riSipProvider);
0728:                    } catch (TooManyListenersException ex) {
0729:                        throw new TckInternalError(
0730:                                "Failed to regiest a SipListener with an RI SipProvider",
0731:                                ex);
0732:                    }
0733:                    try {
0734:                        riSipProvider.sendResponse((Response) busyHere.clone());
0735:                    } catch (Throwable ex) {
0736:                        throw new TckInternalError(
0737:                                "The TCK could not send a BUSY HERE response back to the TI",
0738:                                ex);
0739:                    }
0740:                    waitForMessage();
0741:                    // The TU shouldn't see the retransmitted BUSY_HERE response
0742:                    responseEvent = eventCollector
0743:                            .extractCollectedResponseEvent();
0744:                    assertNull(
0745:                            "The Tested Implementation passed a retransmitted 300-699 response "
0746:                                    + "to the TU instead of just silently acknowledging it!",
0747:                            responseEvent);
0748:                    // We must still be in the completed state.
0749:                    assertEquals(
0750:                            "The ClientTransaction did not stay long enough in the COMPLETED "
0751:                                    + "state.", tran.getState(),
0752:                            TransactionState.COMPLETED);
0753:                    // check whether the ackCollector has caught any fish
0754:                    ackReceivedEvent = ackCollector
0755:                            .extractCollectedRequestEvent();
0756:                    assertNotNull(
0757:                            "The TI did not send an ACK request to the second response",
0758:                            ackReceivedEvent);
0759:                    assertNotNull(
0760:                            "The TI did not send an ACK request to the second response",
0761:                            ackReceivedEvent.getRequest());
0762:
0763:                    assertEquals(Request.ACK, ackReceivedEvent.getRequest()
0764:                            .getMethod());
0765:
0766:                    // JvB: verify to tag
0767:                    assertEquals(
0768:                            "The To header field in the ACK MUST equal the To header field "
0769:                                    + " in the response being acknowledged",
0770:                            "ack-to-test", ((ToHeader) ackReceivedEvent
0771:                                    .getRequest().getHeader("to")).getTag());
0772:                } catch (Throwable exc) {
0773:                    exc.printStackTrace();
0774:                    fail(exc.getClass().getName() + ": " + exc.getMessage());
0775:                }
0776:                assertTrue(new Exception().getStackTrace()[0].toString(), true);
0777:
0778:                // Unfortunately we can't assert the TERMINATED state as TIMER_D
0779:                // is not exported by JAIN SIP
0780:
0781:            }
0782:
0783:            /**
0784:             * Tries to steer a TI client transaction through the following scenario
0785:             * Calling-->Proceeding-->Terminated. Apart from state transitions, we also
0786:             * test, retransmissions and proper hiding/passing of messages to the TU.
0787:             */
0788:            public void testCallingProceedingTerminatedScenario() {
0789:                try {
0790:                    Request invite = createTiInviteRequest(null, null, null);
0791:                    ClientTransaction tran = null;
0792:                    try {
0793:                        eventCollector.collectRequestEvent(riSipProvider);
0794:                        tran = tiSipProvider.getNewClientTransaction(invite);
0795:                        tran.sendRequest();
0796:                    } catch (SipException ex) {
0797:                        throw new TiUnexpectedError(
0798:                                "A SipExceptionOccurred while trying to send request!",
0799:                                ex);
0800:                    } catch (TooManyListenersException ex) {
0801:                        throw new TckInternalError(
0802:                                "Failed to regiest a SipListener with an RI SipProvider",
0803:                                ex);
0804:                    }
0805:                    waitForMessage();
0806:                    RequestEvent inviteReceivedEvent = eventCollector
0807:                            .extractCollectedRequestEvent();
0808:                    if (inviteReceivedEvent == null
0809:                            || inviteReceivedEvent.getRequest() == null)
0810:                        throw new TiUnexpectedError(
0811:                                "The invite request was not received by the RI!");
0812:                    // At this point the ClientTransaction should be CALLING!
0813:                    assertEquals(TransactionState.CALLING, tran.getState());
0814:                    // Check Request retransmission
0815:                    try {
0816:                        eventCollector.collectRequestEvent(riSipProvider);
0817:                    } catch (TooManyListenersException ex) {
0818:                        throw new TckInternalError(
0819:                                "Failed to regiest a SipListener with an RI SipProvider",
0820:                                ex);
0821:                    }
0822:                    // Wait for the retransmission timer to fire if it had not already
0823:                    // done so.
0824:                    if (tran.getRetransmitTimer() > MESSAGES_ARRIVE_FOR)
0825:                        sleep((long) tran.getRetransmitTimer()
0826:                                - MESSAGES_ARRIVE_FOR); // subtract
0827:                    // the
0828:                    // time
0829:                    // we
0830:                    // waited
0831:                    // for
0832:                    // the
0833:                    // invite
0834:                    // Wait for the retransmitted request to arrive
0835:                    waitForMessage();
0836:                    inviteReceivedEvent = eventCollector
0837:                            .extractCollectedRequestEvent();
0838:                    assertNotNull("The invite request was not retransmitted!",
0839:                            inviteReceivedEvent);
0840:                    assertNotNull("The invite request was not retransmitted!",
0841:                            inviteReceivedEvent.getRequest());
0842:                    assertEquals(Request.INVITE, inviteReceivedEvent
0843:                            .getRequest().getMethod());
0844:                    // At this point the ClientTransaction should STILL be CALLING!
0845:                    assertEquals(TransactionState.CALLING, tran.getState());
0846:                    // Send a TRYING response
0847:                    try {
0848:                        eventCollector.collectResponseEvent(tiSipProvider);
0849:                    } catch (TooManyListenersException ex) {
0850:                        throw new TiUnexpectedError(
0851:                                "Failed to register a SipListener with TI", ex);
0852:                    }
0853:                    try {
0854:                        Response resp = riMessageFactory.createResponse(
0855:                                Response.TRYING, inviteReceivedEvent
0856:                                        .getRequest());
0857:                        addStatus(inviteReceivedEvent.getRequest(), resp);
0858:                        riSipProvider.sendResponse(resp);
0859:                    } catch (Throwable ex) {
0860:                        throw new TckInternalError(
0861:                                "The TCK could not send a trying response back to the TI",
0862:                                ex);
0863:                    }
0864:                    waitForMessage();
0865:                    // Analyze the TRYING response and Tran state back at the TI
0866:                    ResponseEvent responseEvent = eventCollector
0867:                            .extractCollectedResponseEvent();
0868:                    assertNotNull(
0869:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0870:                            responseEvent);
0871:                    assertNotNull(
0872:                            "The Tested Implementation did not pass a 1xx response to the TU!",
0873:                            responseEvent.getResponse());
0874:                    assertTrue(
0875:                            "A response different from TYING was passed to the TU!",
0876:                            responseEvent.getResponse().getStatusCode() == Response.TRYING);
0877:                    assertSame(
0878:                            "The TRYING response was not associated with the right transaction",
0879:                            tran, responseEvent.getClientTransaction());
0880:                    // verify the the tran state is now PROCEEDING
0881:                    assertEquals(
0882:                            "The ClientTransaction did not pass in the PROCEEDING state after "
0883:                                    + "receiving 1xx provisional response",
0884:                            tran.getState(), TransactionState.PROCEEDING);
0885:                    // Send a 200 OK (final) response from the RI
0886:                    try {
0887:                        eventCollector.collectResponseEvent(tiSipProvider);
0888:                    } catch (TooManyListenersException ex) {
0889:                        throw new TiUnexpectedError(
0890:                                "Failed to register a SipListener with TI", ex);
0891:                    }
0892:                    // The OK response shouldn't trigger any ACKs so let's register
0893:                    // a listener with the RI to verify whether that is the case
0894:                    SipEventCollector ackCollector = new SipEventCollector();
0895:                    try {
0896:                        ackCollector.collectRequestEvent(riSipProvider);
0897:                    } catch (TooManyListenersException ex) {
0898:                        throw new TckInternalError(
0899:                                "Failed to regiest a SipListener with an RI SipProvider",
0900:                                ex);
0901:                    }
0902:                    Response ok = null;
0903:                    try {
0904:                        ok = riMessageFactory.createResponse(Response.OK,
0905:                                inviteReceivedEvent.getRequest());
0906:
0907:                        // JvB: MUST add Contact too!
0908:                        ContactHeader contact = riHeaderFactory
0909:                                .createContactHeader(((ToHeader) ok
0910:                                        .getHeader("To")).getAddress());
0911:                        ok.addHeader(contact);
0912:                        // end JvB
0913:
0914:                        addStatus(inviteReceivedEvent.getRequest(), ok);
0915:                        riSipProvider.sendResponse((Response) ok.clone());
0916:                    } catch (Throwable ex) {
0917:                        throw new TckInternalError(
0918:                                "The TCK could not send an OK response back to the TI",
0919:                                ex);
0920:                    }
0921:                    waitForMessage();
0922:                    // Analyze the OK response and Tran state back at the TI
0923:                    responseEvent = eventCollector
0924:                            .extractCollectedResponseEvent();
0925:                    assertNotNull(
0926:                            "The Tested Implementation did not pass a 200 OK response to the TU!",
0927:                            responseEvent);
0928:                    assertNotNull(
0929:                            "The Tested Implementation did not pass a 200 OK response to the TU!",
0930:                            responseEvent.getResponse());
0931:                    assertSame(
0932:                            "The OK response was not associated with the right transaction",
0933:                            tran, responseEvent.getClientTransaction());
0934:                    assertSame(
0935:                            "A response different from OK was passed to the TU",
0936:                            tran, responseEvent.getClientTransaction());
0937:                    assertEquals(
0938:                            "The ClientTransaction did not pass in the TERMINATED state after "
0939:                                    + "receiving 200 final response", tran
0940:                                    .getState(), TransactionState.TERMINATED);
0941:                    // check whether the ackCollector has caught any fish
0942:                    RequestEvent ackReceivedEvent = ackCollector
0943:                            .extractCollectedRequestEvent();
0944:                    if (ackReceivedEvent != null)
0945:                        logger.error("Shouldn't have received that="
0946:                                + ackReceivedEvent.getRequest());
0947:                    assertNull(
0948:                            "The TI sent an ACK to an OK (this is TU's job)!",
0949:                            ackReceivedEvent);
0950:                    // Now let's retransmit the final response and see it is
0951:                    // passed to the TU (again no ACKs)
0952:                    try {
0953:                        eventCollector.collectResponseEvent(tiSipProvider);
0954:                    } catch (TooManyListenersException ex) {
0955:                        throw new TiUnexpectedError(
0956:                                "Failed to register a SipListener with TI", ex);
0957:                    }
0958:                    // go fish the ack
0959:                    try {
0960:                        ackCollector.collectRequestEvent(riSipProvider);
0961:                    } catch (TooManyListenersException ex) {
0962:                        throw new TckInternalError(
0963:                                "Failed to regiest a SipListener with an RI SipProvider",
0964:                                ex);
0965:                    }
0966:                    try {
0967:                        riSipProvider.sendResponse((Response) ok.clone());
0968:                    } catch (Throwable ex) {
0969:                        throw new TckInternalError(
0970:                                "The TCK could not send an OK response back to the TI",
0971:                                ex);
0972:                    }
0973:                    waitForMessage();
0974:                    // Did we get the 2nd OK?
0975:                    responseEvent = eventCollector
0976:                            .extractCollectedResponseEvent();
0977:
0978:                    /*
0979:                     * JvB: the stack should in fact ~not~ pass the retransmitted
0980:                     * response, but filter it out
0981:                     * 
0982:                     * assertNotNull( "The TI did not pass to the TU a retransmitted OK
0983:                     * response!", responseEvent); assertNotNull( "The TI did not pass
0984:                     * to the TU a retransmitted OK response!",
0985:                     * responseEvent.getResponse()); assertTrue( "The TI passed to the
0986:                     * TU a bad response!",
0987:                     * responseEvent.getResponse().getStatusCode()==Response.OK);
0988:                     */
0989:                    // TBD
0990:                    // assertNull( "The TI should filter the retransmitted OK response",
0991:                    // responseEvent );
0992:                    // We must still be in the terminated state.
0993:                    assertEquals(
0994:                            "The ClientTransaction mysteriously left the TERMINATED state!",
0995:                            tran.getState(), TransactionState.TERMINATED);
0996:                    // check whether the ackCollector has caught any fish
0997:                    ackReceivedEvent = ackCollector
0998:                            .extractCollectedRequestEvent();
0999:                    assertNull(
1000:                            "The TI sent an ACK request to the second OK response "
1001:                                    + "(OK acks are TU's responsibility)!",
1002:                            ackReceivedEvent);
1003:                } catch (Throwable exc) {
1004:                    exc.printStackTrace();
1005:                    fail(exc.getClass().getName() + ": " + exc.getMessage());
1006:                }
1007:                assertTrue(new Exception().getStackTrace()[0].toString(), true);
1008:            }
1009:
1010:            /**
1011:             * Tries to steer a TI client transaction through the following scenario
1012:             * Calling-->Terminated. Apart from state transitions, we also test,
1013:             * retransmissions and proper hiding/passing of messages to the TU.
1014:             */
1015:            public void testCallingTerminatedScenario() {
1016:                try {
1017:                    Request invite = createTiInviteRequest(null, null, null);
1018:                    ClientTransaction tran = null;
1019:                    try {
1020:                        eventCollector.collectRequestEvent(riSipProvider);
1021:                        tran = tiSipProvider.getNewClientTransaction(invite);
1022:                        tran.sendRequest();
1023:                    } catch (SipException ex) {
1024:                        throw new TiUnexpectedError(
1025:                                "A SipExceptionOccurred while trying to send request!",
1026:                                ex);
1027:                    } catch (TooManyListenersException ex) {
1028:                        throw new TckInternalError(
1029:                                "Failed to regiest a SipListener with an RI SipProvider",
1030:                                ex);
1031:                    }
1032:                    waitForMessage();
1033:                    RequestEvent inviteReceivedEvent = eventCollector
1034:                            .extractCollectedRequestEvent();
1035:                    if (inviteReceivedEvent == null
1036:                            || inviteReceivedEvent.getRequest() == null)
1037:                        throw new TiUnexpectedError(
1038:                                "The invite request was not received by the RI!");
1039:                    // At this point the ClientTransaction should be CALLING!
1040:                    assertEquals(TransactionState.CALLING, tran.getState());
1041:                    // Check Request retransmission
1042:                    try {
1043:                        eventCollector.collectRequestEvent(riSipProvider);
1044:                    } catch (TooManyListenersException ex) {
1045:                        throw new TckInternalError(
1046:                                "Failed to regiest a SipListener with an RI SipProvider",
1047:                                ex);
1048:                    }
1049:                    // Wait for the retransmission timer to fire if it had not already
1050:                    // done so.
1051:                    if (tran.getRetransmitTimer() > MESSAGES_ARRIVE_FOR)
1052:                        sleep((long) tran.getRetransmitTimer()
1053:                                - MESSAGES_ARRIVE_FOR); // subtract
1054:                    // the
1055:                    // time
1056:                    // we
1057:                    // waited
1058:                    // for
1059:                    // the
1060:                    // invite
1061:                    // Wait for the retransmitted request to arrive
1062:                    waitForMessage();
1063:                    inviteReceivedEvent = eventCollector
1064:                            .extractCollectedRequestEvent();
1065:                    assertNotNull("The invite request was not retransmitted!",
1066:                            inviteReceivedEvent);
1067:                    assertNotNull("The invite request was not retransmitted!",
1068:                            inviteReceivedEvent.getRequest());
1069:                    assertEquals(Request.INVITE, inviteReceivedEvent
1070:                            .getRequest().getMethod());
1071:                    // At this point the ClientTransaction should STILL be CALLING!
1072:                    assertEquals(TransactionState.CALLING, tran.getState());
1073:                    // Send a 200 OK (final) response from the RI
1074:                    try {
1075:                        eventCollector.collectResponseEvent(tiSipProvider);
1076:                    } catch (TooManyListenersException ex) {
1077:                        throw new TiUnexpectedError(
1078:                                "Failed to register a SipListener with TI", ex);
1079:                    }
1080:                    // The OK response shouldn't trigger any ACKs so let's register
1081:                    // a listener with the RI to verify whether that is the case
1082:                    SipEventCollector ackCollector = new SipEventCollector();
1083:                    try {
1084:                        ackCollector.collectRequestEvent(riSipProvider);
1085:                    } catch (TooManyListenersException ex) {
1086:                        throw new TckInternalError(
1087:                                "Failed to regiest a SipListener with an RI SipProvider",
1088:                                ex);
1089:                    }
1090:                    Response ok = null;
1091:                    try {
1092:                        ok = riMessageFactory.createResponse(Response.OK,
1093:                                inviteReceivedEvent.getRequest());
1094:                        addStatus(inviteReceivedEvent.getRequest(), ok);
1095:
1096:                        // JvB: MUST add Contact too!
1097:                        ContactHeader contact = riHeaderFactory
1098:                                .createContactHeader(((ToHeader) ok
1099:                                        .getHeader("To")).getAddress());
1100:                        ok.addHeader(contact);
1101:                        // end JvB
1102:
1103:                        riSipProvider.sendResponse(ok);
1104:                    } catch (Throwable ex) {
1105:                        throw new TckInternalError(
1106:                                "The TCK could not send an OK response back to the TI",
1107:                                ex);
1108:                    }
1109:                    waitForMessage();
1110:                    // Analyze the OK response and Tran state back at the TI
1111:                    ResponseEvent responseEvent = eventCollector
1112:                            .extractCollectedResponseEvent();
1113:                    assertNotNull(
1114:                            "The Tested Implementation did not pass a 200 OK response to the TU!",
1115:                            responseEvent);
1116:                    assertNotNull(
1117:                            "The Tested Implementation did not pass a 200 OK response to the TU!",
1118:                            responseEvent.getResponse());
1119:                    assertSame(
1120:                            "The OK response was not associated with the right transaction",
1121:                            tran, responseEvent.getClientTransaction());
1122:                    assertSame(
1123:                            "A response different from OK was passed to the TU",
1124:                            tran, responseEvent.getClientTransaction());
1125:                    assertEquals(
1126:                            "The ClientTransaction did not pass in the TERMINATED state after "
1127:                                    + "receiving 200 final response", tran
1128:                                    .getState(), TransactionState.TERMINATED);
1129:                    // check whether the ackCollector has caught any fish
1130:                    RequestEvent ackReceivedEvent = ackCollector
1131:                            .extractCollectedRequestEvent();
1132:                    assertNull(
1133:                            "The TI sent an ACK to an OK (this is TU's job)!",
1134:                            ackReceivedEvent);
1135:                    // Now let's retransmit the final response and see that it is
1136:                    // passed to the TU (again no ACKs should be sent by the TI)
1137:                    try {
1138:                        eventCollector.collectResponseEvent(tiSipProvider);
1139:                    } catch (TooManyListenersException ex) {
1140:                        throw new TiUnexpectedError(
1141:                                "Failed to register a SipListener with TI", ex);
1142:                    }
1143:                    // go fish the ack
1144:                    try {
1145:                        ackCollector.collectRequestEvent(riSipProvider);
1146:                    } catch (TooManyListenersException ex) {
1147:                        throw new TckInternalError(
1148:                                "Failed to regiest a SipListener with an RI SipProvider",
1149:                                ex);
1150:                    }
1151:                    try {
1152:                        riSipProvider.sendResponse((Response) ok.clone());
1153:                    } catch (Throwable ex) {
1154:                        throw new TckInternalError(
1155:                                "The TCK could not send an OK response back to the TI",
1156:                                ex);
1157:                    }
1158:                    waitForMessage();
1159:                    // Did we get the 2nd OK?
1160:                    responseEvent = eventCollector
1161:                            .extractCollectedResponseEvent();
1162:                    /*
1163:                     * JvB: see previous comment
1164:                     * 
1165:                     * assertNotNull( "The TI did not pass to the TU a retransmitted OK
1166:                     * response!", responseEvent); assertNotNull( "The TI did not pass
1167:                     * to the TU a retransmitted OK response!",
1168:                     * responseEvent.getResponse()); assertTrue( "The TI passed to the
1169:                     * TU a bad response!",
1170:                     * responseEvent.getResponse().getStatusCode()==Response.OK);
1171:                     */
1172:                    // JvB: TBD
1173:                    // assertNull( "The TI should filter the retransmitted OK response",
1174:                    // responseEvent );
1175:                    // We must still be in the terminated state.
1176:                    assertEquals(
1177:                            "The ClientTransaction mysteriously left the TERMINATED state!",
1178:                            tran.getState(), TransactionState.TERMINATED);
1179:                    // check whether the ackCollector has caught any fish
1180:                    ackReceivedEvent = ackCollector
1181:                            .extractCollectedRequestEvent();
1182:                    assertNull(
1183:                            "The TI sent an ACK request to the second OK response "
1184:                                    + "(OK acks are TU's responsibility)!",
1185:                            ackReceivedEvent);
1186:                } catch (Throwable exc) {
1187:                    exc.printStackTrace();
1188:                    fail(exc.getClass().getName() + ": " + exc.getMessage());
1189:                }
1190:                assertTrue(new Exception().getStackTrace()[0].toString(), true);
1191:            }
1192:
1193:            // ==================== end of tests
1194:
1195:            // ====== STATIC JUNIT ==========
1196:            public static Test suite() {
1197:                return new TestSuite(
1198:                        InviteClientTransactionsStateMachineTest.class);
1199:            }
1200:
1201:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.