A Free JAVA JNDI naming service provider and MOM system over SSL secured sockets.

 
Home Page   Technical Playground

Help & Tutorial

cyJNDI Copyright 2000 by Erica Andrews a.k.a. Li'L CJ.
cyJMS Copyright 2000 by Erica Andrews
JNDIce Copyright 2000 by Erica Andrews
CJ's MailerBean Copyright 2000 by Erica Andrews
All rights reserved.
cylikon@hotmail.com
More Of My FREE Java Software
 

What Is cyJNDI-cyJMS?Distribution Contents | Installation | Running Setup | Running The Server | Running The Terminal ApplicationGetting An InitialContext  |  Where Is My TopicConnectionFactory? | Where Is My QueueConnectionFactory? | Working With Topics | Working With Queues | Administering Topics And Queues | Hosts And Ports | JMSX Supported Properties | URL Support | JMSType Rules | Class List | ExtrasA MUST READ: SSL Warnings | Notes On SSL-enabled servers | Notes On SSL-disabled servers | Working WIth The cyJNDI Remote Terminal | cyJNDI Terminal Commands | System Requirements | Package Contents | Features | Limitations | Bugs | Screen-shots | DOWNLOAD | Testing | Bug ReportsComing Soon... | LICENSE | DISCLAIMER |


Contents Of This Distribution (version 1.0 beta):

cyJNDIcyJMS_Server.jar (298 KB) - This is the .jar archive needed to run the application server.

cyClients.jar (107 KB) -  This .jar contains ALL the classes any of your clients would need to use cyJNDI and cyJMS services.  These are the classes which should be put in the CLASSPATH of any cyJNDI-cyJMS clients you are using.  The archive is relatively small and can be easily transported on floppy disk to any computer/server for your clients as needed.

cyTerminal.jar (15 KB)  - This is the stand-alone terminal application you can use to access your cyJNDI server.  It supports both SSL and non-SSL terminal connections.  Since I don't know of any telnet applications which support SSL, I created one for use with cyJNDI.  If your server is not running in SSL mode, you can  use an ordinary telnet client to connect to your cyJNDI server. Otherwise, it is suggested that you use the SSL-enabled telnet client provided for you.  If you plan to access cyJNDI-cyJMS remotely, it is suggested that you place this application on a floppy disk and take it to your remote location, giving you easy access to your SSL-enabled server.

cySetup.jar (15 KB) - This is the setup program for configuring your cyJNDI-cyJMS server environment

Miscellaneous: Documentation, images, and 3 icons.



Installation:
With cyJNDI-cyJMS, there is really nothing to install, other than supplementary packages you need to download from Sun's site.
Please check the System Requirements section for information on what Sun packages you need, how to install JSSE, and how to find and choose and SSL security provider.  I recommending using Sun's free SSL security provider, which comes bundled with the JSSE, but any standard SSL provider should work just fine.  Afterwards, just unzip your cyJNDI-cyJMS installation to your preferred directory.
 

If you are using Sun's JDK 1.3 (I don't know about 1.2.  I don't use it), you should be able to drop the supplementary Sun  .jar files into your  <java.home>\lib\ext  directory as a quick way to get them into your classpath.

Run Setup: double click the cySetup.jar file to configure your server to your liking.

If you need to run Setup from a command line:  type    javaw -jar cySetup.jar      or   java -jar cySetup.jar    or java -classpath C:\myDirectory\cySetup.jar cySetup

 If you wish to disable/enable SSL, set any passwords, garbage collection, setup a mail host, etc. you may do so here.


Running Setup:
Run Setup: double click the cySetup.jar file to configure your server to your liking.

If you need to run Setup from a command line:  type    javaw -jar cySetup.jar      or   java -jar cySetup.jar    or java -classpath C:\myDirectory\cySetup.jar cySetup

 If you wish to disable/enable SSL, set any passwords, garbage collection, setup a mail host, etc. you may do so here.


Running The cyJNDI-cyJMS Application Server:
Run The Server: double click the cyJNDcyJMS_Server.jar file to run the application server.

If you need to run the server  from a command line:  type    javaw -jar cyJNDIcyJMS_Server.jar      or   java -jar cyJNDIcyJMS_Server.jar    or    java -classpath C:\myDirectory\cyJNDIcyJMS_Server.jar cyJNDIServer

Server startup up should be fairly quick, especially if SSL is disabled.  If SSL is enabled, expect startup to take a couple extra minutes, while your system's cipher suites (encryption algorithms and handshaking abilites) are loaded for client interaction.


Running The Terminal Application:
Running The Terminal Inside  the Application Server (Local): click the "cyJNDI Terminal" tab.

Running The Terminal Outside the Application Server (Remotely): double click the cyTerminal.jar file to run the application.
If you need to run the terminal  from a command line:  type    javaw -jar cyTerminal.jar     or     java -jar cyTerminal.jar    or    java -classpath C:\myDirectory\cyTerminal.jar cyTerminal

