|Oracle8i Application Developer's Guide - Object-Relational Features
Release 2 (8.1.6)
Part Number A76976-01
In Oracle8i, you can create object types with SQL data definition language (DDL) commands, and you can manipulate objects with SQL data manipulation language (DML) commands. Object support is built into Oracle's application programming environments:
Oracle SQL DDL provides the following support for object types:
Oracle SQL DML provides the following support for object types:
PL/SQL allows you to use the SQL features that support object types within functions and procedures.
The parameters and variables of PL/SQL functions and procedures can be of object types.
You can implement the methods associated with object types in PL/SQL. These methods (functions and procedures) reside on the server as part of a user's schema.
For a complete description of PL/SQL, see PL/SQL User's Guide and Reference.
OCI is a set of C library functions that applications can use to manipulate data and schemas in an Oracle database. OCI supports both traditional 3GL and object-oriented techniques for database access, as explained in the following sections.
An important component of OCI is a set of calls to manage a workspace called the object cache. The object cache is a memory block on the client side that allows programs to store entire objects and to navigate among them without additional round trips to the server.
The object cache is completely under the control and management of the application programs using it. The Oracle server has no access to it. The application programs using it must maintain data coherency with the server and protect the workspace against simultaneous conflicting access.
OCI provides functions to
OCI improves concurrency by allowing individual objects to be locked. It improves performance by supporting complex object retrieval.
OCI developers can use the object type translator to generate the C datatypes corresponding to a Oracle object types.
Oracle Call Interface Programmer's Guide for more information about using objects with OCI.
Traditionally, 3GL programs manipulate data stored in a relational database by executing SQL statements and PL/SQL procedures. Data is usually manipulated on the server without incurring the cost of transporting the data to the client(s). OCI supports this associative access to objects by providing an API for executing SQL statements that manipulate object data. Specifically, OCI allows you to:
REFs), and collections as input variables in SQL statements
REFs, and collections as output of SQL statement fetches
REFs, and collections
In the object-oriented programming paradigm, applications model their real-world entities as a set of inter-related objects that form graphs of objects. The relationships between objects are implemented as references. An application processes objects by starting at some initial set of objects, using the references in these initial objects to traverse the remaining objects, and performing computations on each object. OCI provides an API for this style of access to objects, known as navigational access. Specifically, OCI allows you to:
To support high-performance navigational access of objects, OCI runtime provides an object cache for caching objects in memory. The object cache supports references (
REFs) to database objects in the object cache, the database objects can be identified (that is, pinned) through their references. Applications do not need to allocate or free memory when database objects are loaded into the cache, because the object cache provides transparent and efficient memory management for database objects.
Also, when database objects are loaded into the cache, they are transparently mapped into the host language representation. For example, in the C programming language, the database object is mapped to its corresponding C structure. The object cache maintains the association between the object copy in the cache and the corresponding database object. Upon transaction commit, changes made to the object copy in the cache are propagated automatically to the database.
The object cache maintains a fast look-up table for mapping
REFs to objects. When an application de-references a
REF and the corresponding object is not yet cached in the object cache, the object cache automatically sends a request to the server to fetch the object from the database and load it into the object cache. Subsequent de-references of the same
REF are faster because they become local cache access and do not incur network round-trips. To notify the object cache that an application is accessing an object in the cache, the application pins the object; when it is finished with the object, it unpins it. The object cache maintains a pin count for each object in the cache. The count is incremented upon a pin call and decremented upon an unpin call. When the pin count goes to zero, it means the object is no longer needed by the application. The object cache uses a least-recently used (LRU) algorithm to manage the size of the cache. When the cache reaches the maximum size, the LRU algorithm frees candidate objects with a pin count of zero.
When you build an OCI program that manipulates objects, you must complete the following general steps:
For example, to manipulate instances of the object types in a C program, you must represent these types in the C host language format. You can do this by representing the object types as C structs. You can use a tool provided by Oracle called the Object Type Translator (OTT) to generate the C mapping of the object types. The OTT puts the equivalent C structs in header (*.h) files. You include these *.h files in the *.c files containing the C functions that implement the application.
The Oracle Pro*C/C++ precompiler allows programmers to use user-defined datatypes in C and C++ programs.
Pro*C developers can use the Object Type Translator to map Oracle object types and collections into C datatypes to be used in the Pro*C application.
Pro*C provides compile time type checking of object types and collections and automatic type conversion from database types to C datatypes.
Pro*C includes an EXEC SQL syntax to create and destroy objects and offers two ways to access objects in the server:
For background information on associative access, see "Associative Access in OCI Programs".
Pro*C/C++ offers the following capabilities for associative access to objects:
DELETEstatements, or in the
WHEREclause of a
DESCRIBEstatement, to get the object's type and schema information
For background information on navigational access, see "Navigational Access in OCI Programs".
Pro*C/C++ offers the following capabilities to support a more object-oriented interface to objects:
The C representation for objects that is generated by the Oracle Type Translator (OTT) uses OCI types whose internal details are hidden, such as
OCINumber for scalar attributes. Collection types and object references are similarly represented using
OCIRef types. While using these "opaque" types insulates you from changes to their internal formats, using such types in a C or C++ application is cumbersome. Pro*C/C++ provides the following ease-of-use enhancements to simplify use of OCI types in C and C++ applications:
GETstatement. Furthermore, if the collection is comprised of scalar types, then the OCI types can be implicitly converted to a compatible C type.
SETstatement. As with the
GETstatement, if the collection is comprised of scalar types, C types are implicitly converted to OCI types.
The Oracle type translator (OTT) is a program that automatically generates C language structure declarations corresponding to object types. OTT makes it easier to use the Pro*C precompiler and the OCI server access package.
Oracle Objects for OLE (OO4O) provides full support for accessing and manipulating instances of
REFs, value instances, variable-length arrays (
VARRAYs), and nested tables in an Oracle database server.
Figure 3-1 illustrates the containment hierarchy for value instances of all types in OO4O.
Instances of these types can be fetched from the database or passed as input or output variables to SQL statements and PL/SQL blocks, including stored procedures and functions. All instances are mapped to COM Automation Interfaces that provide methods for dynamic attribute access and manipulation. These interfaces may be obtained from:
The OraObject interface is a representation of an Oracle embedded object or a value instance. It contains a collection interface (OraAttributes) for accessing and manipulating (updating and inserting) individual attributes of a value instance. Individual attributes of an OraAttributes collection interface can be accessed by using a subscript or the name of the attribute.
The following Visual Basic example illustrates how to access attributes of the
Address object in the
Dim Address OraObject Set Person = OraDatabase.CreateDynaset("select * from person_tab", 0&) Set Address = Person.Fields("Addr").Value msgbox Address.Zip msgbox.Address.City
The OraRef interface represents an Oracle object reference (
REF) as well as referenceable objects in client applications. The object attributes are accessed in the same manner as attributes of an object represented by the OraObject interface. OraRef is derived from an OraObject interface via the containment mechanism in COM.
REF objects are updated and deleted independent of the context they originated from, such as Dynasets. The OraRef interface also encapsulates the functionality for navigating through graphs of objects utilizing the Complex Object Retrieval Capability (COR) in OCI, described in "Pre-Fetching Related Objects (Complex Object Retrieval)".
The OraCollection interface provides methods for accessing and manipulating Oracle collection types, namely variable-length arrays (
VARRAYs) and nested tables in OO4O. Elements contained in a collection are accessed by subscripts.
The following Visual Basic example illustrates how to access attributes of the
EnameList object from the
Dim EnameList OraCollection Set Person = OraDatabase.CreateDynaset("select * from department", 0&) set EnameList = Department.Fields("Enames").Value 'access all elements of the EnameList VArray for I=1 to I=EnameList.Size msgbox EnameList(I) Next I
Java has emerged as a powerful, modern object-oriented language that provides developers with a simple, efficient, portable, and safe application development platform. Oracle provides two ways to integrate Oracle object features with Java: JDBC and Oracle SQLJ. The following sections provide more information about these environments.
JDBC (Java Database Connectivity) is a set of Java interfaces to the Oracle server. Oracle provides tight integration between objects and JDBC. You can map SQL types to Java classes with considerable flexibility.
Version 2.0 of the JDBC specification supports Object-Relational constructs such as user-defined (Object) types. JDBC materializes Oracle objects as instances of particular Java classes. Using JDBC to access Oracle objects involves creating the Java classes for the Oracle objects and populating these classes. You can either:
STRUCT. In this case, JDBC creates the classes for the attributes and populates them for you.
SQLDatainterface or the
SQLJ provides access to server objects using SQL statements embedded in the Java code:
Oracle SQLJ supports either strongly typed or weakly typed Java representations of object types, reference types (
REFs), and collection types (
VARRAYs and nested tables) to be used in iterators or host expressions.
Strongly typed representations use a custom Java class that corresponds to a particular object type, reference type, or collection type and must implement the interface
CustomDatum. The Oracle JPublisher utility can automatically generate such custom Java classes.
Weakly typed representations use the class
STRUCT (for objects),
REF (for references), or
ARRAY (for collections).
See Also: "Manipulating Objects Through Java" for sample code showing both techniques.:
Oracle lets you map Oracle object types, reference types, and collection types to Java classes and preserve all the benefits of strong typing. You can:
We recommend that you use JPublisher, and subclass when the generated classes do not do everything you need.
When you run JPublisher for a user-defined object type, it automatically creates the following:
This class includes getter and setter methods for each attribute. The method names are of the form
setFoo() for attribute
Also, you can optionally instruct JPublisher to generate wrapper methods in your class that invoke the associated Oracle object methods executing in the server.
This class includes a
getValue() method that returns an instance of your custom object class, and a
setValue() method that updates an object value in the database, taking as input an instance of the custom object class.
When you run JPublisher for a user-defined collection type, it automatically creates the following:
This class includes overloaded
setArray() methods to retrieve or update a collection as a whole, a
getElement() method and
setElement() method to retrieve or update individual elements of a collection, and additional utility methods.
JPublisher-produced custom Java classes in any of these categories implement the
CustomDatum interface, the
CustomDatumFactory interface, and the
The Oracle8i JPublisher User's Guide for more information about using JPublisher.