Oracle8i Enterprise JavaBeans and CORBA Developer's Guide
Release 8.1.5

A64683-01

Library

Product

Contents

Index

Prev  Chap Top Next

A First CORBA Application

This section introduces the JServer CORBA application development process. It tells you how to write a simple but useful program that runs on a client system, connects to Oracle using IIOP, and invokes a method on a CORBA server object that is activated and runs inside an Oracle8i Java VM.

This section addresses only the purely mechanical aspects of the development process. Application developers know that for large-scale applications the design is a crucially important step. See "For More Information" for references to documents on CORBA design.

The CORBA application development process has seven phases:

  1. Design and write the object interfaces.

  2. Generate stubs and skeletons, and other required support classes.

  3. Write the server object implementations.

  4. Use the client-side Java compiler to compile both the Java code that you have written, and the Java classes that were generated by the IDL compiler. Generate a JAR file to contain the classes and any other resource files that are needed.

  5. Publish a name for the directly-accessible objects with the CosNaming service, so you can access them from the client program.

  6. Write the client side of the application. This is the code that will run outside of the Oracle8i data server, on a workstation or PC.

  7. Compile the client code using the JDK Java compiler.

  8. Load the compiled classes into the Oracle8i database, using the loadjava tool and specifying the JAR file as its argument. Make sure to include all generated classes, such as stubs and skeletons. (Stubs are required in the server when the server object acts as a client to another CORBA object.)

The remainder of this section describes these steps in more detail, with IDL and Java code examples to illustrate the coding steps.

The first sample application simply asks the user for an employee number in the famous EMP table, and returns the employee's last name and current salary, or throws an exception if there is no employee in the database with that ID number.

Writing the IDL Code

From the description above, it is apparent that the application requires only a single server-side object: some code that takes an ID number and queries the database for the other information about the employee.

So the interface requires three things:

The example defines an operation called query to get the information, uses an IDL struct to return the information, and defines an exception called SQLError to signal that no employee was found. Here is the IDL code:

module employee {

  struct EmployeeInfo {
    wstring name;
    long number;
    double salary; 
  };

  exception SQLError {
    wstring message;
  };

  interface Employee {
    EmployeeInfo getEmployee (in long ID) raises (SQLError);
  };
};

This code specifies the three things listed above: a struct, EmployeeInfo, an operation or method, getEmployee(), and the exception, SQLError.

Generate Stubs and Skeletons

Use the idl2java compiler to compile the interface description. Since there is no use of the Tie mechanism in this example, you can invoke the compiler with the -no_tie option. This means that two fewer classes are generated. The compiler does generate interface, helper, and holder classes for the three objects in the IDL file, as well as a stub and skeleton class for the Employee interface. (The 12th class is the example for the interface. See "Using IDL" for more information about these classes.)

Compile the IDL as follows:

% idl2java -no_tie -no_comments employee.idl


Note:

In this section, separate commands are shown for each step of the process. Since developing a CORBA application involves many compilation, loading, and publishing steps, Oracle recommends that if you are working in a command-line oriented environment, you always use a makefile or a batch file to control the process. Or, you can use IDE products such as Oracle's JDeveloper to control the process.

Study the make or batch files that come with the CORBA programs on the CD for good examples.  


Write the Server Object Implementation

For this example, you must implement the Employee interface. The _example_Employee.java file that the IDL compiler generates can provide a basis for the implementation. Here is the complete code that implements the interface:

package employeeServer;

import employee.*;
import java.sql.*;

public class EmployeeImpl extends _EmployeeImplBase {

  public EmployeeImpl() {
  }

  public EmployeeInfo getEmployee (int ID) throws SQLError {
    try {
      Connection conn =
          new oracle.jdbc.driver.OracleDriver().defaultConnection ();
      PreparedStatement ps =
          conn.prepareStatement ("select ename, sal from emp where empno = ?");
      try {
        ps.setInt (1, ID);
        ResultSet rset = ps.executeQuery ();
        if (!rset.next ())
          throw new SQLError ("no employee with ID " + ID);
        return new EmployeeInfo (rset.getString (1), ID, rset.getFloat (2));
      } finally {
        ps.close ();
      }
    } catch (SQLException e) {
      throw new SQLError (e.getMessage ());
    }
  }
}

This code uses the JDBC API to perform the query. Notice the use of a prepared statement to accommodate the variable in the WHERE clause of the query. See the for more about Oracle8i JDBC. Also notice that when a JDBC SQLException is caught, the IDL-defined SQLError is thrown back to the client.

Write the Client Code

To access the server object you must be able to refer to it by name. In step 7 of this process, you will publish the server object in the Oracle8i database. The client code looks up the published name, and activates the server object as a by-product of the look up. There are a number of other operations that go on when code such as that listed below looks up a published object. For example, the ORB on the server side is started, and the client is authenticated using the environment properties supplied when the initial context object is created. See "Authentication".