After the terminal application has started, simply click "Setup" to choose a host and port to connect to.  IMPORTANT: If the cyJNDI server you are connecting to is NOT using SSL, make sure the "Use SSL Sockets" button is not checked. If the cyJNDI server you are connecting to IS using SSL, leave the "Use SSL Sockets" field checked.  It is VERY important that this field is properly checked or unchecked, since incompatible security protocols on either the server or client side can cause your connection (and your application) to freeze and/or crash. After you have successfully connected to a remote cyJNDI server, you may send commands to the terminal by typing them in the textfield and then clicking the "Send" button.
When asked for your ROLE, type 'ADMIN', then login with your username and password.  You can get a list of commands at the terminal by typing 'HELP'.


Getting An Initial Context:
WITH SSL Secure Sockets ENABLED:

If the cyJNDI server you are connecting to DOES use SSL, you can simply do the following:

Properties p=new Properties();

   /*  provide the name of the Context Factory  */
p.put(Context.INITIAL_CONTEXT_FACTORY,"cylikon.cyJNDI.cyInitialContextFactory");

  /*  put your CLIENT username into the Properties */
p.put(Context.SECURITY_PRINCIPAL,"myUsername");

  /* put your CLIENT password into the Properties */
p.put(Context.SECURITY_CREDENTIALS,"myPassword");

InitialContext ic=new InitialContext(p);
Object o= ic.lookup("YadaYada");

The rest is just straight JNDI, so you can consult your JNDI documentation for all the specific JNDI methods to call. By default, the InitialContext is setup to use SSL sockets, so you don't need to do anything special if you DO wish for you Context to use SSL.  Please note that InitialContexts that use SSL will take slightly longer to connect than those that don't.  The delay is due to the standard SSL "handshake".  However, the safety and privacy alotted is WELL worth it.

NOTE:  If you need to connect to some other host besides "localhost" or some other port besides the default (21472), click here for information on URL Support.

Programming Tip:
If you find that you will be switching between SSL-enabled mode and SSL-disabled mode frequently, it may be smarter to specify your InitialContext properties in a jndi.properties file and simply call "new InitialContext()".  Using a jndi.properties file (usually stored in your java.home directory) will save you from having to re-compile your applications every time you change your cyJNDI-cyJMS server's settings. Instead, you can make adjustments to your Initial Contexts by simply adjusting the values in the jndi.properties text file.  Please consult the JNDI Specification at the Java Sun site for more information on using jndi.properties files, where to store them, etc.   Using a jndi.properties file is the best bet when programming applications which need to be ported between different servers and different naming and directory systems.

WITH SSL Secure Sockets DISABLED:

If the cyJNDI server you are connecting to DOES NOT use SSL, you will need to add ONE additionaly line to your InitialContext's Properties:

Properties p=new Properties();
   /*  provide the name of the Context Factory  */
p.put(Context.INITIAL_CONTEXT_FACTORY,"cylikon.cyJNDI.cyInitialContextFactory");

  /*  put your CLIENT username into the Properties */
p.put(Context.SECURITY_PRINCIPAL,"myUsername");

  /* put your CLIENT password into the Properties */
p.put(Context.SECURITY_CREDENTIALS,"myPassword");

    /*  IMPORTANT: This line MUST be here if you do not wish to use SSL (the cyJNDI-cyJMS server you are connecting to does not use SSL) */

p.put(Context.SECURITY_PROTOCOL,"None"); 

    /* The "none" is case-insensitive, so you can put "none", "NONE", "NoNE", etc. */

InitialContext ic=new InitialContext(p);
Object o= ic.lookup("YadaYada");

The rest is just straight JNDI, so you can consult your JNDI documentation for all the specific JNDI methods to call.
By default, the InitialContext is setup to use SSL sockets, so be sure to add the extra line mentioned above if you do NOT wish to use SSL.  Otherwise, your connection will most likely freeze or crash.

NOTE:  If you need to connect to some other host besides "localhost" or some other port besides the default (21472), click here for information on URL Support.

Programming Tip:
If you find that you will be switching between SSL-enabled mode and SSL-disabled mode frequently, it may be smarter to specify your InitialContext properties in a jndi.properties file and simply call "new InitialContext()".  Using a jndi.properties file (usually stored in your java.home directory) will save you from having to re-compile your applications every time you change your cyJNDI-cyJMS server's settings. Instead, you can make adjustments to your Initial Contexts by simply adjusting the values in the jndi.properties text file.  Please consult the JNDI Specification at the Java Sun site for more information on using jndi.properties files, where to store them, etc.   Using a jndi.properties file is the best bet when programming applications which need to be ported between different servers and different naming and directory systems.
 


Where Is My TopicConnectionFactory?:
The TopicConnectionFactory is bound in the namespace to the name  "cyTopicConnectionFactory".  So, simply called Context.lookup("cyTopicConnectionFactory") to get access to it.  If by some accident you unbind your own TopicConnectionFactory from the namespace, do not sweat it.  Simply restart your cyJNDI-cyJMS server and your TopicConnectionFactory will be right back where it was.
More on working with the TopicConnectionFactory

