Интерфейс уровня вызовов Oracle для C++ (Oracle C++ Call Interface, OCCI) специфицирует отображение объектных типов в C++. Таким образом, можно получить доступ к экземплярам объектных типов в базе данных, и их можно модифицировать из объектов C++ в приложении. Навигационный интерфейс OCCI позволяет получать доступ к объектно-реляционным данным и модифицировать их как объекты C++ без явного использования SQL.
Транслятор объектных типов Object Types Translator (OTT) генерирует по умолчанию классы C++, соответствующие объектным типам, включая иерархии типов. Он также предоставляет по умолчанию реализации методов, необходимых для чтения объектов из базы данных и их записи в базу данных.
Для примера рассмотрим следующую иерархию объектных типов:
CREATE TYPE Person AS OBJECT (name VARCHAR2(100), age NUMBER) NOT FINAL; CREATE TYPE Student UNDER Person(dept VARCHAR2(50), advisor REF Person);
Далее приведены классы C++, сгенерированные OTT для этой иерархии типов. Класс OCCIPObject предоставляется интерфейсом OCCI как базовый класс для классов, обладающих сохраняемыми (persistent) или временными объектами.
class Person : public OCCIPObject { … void *operator new(size_t size, const OCCIConnection& con, const OCCIString& table); static void readSQL(const OCCIAnyData& stream, Person *obj); static void writeSQL(const Person *obj, OCCIAnyData& stream); …} class Student : public Person {… static void readSQL(const OCCIAnyData& stream, Student *obj); static void writeSQL(const Student *obj, OCCIAnyData& stream); …}
Фрагменты кода, соответствующие двум методам, приведены ниже:
void Person::readSQL(const OCCIAnyData& stream, Person *obj){ obj->name = stream.getString(1); obj->age = stream.getNumber(2); } void Student::readSQL(const OCCIAnyData& stream, Student *obj) { Person::readSQL(stream, obj); obj->dept = stream.getString(3); obj->advisor = stream.getRef(4); }
Таблица отображения типов поддерживает ассоциацию между именами типов SQL и именами классов C++, и она используется во время исполнения для определения класса, чьи подпрограммы readSQL и writeSQL должны быть вызваны. OTT также обеспечивает для пользователей гибкость расширения сгенерированных классов для добавления дополнительных выполняемых функций.
Следующий фрагмент кода иллюстрирует выборку объекта SQL в экземпляре класса C++:
OCCIResultSet *resultSet = stmt->executeQuery("select VALUE(p) from person_tab p where name = "Joe""); /* выборка объекта создает соответствующий экземпляр класса */ Student *joe = (Student *)resultSet.getObject(1); /* dereferencing the REF value yields the object */ Person *joe_advisor = joe->advisor->ptr();