After getting parameters such as the name of the object to look up, an IIOP service name, and some authentication information like the database username and password, the client code performs the following four steps:

  1. Instantiates and populates a JNDI InitialContext object with the required connect properties. See "About JNDI".

  2. Invokes the lookup() method on the initial context, with a URL as a parameter that specifies the service name and the name of the object to be found. lookup() returns an object reference to the Employee CORBA server object. See "Looking Up an Object" for more information.

  3. Using the object reference returned by the lookup() method, invokes the getEmployee() method on the object in the server. This method returns an EmployeeInfo class (derived from the IDL EmployeeInfo struct). For simplicity an employee ID number is hard-coded as a parameter of this method invocation.

  4. Prints the values returned by getEmployee() in the EmployeeInfo class.

    import employee.*;
    import oracle.aurora.jndi.sess_iiop.ServiceCtx;
    import javax.naming.Context;
    import javax.naming.InitialContext;
    import java.util.Hashtable;
    
    public class Client {
      public static void main (String[] args) throws Exception {
        String serviceURL = "sess_iiop://localhost:2481:ORCL";
        String objectName = "/test/myEmployee";
     
    // Step 1:
        Hashtable env = new Hashtable ();
        env.put (Context.URL_PKG_PREFIXES, "oracle.aurora.jndi");
        env.put (Context.SECURITY_PRINCIPAL, "SCOTT");
        env.put (Context.SECURITY_CREDENTIALS, "TIGER");
        env.put (Context.SECURITY_AUTHENTICATION, ServiceCtx.NON_SSL_LOGIN);
        Context ic = new InitialContext (env);
    
    // Step 2:
        Employee employee = (Employee)ic.lookup (serviceURL + objectName);
    
    // Step 3 (using SCOTT's employee ID number):
        EmployeeInfo info = employee.getEmployee (7788);
    
    // Step 4:
        System.out.println (info.name + " " + info.number + " " + info.salary);
      }
    }
    
    

When the client code runs, it should print the line

SCOTT 7788 3000.0

on the client system console.

Compiling the Java Source

You run the client-side Java byte code compiler to compile all the Java source that you have created, including the client and server object implementation that you wrote as well as the Java sources for the classes that were generated by the IDL compiler.

For the example shown above, you must compile the following files:

Other generated Java files are compiled following the dependencies that the Java compiler uses.

Oracle8i JServer supports the Java JDK compiler, release 1.1.6. You might be able to use other Java compilers, such as a compiler incorporated in an IDE, but only JDK 1.1.6 is supported for this release.

Load the Classes into the Database

CORBA server objects, such as the EmployeeImpl object that has been created for this example, execute inside the Oracle8i database server. You must load them into the server, so that they can be activated by the ORB as required. You must also load all dependent classes, such as IDL-generated Holder and Helper classes, and classes used by the server object, such as the EmployeeInfo class of this example.

Use the loadjava tool to load each of the server classes into the Oracle8i database. For the example in this section, issue the loadjava command in the following way:

% loadjava -oracleresolver -resolve -user scott/tiger 
   employee/Employee.class employee/EmployeeHolder.class 
   employee/EmployeeHelper.class employee/EmployeeInfo.class 
   employee/EmployeeInfoHolder.class employee/EmployeeInfoHelper.class 
   employee/SQLError.class employee/SQLErrorHolder.class 
   employee/SQLErrorHelper.class employee/_st_Employee.class 
   employee/_EmployeeImplBase.class employeeServer/EmployeeImpl.class

Of course you do not load any client implementation classes, or any other classes that are not used on the server side.

It is sometimes more convenient to combine the server classes into a JAR file, and simply use that file as the argument to the loadjava command. In this example, you could issue the command:

% jar -cf0 myJar.jar employee/Employee.class employee/EmployeeHolder.class \
   employee/EmployeeHelper.class employee/EmployeeInfo.class \
   employee/EmployeeInfoHolder.class employee/EmployeeInfoHelper.class \
   employee/SQLError.class employee/SQLErrorHolder.class \
   employee/SQLErrorHelper.class employee/_st_Employee.class \
   employee/_EmployeeImplBase.class employeeServer/EmployeeImpl.class

and then give the loadjava command as simply:

% loadjava -oracleresolver -resolve -user scott/tiger myJar.jar

Publish the Object Name

The final step in preparing the application is to publish the name of the CORBA server object implementation in the Oracle8i database. See "The Name Space" for information about publishing and published objects.

For the example in this section, you can publish the server object using the publish command as follows:

% publish -republish -user scott -password tiger -schema scott 
    -service sess_iiop://localhost:2481:ORCL 
    /test/myEmployee employeeServer.EmployeeImpl employee.EmployeeHelper

This command specifies the following:

See "publish" for more information about the publish command and its arguments.

Run the Example

To run this example, simply execute the client class using the client-side Java VM. For this example, you must set the CLASSPATH for the java command to include

These libraries are located in the lib directory under the Oracle home location in your installation.

The following invocation of the JDK java command runs this example. Note that the UNIX shell variable ORACLE_HOME might be represented as %ORACLE_HOME% on Windows NT, and that JDK_HOME is the installation location of the Java Development Kit (JDK), version 1.1.6:

% java -classpath 
.:$(ORACLE_HOME)/lib/aurora_client.jar:$(ORACLE_HOME)/jdbc/lib/classes111.zip:
$(ORACLE_HOME)/sqlj/lib/translator.zip:$(ORACLE_HOME)/lib/vbjorb.jar:
$(ORACLE_HOME)/lib/vbjapp.jar:$(JDK_HOME)/lib/classes.zip Client 
sess_iiop://localhost:2481:ORCL /test/myEmployee scott tiger 

This example assumes that the client is invoked with four arguments on the command line:

From the java command you can see why it is almost always better to use a makefile or a batch file to build CORBA applications.




Prev

Top

Next
Oracle
Copyright © 1999 Oracle Corporation.

All Rights Reserved.

Library

Product

Contents

Index