Where Is My QueueConnectionFactory?:
The QueueConnectionFactory is bound in the namespace to the name  "cyQueueConnectionFactory".  So, simply called Context.lookup("cyQueueConnectionFactory") to get access to it.  If by some accident you unbind your own QueueConnectionFactory from the namespace, do not sweat it.  Simply restart your cyJNDI-cyJMS server and your QueueConnectionFactory will be right back where it was.
More on working with the QueueConnectionFactory
 
 



Working With Topics & Queues:
Working WIth TOPICS:

Assuming you have done everything right to get the proper kind of InitialContext, you would simply do the following the establish a TopicConnection and TopicSession:

InitialContext ic = new IntialContext(p);     //  notes

/* Lookup the TopicConnectionFactory */
TopicConnectionFactory tcf=(TopicConnectionFactory)   ic.lookup("cyTopicConnectionFactory"); 

/* Establish a TopicConnection  */
TopicConnection tc=tcf.createTopicConnection();

     /*  If your cyJMS requires authentication, use       tcf.createTopicConnection("myUsername", "myPassword") instead  */

/*  Create a TopicSession  */
TopicSession ts = tc.createTopicSession(false,Session.CLIENT_ACKNOWLEDGE);

/* See the JMS Specification about the different types of TopicSessions you can create. This is merely an example */

/*  Lookup the Queue you wish to use in the namespace */
Topic t = (Topic) ic.lookup("myTopic");

/* Create a TopicPublisher to publish messages */
TopicPublisher pub=ts.createPublisher(t);

/* Create a Subscriber to view the message */
TopicSubscriber sub=ts.createSubscriber(t);

/* Send a message to the Topic */
Message m= ts.createMessage();
m.setStringProperty("type","myFirstcyJMS_Message");
pub.publish(m);

/* Start the TopicConnection to allow  messages to be received */
tc.start();

/* Receive the first message available or NULL if none exists */
Message mess=sub.receiveNoWait();

mess.acknowledge();

NOTE: If you decided to use a MessageListener rather than calling TopicSubscriber.receive(), you must first call TopicSession.run()   to allow messages to be sent to the MessageListener.  You will NOT need to create any seperate threads unless you call TopicSubscriber.receive() - with no timeout.  In that case, you might want to create a seperate thread for the TopicSubscriber.

Working With QUEUES:

Assuming you have done everything right to get the proper kind of InitialContext, you would simply do the following the establish a QueueConnection and QueueSession:

InitialContext ic = new IntialContext(p);    //  notes

/* Lookup the QueueConnectionFactory */
QueueConnectionFactory qcf=(QueueConnectionFactory)   ic.lookup("cyQueueConnectionFactory"); 

/* Establish a QueueConnection  */
QueueConnection qc=qcf.createQueueConnection();

     /*  If your cyJMS requires authentication, us       qcf.createQueueConnection("myUsername", "myPassword") instead  */

/*  Create a QueueSession  */
QueueSession qs = qc.createQueueSession(false,Session.CLIENT_ACKNOWLEDGE);

/* See the JMS Specification about the different types of QueueSessions you can create. This is merely an example */

/*  Lookup the Queue you wish to use in the namespace */
Queue q = (Queue) ic.lookup("myQueue");

/* Create a QueueSender to send messages */
QueueSender sender=qs.createSender(q);

/* Send a message to the Queue */
Message m= qs.createMessage();
m.setStringProperty("type","myFirstcyJMS_Message");
sender.send(m);

/* Create a Receiver to view the message */
QueueReceiver rec=qs.createReceiver(q);

/* Start the QueueConnection to allow messages to be received */
qc.start();

/* Receive the first message available or NULL if none exists */
Message mess=rec.receiveNoWait();

mess.acknowledge();

NOTE: If you decided to use a MessageListener rather than calling QueueReceiver.receive(), you must first call QueueSession.run()   to allow messages to be sent to the MessageListener.  You will NOT need to create any seperate threads unless you call QueueReceiver.receive() - with no timeout.  In that case, you might want to create a seperate thread for the QueueReceiver.


SSL Warnings: 

WARNING - CONNECTIONS (AND YOUR APPLICATION) CAN FREEZE IF...

1. You attempt to connect to a server using TLS\SSL
   secure sockets with a client that is NOT using TLS/SSL
2. You attempt to connect to a server NOT using
    TLS\SSL secure sockets with a client that IS using TLS/SSL
3. You attempt to connect to a server using some
   other form of secure sockets besides the
   supported TLS\SSL security.

Bottom line: KNOW what kind of security, or lack
thereof, the server you are connecting to uses.

Please also note that  initial connections over SSL are inherently slower than connections without SSL, due to the need for the client and server to establish common cipher suites and conduct "handshaking".


Notes For SSL-Enabled Servers: 

First, note that  initial connections over SSL are inherently slower than connections without SSL, due to the need for the client and server to establish common cipher suites and conduct "handshaking".

Second, be aware that, with SSL enabled on your server, server start up may take an additional 1-3 minutes depending on the speed of your server.  This is due to the fact that the server must load all the cipher suites, encryption mechanisms, and certificates available on your computer/server for use with server's sockets.

Third, with SSL enabled, you will NOT be able to telnet into your cyJNDI server with any ordinary telnet client.  You will have to access the terminal using either the built-in terminal application (in the server's interface), the standalone terminal application (cyTerminal.jar), or possibly another terminal application which supports SSL (if you can find one).   The possible results of using a third-party terminal application to connect to the cyJNDI server is not known, as I have not tested this and do not take any responsibility for whatever may happen if you attempt this method.


Notes For SSL-Disabled Servers: 

Initial connections will be slightly faster without SSL, but much less secure.

With SSL disabled, you will be able to telnet into you cyJNDI server with any ordinary telnet client. (This is NOT true for SSL-enabled servers!).

IMPORTANT: You will need to add an crucial line to the Properties of your Initial Context to prevent Exceptions from being thrown and possible application crashes.  If you are setting the properties of your Initial Context inside your application, you will need to do something like the following:
       Properties p=new Properties();
       p.put(Context.SECURITY_PROTOCOL,"NONE")

If you are setting the properties of your Initial Context in a jndi.properties file, you will need to add the following line:
      java.naming.security.protocol=NONE

This is a necessary step, since Initial Contexts for cyJNDI run in SSL-enabled mode by default (since the emphasis of this application server is security).  So, for SSL-disabled Initial Contexts, you MUST set the security protocol to "none".  Otherwise, your client will erroneously attempt to connect to an SSL-disabled server using  SSL sockets, causing either a BadHandshakeException to be thrown or  your client and application to completely hang and/or crash.




Administering Topics And Queues: 

Topic and Queue administration with cyJNDI-cyJMS is very simple.  Simply run the server.  Click the "Topics & Queues" tab. To add a Topic or Queue, type the name of the Topic or Queue in the text field, then click "ADD".  To remove a Topic or Queue, select the name from the drop-down list and click "REMOVE".  It's that easy.  Your new Topic or Queue will be immediately deployed and ready for use.  There is NEVER a need to restart your server after creating or deleting a Topic or Queue.


URL Support & Non-standard hosts and ports: 

cyJNDI provides complete support for URLs as appropriate for this particular namespace.  You can use URLs in your environment Hashtable when setting an InitialContext to point your InitialContext to an already existing context.  URLs   should also be used if you need to connect to a host other than "localhost", or need to connect to a port other than the default "21472".   Valid URLs must be in the following form:

cyjndi://<host Name or Address>:<port>/<context>/     or     cyjndi://<host Name or Address>:<port>/

Examples:
cyjndi://www.myHost.com:555/
cyjndi://www.myHost.com:555
cyjndi://www.myHost.com:1298/myContext/mySubcontext/   (points to the context "/myContext/mySubcontext/")

You would adjust the URL by doing something like the following:

Properties p=new Properties();
p.put(Context.PROVIDER_URL,"cyjndi://www.myHost.com:1298/myContext/mySubcontext/");
InitialContext ic=new InitialContext(p);

Rules To Remember:
1.  The URL MUST begin with "cyjndi://" (Case is NOT important).

2.  If no URL is provided, the InitialContext will point to the URL "cyjndi://localhost:21472/" : A default host of "localhost", the default port 21472, and the default context, "/"  (the uppermost context).

3.  If the URL contains a context ( i.e. cyjndi://www.myHost.com:1298/myContext/mySubcontext/), the URL MUST end with a slash  ( / ) .

4.  If the URL points to a context, it must point to an ALREADY EXISTING CONTEXT.  Otherwise, you will receive a NameNotFoundException when the InitialContext initializes.

5.  URLS that point to a context are only useful for namespaces which are persistent.  If you attempt to point your URL to a context in a NON-persistent cyJNDI namespace, you will automatically receive a NameNotFoundException, since all contexts and bound objects are washed out of a non-persistent namespace each time the server shuts down.

6.  URLs can only point to a host, a port, and a context, not other bound objects.  If a Vector named "BANK" is bound under the context "/myAccount/"  (i.e. "/myAccount/BANK")  you cannot point the URL to "/myAccount/BANK", since it is not a context. You can, however, point the URL to "/myAccount/", if that context exists.  You could then lookup "BANK" from the context.

7.  Lastly, please remember that if your URL points to a context, that you will not be able to lookup or access objects and contexts above the specified context.  So, a URL that points to "/myContext/mySubcontext/" will not be able to access the context "/myContext/" or the uppermost context, "/".  This is VERY important to remember, especially if you will need access to the cyTopicConnectionFactory or the cyQueueConnectionFactory, both of which are bound under the root context, "/".  This should be very obvious, but I have to mention it. Otherwise, someone is likely to e-mail me claiming that their NameNotFoundExceptions are a programming error, when in reality, it is a user error.


Supported JMSX Properties: 

If you've read the JMS 1.0.2 specification, you know that spec allows providers to support optional JMSX properties in Messages, in addition to all the standard JMS properties (JMSReplyTo, JMSType, JMSDestination, etc.).  cyJNDI-cyJMS supports 5 of these optional properties.  Below, is a table describing these properties, their values, and a developer's read-write access to the properties:
 
 

JMSX Supported Properties
Name
Developer Access
Returns
Purpose
setJMSRcvTimestamp(long) NO - protected void Sets a long, denoting when this message was received by a message consumer, such as a QueueReceiver or TopicSubscriber. 
getJMSRcvTimestamp() YES - public long Gets the long denoting when this message was received. The long can then be read as a Date with  "new Date(long)"
setJMSXAppID(String) NO - protected void Identifies your application and connection.  Constant across the connection.
getJMSXAppID() YES - public String Gets the identifier for your connection and application.
setJMSXUserID(String) NO - protected void Identifies your connection. Constant across the connection.
getJMSXUserID() YES - public String Gets the identifier for your connection.
setJMSXGroupID(String) YES - public void A developer can set this property to help categorize related messages.  The value can be set to any String you see fit.
getJMSXGroupID() YES - public String Gets the categorization ID for this message, or NULL if none exists.
setJMXGroupSeq(String) YES - public void  A developer can set this property to help further organize categorized messages.  The value can be set to any String you see fit.
getJMXGroupSeq() YES - public String Gets this message's place in your categorization scheme, or NULL if none exists.

Tip:  To access these JMSX properties, you will need to cast your Message to a cyMessage. For example:
   Message m=Subscriber.receiveNoWait();
   ((cyMessage) m).setJMSXGroupSeq("OurCategory");
  String id = ((cyMessage) m).getJMSXGroupID();
  Date receiveDate= new Date(  ((cyMessage) m ).getJMSXRcvTimestamp()  );
  System.out.println("Message received: "+receiveDate.toString());

Since these properties, are optional (but encouraged) by the Sun's JMS 1.0.2 specification, these methods are NOT standard methods in all  Message objects.  Support for JMSX properties is provider-specific, so casting to a cyMessage is a must if you wish to use them. Beware of CastClassExceptions if you have third-party Message objects floating around in the server  (i.e. messages not created by cyJMS).


JMSType - Usage Rules: 

The JMS 1.0.2 spec provides no rules as to how the setJMSType(String) and getJMSType() methods of a message should be implemented.  So, implementation is pretty much provider-specific.  cyJMS supports 3 types of JMSType settings:

normal : By default, all messages start out with   Message.setJMSType("normal").  With this setting a message may be read and written to freely.

read-only :  If a message is in read-only mode, the Message's primitive properties (setBooleanProperty, setObjectProperty, setStringProperty, setIntProperty, etc.) cannot be written to.  Doing so, will cause a MessageNotWriteableException to be thrown.  Please note that calling   Message.setJMSType("read-only") does NOT stop applications from writing to JMS or JMSX properties, or stop applications from writing to the Text in TextMessages, or the Object in ObjectMessages.  Read-only mode only applies to the standard primitive properties mentioned above.  The only exceptions to this rule are StreamMessages and BytesMessages, which can call BytesMessage.setJMSType("read-only") or StreamMessage.setJMSType("read-only") to prevent applications from writing to the stream or bytes.  Calling BytesMessage.reset() or StreamMessage.reset() automatically puts the message in "read-only" mode, as required by Sun's JMS specification.  Calling Message.setJMSType("normal") will make the message writeable again.

write-only :  This type is ignored unless it is called on a BytesMessage or a StreamMessage.  When called in these cases, Message.setJMSType("write-only") will prevent  applications from reading from the stream or bytes. Attempting to read from a "write-only" message will cause a MessageNotReadableException to be thrown.  Calling Message.setJMSType("normal") will make the message readable again.

NOTE: Setting JMSType to any value besides "normal", "read-only", or "write-only" will cause a NamingException to be thrown.


Class List - Vital Classes Only: 

Server, Setup, and Terminal Classes:

   Package:   cylikon.cyJNDI.*
cyJNDIServer.class  -  The main class for the cyJNDI-cyJMS Server   (cyJNDIcyJMS_Server.jar)
cySetup.class  - The setup program  (cySetup.jar, cyJNDIcyJMS_Server.jar)
cyTerminal.class  -  The SSL-enabled terminal application  (cyTerminal.jar, cyJNDIcyJMS_Server.jar)
Client Classes:
   Package:   cylikon.cyJNDI.*
cyInitialContext.class
cyInitialContextFactory.class
cyInitialContextFactoryBuilder.class
cyContext.class
cyNameParser.class
  Package:   cylikon.cyJMS.*
cyTopicSubscriber.class
cyTopicSession.class
cyTopicPublisher.class
cyTopicConnectionFactory.class
cyTopicConnection.class
cyTopic.class
cyTextMessage.class
cyQueueSession.class
cyQueueSender.class
cyQueueReceiver.class
cyQueueConnectionFactory.class
cyQueueConnection.class
cyQueueBrowser.class
cyQueue.class
cyObjectMessage.class
cyMessageListener.class    (A serializable MessageListener for your convenience )
cyMessage.class
cyMapMessage.class
cyExceptionListener.class    (A serializable ExceptionListener for your convenience )
cyConnectionMetaData.class
cyBytesStreamMessage.class

Extras: 

Two extra classes are included for your convenience:

cyMessageListener.class  - a Serializable MessageListener.  To use it, just extend the class, the override the onMessage(Message m) method.  It is esepecially adviced that you use a Serializable MessageListener if you are creating durable TopicSubscribers, which must be serialized.

cyExceptionListerner.class - a Serializable MessageListener.  To use it, just extend the class, the override the onException(JMSException je) method.   It is esepecially adviced that you use a Serializable ExceptionListener if you are creating durable TopicSubscribers, which must be serialized.
 
 


Working With The cyJNDI Remote Terminal: 

First, connect to the cyJNDI terminal.  After you have established a connection, you will be prompted for a "ROLE:". Simply type 'ADMIN'.  Enter your userame and password when requested.  You can then type 'HELP' at the prompt for a list of commandsPlease Note: All commands, usernames, and passwords are CASE-SENSITIVE.   Type 'EXIT', 'LOGOUT', or 'QUIT' at anytime to logout.  Here is a sample session (Words in red indicate user input):
 
 
cyJNDI-cyJMS Server, version 1.0 beta.
A 100% Java, Secure Naming And Messaging Service Provider.
Copyright 2000 by Li'L CJ (cylikon@hotmail.com). All rights reserved.

Server IP is: 169.254.6.59
Client IP is: 127.0.0.1
Local Time: 18:2:26  6/19/2000 Eastern Standard Time

ROLE: 
ADMIN

login: myUsername
password: ********

200  login ok

Type 'HELP' for a list of commands or 'QUIT' to logout. 

You have 0 ALERTS 

<<?> cyJNDI <?>>==@ SYSSTAT

200  Command ok. 

Server started: 17:54:31  6/19/2000
Current time:   18:8:27  6/19/2000
Total Connections Since Uptime:   2
Number Of Current Connections:   1
Security Incidents:   0 

<<?> cyJNDI <?>>==@ INFO

cyJNDI Server Port: 21472
Max Simultaneous Connections: 5
Using SSL Secure Sockets: true
Monitoring Client Activity: true
Monitoring Security Incidents: true
LOG Files Directory: C:\cylikon
Bound Objects Are Persistent: true
Mail Server Host: localhost
Mail Server Port: 25
Allow Only Selected Clients: false 

Press 'Enter', 'Return', or the 'Send' button to continue.

Block Only Selected Clients: false
List Of Selected Clients: 
Using Scheduled Garbage Collection: true
Garbage Collection Frequency: 240000 milliseconds 

<?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?><?>

Run cySetup to adjust your general cyJNDI server's configuration.
Type 'HELP [USERNAME]' or 'HELP [PASSWD]' for help on changing
usernames and passwords.
 

<<?> cyJNDI <?>>==@ LIST [/]

200  Command ok.

Attempting to list objects... 

Name: /JNDI/   Class: cylikon.cyJNDI.cyContext
Name: /JNDI/JMS/   Class: cylikon.cyJNDI.cyContext
Name: /   Class: cylikon.cyJNDI.cyContext
Name: CJ   Class: javax.naming.CompositeName
Name: /JNDI/JMS/cyJMS/   Class: cylikon.cyJNDI.cyContext
Name: cyQueueConnectionFactory  Class: cylikon.cyJNDI.cyQueueConnectionFactory
Name: cyTopicConnectionFactory  Class: cylikon.cyJNDI.cyTopicConnectionFactory
Name: /JNDI/JMS/cyJMS/   Class: cylikon.cyJNDI.cyContext
Name: /JNDIce/   Class: cylikon.cyJNDI.cyContext

<<?> cyJNDI <?>>==@ LOOKUP [cyQueueConnectionFactory]

200  Command ok.

Attempting object lookup...
 

Context: /
Name: cyQueueConnectionFactory
Class: cylikon.cyJMS.cyQueueConnectionFactory

<<?> cyJNDI <?>>==@ LIST [/JNDIce/]

200  Command ok.

Attempting to list objects...
 

Name: /   Class: cylikon.cyJNDI.cyContext
Name: ICE   Class: java.util.Vector

<<?> cyJNDI <?>>==@ LOOKUP [/JNDIce/ICE]

200  Command ok.

Attempting object lookup... 
 

Context: /JNDIce/
Name: ICE
Class: java.util.Vector

<<?> cyJNDI <?>>==@ EXIT

200  Command ok.
Administrator logged out.
 


cyJNDI Terminal Commands: 

ABOUT  Information about cyJNDI. Shows information about cyJNDI.  Type 'ABOUT' at the prompt for info about this cyJNDI distribution,
possible updates, and other free Java software.

ALERTS  Shows info about any major errors or security-issues since uptime.  Shows info about any major errors or security-issues since uptime.  Type 'ALERTS' at the prompt for any urgent messages you need to read.

EXIT  Logout from this terminal.  Same as 'QUIT' and 'LOGOUT'  Simply type 'EXIT' at the prompt to disconnect from the cyJNDI
terminal.

INFO  Shows information about your cyJNDI settings. Shows information about your cyJNDI settings. Type 'INFO' at the prompt for useful information about your cyJNDI server's current configuration.

HELP  Provide help with available commands.  Simply type 'HELP' at the prompt to view all commands.

 Usage: 'HELP [command]'
Usage: 'HELP' - shows quick explanations of all available commands
Usage: 'HELP [command]' - provides detailed information on the specified command
Example:  HELP [LOOKUP]


LIST  Lists objects under the specified context.  Usage: 'LIST [context]'  Returns a name-class pair listing for objects under the specified context.

Usage: 'LIST [context]'
Example: LIST [/] to list objects under the uppermost context
Example: LIST [/hello/] to list objects under a context named 'hello'


LOGOUT  Logout from this terminal.  Same as 'QUIT' and 'EXIT'.  Logout from this terminal.  Simply type 'LOGOUT' at the prompt to disconnect from the cyJNDI terminal.

LOOKUP  Check the availability of a bound object.  Usage: 'LOOKUP [object name]'.  Checks the availability of a bound object.

Usage: 'LOOKUP [object name]'
Example:  LOOKUP [myJNDIMailServer]
The LOOKUP command will either return a
'404 Object not bound' message, indicating that no object
by the specified name is currently bound to the
JNDI namespace or will indicate that the object is bound and
return the name of the Java class object
currently associated with the specified name.
Example: LOOKUP [/myObj/Vector]
to lookup an object named 'Vector' under the context '/myObj/'
 
 

PASSWD  Change a password. Usage: 'PASSWD [CLIENT]' or 'PASSWD [ADMIN]'.  Use this command to change an ADMIN or CLIENT password. You will be asked to confirm your old password, then enter a new password.
 

Usage: PASSWD [ADMIN] - will guide you through changing your
ADMINISTRATOR password. The changes will take effect the next
time you login under the ADMIN account.
Usage: PASSWD [CLIENT] - will guide you through changing the
password for ALL cyJNDI CLIENTS. To prevent problems with currently
running cyJNDI clients, changes to CLIENT passwords will
take effect the next time the cyJNDI server is restarted.

 

QUIT  Logout from this terminal.  Same as 'EXIT' and 'LOGOUT'.  Logout from this terminal.  Simply type 'QUIT' at the prompt to disconnect
from the cyJNDI terminal.

SENDLOGS  Have your cyJNDI logs sent to you via e-mail.  This feature requires the JavaMail API classes version 1.1.3 or
better and a mail server and mail port properly configured using  cySetup. This feature will send any available logs, including error
and security logs,@to the email address you specify.  Simply type 'SENDLOGS' at the prompt.

SHUTDOWN  Shutdown the cyJNDI-cyJMS server completely.  This command will shutdown the cyJNDI service, including all current connections.  Simply type 'SHUTDOWN' to shutdown your server remotely.

SYSSTAT  Shows cyJNDI system stats. Shows useful information such as the current load, uptime, total users since uptime, etc.
Simply type 'SYSSTAT' at the prompt

UNBIND  Remove an object from the JNDI namespace.  Usage: 'UNBIND [object name]'.  Removes an object from the JNDI namespace.
UNBIND destroys the association between the specified name and its bound object. The resources once held by the object bound to this name are freed.  To make the object available to the JNDI namespace again, 'bind' or 'rebind' would have to be called from within a client's Context or InitialContext session (see the javax.naming API for more info)

Usage: 'UNBIND [object name]'
Example: UNBIND [myJNDIMailServer]
Example:  UNBIND [/myObj/Vector] to unbind an object from the
hypothetical context /myObj/


USERNAME  Change a username.  Usage: 'USERNAME [CLIENT]' or 'USERNAME [ADMIN]'. Use this command to change a ADMIN or CLIENT username.

Usage: USERNAME [ADMIN] - will guide you through changing your ADMINISTRATOR username.
The changes will take effect the next time you login under the ADMIN account.

Usage: USERNAME [CLIENT] - will guide you through changing the username for ALL cyJNDI CLIENTS. To prevent problems with currently running cyJNDI clients, changes to CLIENT usernames will take effect the next time the cyJNDI server is restarted.


WHO  Show a list of currently logged on IP addresses.  Shows a list of currently logged on IP addresses. Also indicates whether each user is an ADMIN or CLIENT  Simply type 'WHO' at the prompt for a list of currenly logged on users.  A user is one of two types: a 'CLIENT', indicating a  person using cyJNDI from a Context or InitialContext,  or an 'ADMIN', indicating an administrator using cyJNDI
from the cyJNDI terminal.
 



Known Bugs:

- JPYTHON users:  If you use cyJMS from the JPython prompt or a JPython program, you may experience a problem sending ObjectMessages.  This problem usually occurs when setObject() is called.  When a ObjectMessage is sent in which the object value is NOT null, you may receive a ClassNotFoundException for "org.python.core.PyJavaInstance".  Even if you do somehow add "org.python.core.PyJavaInstance" to your classpath and get rid of the ClassNotFoundException, you will probably encounter a NotSerializableException directed at the object you supplied to setObject() and "org.python.core.PyJavaInstance" .  This bug only seems to occur when an ObjectMessage is SENT.  I have encountered no problems receiving ObjectMessages in JPython.  It appears that somehow an instance of "org.python.core.PyJavaInstance" is getting "stuffed" into the sent Object.   Note: I did not encounter this problem sending any type of message and calling Message.setObjectProperty("myObject", Object o).  So, this could be an EASY work-around in JPython.  The bug is specific to SENDING non-NULL objects in ObjectMessage using Message.setObject(Object o).  This problem also is specific to JPython as far as I have seen (version 1.1).  If you see this error any place else, send a bug report.

- JPYTHON users:  If you use cyJNDI from the JPython prompt or a JPython program, you may experience a NameNotFoundException with Subcontext.lookupLink(Name name).  This bug seems to arise when a SUB-context's lookupLink() method is called using a Name instead of a String.  You will encounter a NameNotFoundException, even though you know that the object is definitely bound to the namespace. This problem seems to be specific to JPython and SUB-contexts, when lookupLink(Name name) is called instead of lookupLink(String name).
This bug also only affects SUB-contexts, not regular contexts.  I am working on a fix for this bug, so check back often. If you spot this bug in another place besides where I have described, send a bug report.  The work around is to call Subcontext.lookupLink(String name) instead of looking up a Name, CompoundName, or CompositeName.



Bug-Reports:
NO TECHNICAL SUPPORT is offered for this software.  PLEASE DO NOT EMAIL FOR HELP or to ask, "How do I do such and such...?".  However, bug reports and feedback are welcome.  If you are reporting a bug, please do me a huge favor and quickly search for a file named "cyjndi.bugs" in your java.home directory.  If you find this file, and the "cyjndi.bugs" file is not empty, please attach it in your email when reporting a bug.   If you don't know where the java.home directory is, just run a search of your hard-drive.  The file may contain some useful logging of the "bug" you are experiencing, and may have logged your server's errors at the time they occurred. It would be a big help and will probably help get the "bug" fixed faster.  Thanks a bunch.  8-)
cylikon@hotmail.com


Coming Soon: 

- Full directory and search support  (hopefully, within the next couple of weeks - as time permits).
- Support for events and event listeners  (hopefully, within the next month or so - as time permits)
- More complete message selector support (when I get around to it).
- Bug fixes and overall improvements as I see the need for them.

Check back often for updated versions of cyJNDI-cyJMS.


License and Copyright: 

cyJNDI Copyright 2000 by Erica Andrews a.k.a. Li'L CJ.
cyJMS Copyright 2000 by Erica Andrews
JNDIce Copyright 2000 by Erica Andrews
CJ's MailerBean Copyright 2000 by Erica Andrews
All rights reserved.
cylikon@hotmail.com
http://members.aol.com/IcedPinky/
http://members.aol.com/ButchWhipAppeal/

This application is RESTRICTED FREEWARE.
This application is NOT OPEN SOURCE.

The author of this application hereby grants the public unlimited *personal* use of this software provided it is *not* used for any commercial purposes or ventures whatsoever, is *not* used for any sort of profit, either directly or indirectly, and *no* portion of this software is modified in any way. No disassembly, decompilation, or other dealings with any source code from this software are permitted.  This software may not be used  by for-profit organizations/individuals, or used on computers or other data systems owned  by corporations or other for-profit organizations, without the express, written consent of the author.  Any use of this software which is not consistent with the aforementioned terms, without the  written consent of the author, constitutes unauthorized, fraudulent misuse of the software, punishable in a court of law. By  downloading and/or using this software, you agree to the terms above as well as the disclaimer.



Disclaimer: 

By using this software, you acknowledge that this software is distributed on an as-is basis, without any warrantee of any kind, and
agree that the author of this software will not, under any circumstances, be held responsible for any damages, losses, or inconveniences derived from the use of this software.