Logo Море(!) аналитической информации!
IT-консалтинг Software Engineering Программирование СУБД Безопасность Internet Сети Операционные системы Hardware
Скидка до 20% на услуги дата-центра. Аренда серверной стойки. Colocation от 1U!

Миграция в облако #SotelCloud. Виртуальный сервер в облаке. Выбрать конфигурацию на сайте!

Виртуальная АТС для вашего бизнеса. Приветственные бонусы для новых клиентов!

Виртуальные VPS серверы в РФ и ЕС

Dedicated серверы в РФ и ЕС

По промокоду CITFORUM скидка 30% на заказ VPS\VDS

VPS/VDS серверы. 30 локаций на выбор

Серверы VPS/VDS с большим диском

Хорошие условия для реселлеров

4VPS.SU - VPS в 17-ти странах

2Gbit/s безлимит

Современное железо!

2003 г

Простые стратегии для сложных данных: объектно-реляционная технология Oracle9i

Источник: Geoff Lee и др., An Oracle Technical White Paper, май 2002
Перевод Алексея Резниченко
Oracle Magazine RE

Предисловие редакторов русского перевода

В данном документе четко и лаконично изложены основные принципы объектно- реляционной технологии, воплощенной в новом продукте компании Oracle – в сервере баз данных Oracle9i. Редакция журнала считает необходимым познакомить с ним читателей. Вместе с тем, подготовка и публикация перевода этого документа была в определенной степени инициирована также терминологической дискуссией, сопровождавшей перевод на русский язык документации Oracle9i, который выполнялся специалистами компаний РДТЕХ (www.rdtex.ru) и ITI Ltd. (www.iti.ru). Некоторые фрагменты этой дискуссии отражены в последних публикациях колонки "О чистоте русского языка и точности терминологии". В ходе дискуссии ее участники неоднократно указывали на вольности с терминологией в документации Oracle. В отличие от документации Oracle9i данный документ безупречен в части терминологии.

К сожалению, авторы документа не приводят никаких сведений о соотношении объектных возможностей, предусмотренных в Oracle 9i и в стандартах SQL:1999, а также SQL:200n – новой версии международного официального стандарта языка SQL, разработка которой завершается в настоящее время.

Все стандарты, на которые имеются ссылки в данном документе, подробно рассмотрены в книге М.Р.Когаловского "Энциклопедия технологий баз данных" (М: "Финансы и статистика", 2002). Там же содержатся необходимые ссылки на соответствующие официальные документы и другие публикации, включая отечественные. Кроме того, полезные публикации по затрагиваемым в статье вопросам указываются в примечаниях редакторов перевода.

Анатолий Бачин,
Михаил Когаловский,
Александр Соколов

Содержание

 Введение

СУБД Oracle9i ™ быстро превратилась в СУБД для всех типов данных – от простых до сложных. Мультимедийные типы данных, такие, как изображения, карты, видео- и аудио- клипы, редко обрабатывались неспециализированным программным обеспечением. Но в настоящее время многие веб-приложения требуют от своих серверов баз данных управления такими данными. Иные программные решения были также необходимы для хранения данных, которыми оперируют:

  • финансовые инструменты;
  • технические диаграммы;
  • молекулярные структуры.

Для удовлетворения этих потребностей сервер баз данных Oracle9i ™ предоставляет объектно-реляционную технологию, которая обеспечивает простые методы разработки, развертывания и управления приложениями, оперирующими со сложными данными.

Сервер Oracle9i ™ с объектно-реляционной технологией может быть "подогнан" разработчиками для создания их собственных специфических для области применения (application-domain-specific) типов данных. СУБД Oracle9i ™ была расширена для поддержки полных возможностей объектного моделирования, включая наследование (inheritance) и многоуровневые коллекции (multi-level collections), а также эволюции типов данных (type evolution). Например, можно создать новые типы данных, представляющие клиентов (customers), финансовые портфели (financial portfolios), фотографии и телефонные сети – и, тем самым, обеспечить, чтобы ваши приложения баз данных оперировали абстракциями, свойственными вашей предметной области (application domain). Кроме того, весьма желательно интегрировать эти новые типы с сервером баз данных настолько тесно, насколько это возможно, чтобы они обрабатывались наравне со встроенными типами данных, такими, как NUMBER или VARCHAR.

Рис. 0. Объектно-реляционная архитектура СУБД Oracle9i.

И, наконец, СУБД Oracle9i ™ предлагает большой набор интерфейсов прикладного программирования (API), реализующих связывания для различных языков. Для Java и PL/SQL предлагается "прямая" (native) поддержка внутри самой СУБД с тесной интеграцией между системой объектно-реляционных типов и хранимыми процедурами, написанными на Java или PL/SQL. Так как XML быстро становится стандартом для обмена информацией, то используя объектно-реляционную среду, можно "напрямую" хранить данные XML и эффективно манипулировать ими, индексировать их и эффективно обрабатывать запросы. Можно также поддерживать отображение между типами языка SQL и клиентских языков программирования (Java и C++), чтобы обеспечить "бесшовный" доступ к экземплярам типов данных SQL из приложений, написанных на Java или C++.

 Объектно-ориентированная разработка приложений

Со времени своего появления в 1960-х годах объектно-ориентированная технология становилась все более зрелой. Поскольку появились индустриальные стандарты, обеспечившие ее повсеместное принятие, разработка объектно-ориентированных приложений стала в настоящее время доминирующей в области ИТ. Наиболее важные из этих стандартов:

  • UML (Unified Modeling Language) – унифицированный язык моделирования для объектно-ориентированного анализа и проектирования (Прим. ред. Общие сведения о языке UML можно найти, например, в статье [1]. В ней также приведен список рекомендуемой литературы по этому языку.);
  • стандарт объектно-реляционных баз данных SQL:1999 (Прим. ред. Более подробно со стандартом SQL:1999 можно ознакомиться по статьям [2] и [3]. О дальнейшем развитии стандарта SQL читайте [12]);
  • стандарты языков объектно-ориентированного программирования Java и C++. Прежде чем приступить к рассмотрению реализации стандарта SQL:1999 в СУБД Oracle9i и соответствующих ему объектно-ориентированных интерфейсов прикладного программирования для Java и C++, необходимо сначала обсудить UML.

Рис. 1. UML-диаграмма приложения "Оперативный каталог" (Online Catalog).

Надписи на рисунке:

  • Inheritance – наследование (Прим.ред.: на рис. опечатка: "inheritanc" вместо "inheritance");
  • Aggregation ­– агрегирование;
  • Navigable Association ­– навигационная ассоциация.

Спецификации UML – это сплав лучших результатов, достигнутых в индустрии объектно- ориентированных технологий. Текущей является версия 1.4 этих спецификаций от Object Management Group (OMG), международной организации, разрабатывающей стандарты объектных технологий. (Прим. ред. В июне 2003 г. консорциум OMG принял новую версию этого стандарта – UML 2.0.) UML определяет стандартные конструкции для описания объектно-ориентированного программного обеспечения как объектной модели. Например, UML-диаграмма на рис. 1 изображает объектную модель приложения "Оперативный каталог", которое корпорация Oracle разработала как часть нового проекта Common Schema (общая схема). В этой объектной модели есть несколько классов (например, Category, leafCategory). Каждый из этих классов обладает рядом атрибутов и операций. Например, класс Category обладает атрибутами category_name и category_description, а также операциями add() и remove().

Классы также связаны между собой различными связями. Например:

  • класс leafCategory наследует от класса Category;
  • класс compositeCategory может агрегировать объекты класса Category;
  • а класс leafCategory имеет навигационную ассоциацию с классом Product_Information (то есть, классы leafCategory ссылаются на список объектов Product_Information).

Как только приложение проанализировано и спроектировано с применением UML, результирующая объектная модель может быть отображена в целевую реализацию с заданным языком программирования и сохраняемостью данных. После этого реализованное приложение готово для развертывания в рамках заданной целевой архитектуры. Преимущества объектно-реляционной технологии СУБД Oracle9i становятся очевидными по мере развертывания такого объектно-ориентированного процесса разработки. Как описано в следующем разделе, система объектных типов Oracle9i позволяет осуществлять отображение "один-к-одному" конструкций объектной модели UML в соответствующую объектно-реляционную схему.

 Система объектных типов СУБД Oracle9i

Исторически приложения разрабатывались с прицелом на доступ и модификацию корпоративных данных, которые хранятся в таблицах, составленных из "родных" для SQL типов данных, таких, как INTEGER, NUMBER, DATE и CHAR. Но, начиная с СУБД Oracle8, поддерживаются не только эти, но также и новые объектные типы данных, которые теперь являются частью действующего стандарта ANSI SQL:99. В этом разделе дан краткий обзор основных характеристик системы объектно-реляционных типов Oracle.

 Объектные типы

Корпорация Oracle расширила SQL (как DDL, так и DML), чтобы позволить пользователям:

  • определять свои собственные типы (которые представляют их бизнес-объекты) и связи (например, наследование и агрегирование) между этими определяемыми пользователями типами;
  • хранить их экземпляры (то есть, объекты) в базе данных (либо в столбцах таблиц, либо как сами таблицы);
  • запрашивать, вставлять и изменять эти экземпляры.

Бизнес-объект:

  • может содержаться внутри другого бизнес-объекта;
  • на него может ссылаться другой объект (используя конструкцию, называемую REF);
  • к нему можно получить доступ;
  • с ним можно манипулировать как с коллекциями (collections) или наборами (sets), используя структуры, называемые массивами переменной длины (VARRAYS) и вложенными таблицами (Nested Tables).

Пользователи могут определять операции над бизнес-объектами как методы (methods) определяемых пользователями типов. Методы могут быть реализованы как хранимые процедуры на языках Java или PL/SQL. Объекты также обладают глобально уникальными идентификаторами, называемыми объектными идентификаторами (Object ID), которые могут быть использованы для поддержки ссылок между объектами.

СУБД Oracle9i позволяет пользователям рассматривать объектные данные как реляционные. Например, пользователи могут использовать SQL для запросов объектных данных точно так же, как для запросов реляционных данных. Пользователи могут получать доступ к объекту, используя операторы SQL DML, к его атрибутам и методам, используя расширенные выражения путей (например, объект.атрибут). Они могут также использовать SQL для выполнения явных соединений (explicit joins) объектов в таблицах. Кроме того, Oracle9i позволяет пользователям выполнять неявные соединения (implicit joins) объектов, путем обхода (traversing) или навигации по ссылкам от одного объекта к другому. Объекты можно индексировать, применяя методы MAP или ORDER для преобразования их в скалярные значения, которые затем могут быть индексированы.

Объектно-реляционные конструкции СУБД Oracle9i весьма близки к реляционным, которые хорошо знакомы пользователям СУБД Oracle. Например, ссылка REF очень похожа на внешний (foreign) ключ, методы – это хранимые процедуры (которые могут быть написаны на языках Java, PL/SQL или C/C++), модели безопасности и транзакций, оперирующие с объектными типами, являются точно такими же, как и модели, определенные для реляционных таблиц.

Рис. 2. Определяемые пользователями объектные типы позволяют использовать конструкции предметной области.

Рассматриваемая система объектных типов существенно повышает уровень абстракции, на котором пишутся программы для работы с базами данных. Вместо оперирования типами данных NUMBER, CHAR и т.д., эти программы могут работать с конструкциями предметной области, такими, как Customer, Portfolio или Money. Из этого проистекают многие преимущества, не последним из которых является лучшее моделирование вашего бизнеса в базе данных.

  Объектные представления

С другой стороны, СУБД Oracle9i также позволяет пользователю рассматривать реляционные данные как объекты. Объектные представления (Object Views) позволяют синтезировать бизнес-объект из данных, которые продолжают храниться в реляционных таблицах. А именно, можно:

  • определять объекты, которые вы можете использовать в своих приложениях, без миграции каких-либо существующих реляционных данных;
  • различными способами комбинировать объекты, разработанные для одного приложения, для использования их другими приложениями. Объектные представления обладают примерно той же функциональностью, что и объектные таблицы. Они могут обладать методами, принадлежать коллекциям, ссылаться друг на друга, обладать свойством индивидуальности объектов (object identity), к ним можно получать доступ как через SQL, так и навигационным путем (path traversal). Более того, корпорация Oracle расширила механизм представлений, чтобы использовать специальные триггеры INSTEAD OF для поддержки полностью обновляемых представлений.

Рис. 3. Объектные представления добавляют гибкость при доступе к унаследованным данным.

Надписи на рисунке:

  • Relational Applications – реляционные приложения;
  • Object Applications – объектные приложения;
  • Object Views – объектные представления;
  • Relational Data – реляционные данные;
  • Objects – объекты;
  • One Database – одна база данных.
 Наследование

Наследование типов (Type inheritance) – это фундаментальная концепция в любой объектно-ориентированной системе. Наследование типов позволяет совместно использовать похожие свойства различных типов, а также расширять их характеристики.

Во многих объектно-ориентированных приложениях объекты организованы в типы, а типы – в иерархии типов. Эмпирически вполне достаточно организовать иерархии типов в виде набора деревьев. Тем самым, простого наследования достаточно для поддержки организации типов в большинстве приложений. Java – это объектно-ориентированный язык программирования, поддерживающий простое наследование. С помощью простого наследования тип может расширять один супертип (наследовать от одного супертипа). Такой тип, называемый подтипом (subtype), наследует все атрибуты и методы своего супертипа (supertype). Подтипу можно также добавлять новые атрибуты и методы или переопределять унаследованные методы. СУБД Oracle поддерживает модель простого наследования. А это очень близко соответствует стандарту ANSI SQL:99. (Прим. ред. Этот стандарт ANSI принят одновременно с официальным международным стандартом ISO/IEC SQL:1999 и тождественен ему.) В следующих нескольких разделах поддержка наследования типов в Oracle обсуждается более подробно.

Иерархия типов

Корневой тип иерархии создается с помощью оператора CREATE TYPE, в котором должен быть указано ключевое слово NOT FINAL (нетерминальный).

CREATE TYPE Person_t AS OBJECT(
name VARCHAR2(100),
dob DATE,
MEMBER FUNCTION age() RETURN number,
MEMBER FUNCTION print() RETURN varchar2) NOT FINAL;

Под нетерминальным типом может быть создан подтип. Он наследует все атрибуты и методы от своего супертипа. В нем можно добавить новые атрибуты и методы и/или переопределить унаследованные методы.

CREATE TYPE Employee_t UNDER Person_t(
salary NUMBER,
bonus NUMBER,
MEMBER FUNCTION wages() RETURN number,
OVERRIDING MEMBER FUNCTION print() RETURN varchar2);

В Oracle Common Schema имеется более сложный пример иерархии наследования типов. Как показано на рис. 1, класс Category и его подклассы моделируются элегантной, но простой конструкцией, представляющей иерархии "часть-целое" (part-whole) с древовидной структурой. Этот пример более детально раскрывает основные преимущества системы объектных типов Oracle9i при сохранении всех аспектов объектной модели приложения.

create type category_typ as object
( category_name varchar2(50)
, category_description varchar2(1000)
, category_id number(2)
)
NOT INSTANTIABLE NOT FINAL;
create type subcategory_ref_list_typ as table of ref
category_typ;
create type product_ref_list_typ as table of number(6);
/
create type corporate_customer_typ under customer_typ
( account_mgr_id number(6)
);
create type leaf_category_typ under category_typ
(
product_ref_list product_ref_list_typ
);
create type composite_category_typ under category_typ
(
subcategory_ref_list subcategory_ref_list_typ
)
NOT FINAL;
create type catalog_typ under composite_category_typ
(
member function getCatalogName return varchar2
);

Иерархия представлений

Объектное представление может быть создано как подпредставление другого объектного представления, создавая тем самым иерархию представлений. Преимущества иерархии представлений вытекают из того факта, что строки иерархии объектных представлений включают все строки их подпредставлений. Благодаря этому свойству, можно запрашивать объекты типов, принадлежащих к некоторой иерархии, осмысленным образом.

CREATE VIEW Persons OF Person_t WITH OBJECT ID (name) AS
SELECT name, dob FROM r_persons;
CREATE VIEW Employees OF Employee_t UNDER Persons AS
SELECT name, dob, salary, bonus from r_employees;

Запрос к представлению Persons выберет всех лиц, включая служащих.

SELECT VALUE(p) FROM Persons p;

Oracle предоставляет возможность выполнения новых операторов для определения наиболее специализированного типа (most-specific-type) некоторого экземпляра объекта и преобразования объекта супертипа Т в объект подтипа T (если это возможно).

(Прим. ред. Связь "тип-подтип" в объектных моделях данных позволяет моделировать иерархию двойственных видов абстракций типов сущностей предметной области – абстракции обобщения (generalization) и специализации (specialization). При этом супертип является обобщением своего подтипа, а подтип – специализацией супертипа. Естественно назвать подтип нижнего уровня иерархии "наиболее специализированным типом" или "самым специализированным типом". Важно заметить, что это свойство является относительным – оно имеет место относительно заданной иерархии типов.)

Например, следующий запрос выбирает всех персон с заданной датой рождения (date of birth, dob), которые являются служащими.

SELECT TREAT(VALUE(p) AS Employee_t) FROM Persons p
WHERE dob = '01-01-1970' AND VALUE(p) IS OF(Employee_t);

Некоторые другие свойства иерархии представлений:

  • тип суперпредставления должен быть непосредственным супертипом для типа создаваемого объектного представления;
  • подпредставление наследует объектный идентификатор OID от своего суперпредставления.

Свойство подстановочности

Одно из наиболее значительных преимуществ наследования – это подстановочность (substitutability). Подстановочность – это основная характеристика полиформизма типов (type polymorphism), которая позволяет использовать значение некоторого подтипа там, где ожидается значение супертипа (например, параметры метода), причем в этом случае не требуется предварительных конкретных знаний о подтипе. (Прим. ред. Более подробно о подстановочности см. например [4].). В этой статье, к сожалению, уже нельзя исправить термин "подставляемость" на общеупотребительный термин "подстановочность".)

Подстановочность экземпляра (Instance substitutability) – это возможность использования значения некоторого объекта подтипа в контексте, объявленном в терминах супертипа. Подстановочность ссылки REF – это возможность использовать ссылку REF на подтип в контексте, объявленном в терминах ссылки на супертип. По умолчанию, объектные столбцы и объектные таблицы обладают свойством подстановочности. Базовая модель хранения – это единая плоская таблица со столбцами, которые соответствуют всем атрибутам всех возможных подтипов. В столбце идентификатора типа (type id column) хранится информация о наиболее специализированном типе данного типа.

CREATE TABLE dept (id NUMBER, mgr Person_t);
INSERT INTO dept VALUES(1, Employee_t(…));

Динамическая диспетчеризация методов (Dynamic Method Dispatch)

Метод – это процедура или функция, которая является частью определения объектного типа. Методы могут выполняться в среде исполнения Oracle9i или передаваться для выполнения в другую среду. Методы могут быть реализованы с применением ряда языков, в том числе – PL/SQL, C/C++ и Java.

Подтип может переопределять любой из нетерминальных методов экземпляра (non-final member methods), определенных для его супертипа, и предоставлять другую реализацию. Когда вызывается метод некоторого экземпляра объекта, осуществляется диспетчеризация метода и вызов конкретной реализации в зависимости от наиболее специализированного типа данного экземпляра. СУБД Oracle поддерживает возможность мультиязыковой динамической диспетчеризации методов. Когда на некотором экземпляре объекта вызывается метод, осуществляется его диспетчеризация и вызов конкретной его реализации, основанной на наиболее специализированном типе данного экземпляра.

 Типы-коллекции

Коллекции – это типы данных SQL, составляющие элементы которых представляют собой множественные элементы. Каждый элемент или значение для коллекции обладает тем же самым подстановочным типом данных. В Oracle предусмотрено два типа коллекций – массивы переменной длины (Varrays) и вложенные таблицы (Nested Tables).

Массив переменной длины содержит переменное число упорядоченных элементов. Типы данных VARRAY могут быть использованы для столбцов таблиц или атрибутов объектных типов.

С помощью Oracle SQL можно создавать указанные выше типы таблиц. Они могут использоваться как вложенные таблицы для реализации семантики неупорядоченной коллекции. Так же как и VARRAY, типы вложенных таблиц могут быть использованы для столбцов таблиц или атрибутов объектных типов.

Многоуровневые коллекции

СУБД Oracle9i поддерживает множественные уровни вложенности коллекций, например, вложенные таблицы или массивы переменной длины, встроенные в некоторую вложенную таблицу или массив переменной длины. В Oracle Common Schema есть отличный пример, показывающий преимущества поддержки многоуровневых коллекций. В UML-диаграмме на рис. 1, класс Customer показан как имеющий агрегат класса Order, который, в свою очередь, имеет агрегат класса Order_Item. Следующий пример показывает, как отобразить эти конструкции, создавая тип customer_typ, который содержит коллекцию вложенных таблиц типа order_typ, который, в свою очередь, включает коллекцию вложенных таблиц типа order_item_typ.

create type order_item_typ as object
( order_id number(12)
, line_item_id number(3)
, unit_price number(8,2)
, quantity number(8)
, product_ref REF product_information_typ
) ;
create type order_item_list_typ as table of order_item_typ;
create type customer_typ;
create type order_typ as object
( order_id number(12)
, order_mode varchar2(8)
, customer_ref REF customer_typ
, order_status number(2)
, order_total number(8,2)
, sales_rep_id number(6)
, order_item_list order_item_list_typ
) ;
create type order_list_typ as table of order_typ;
create or replace type customer_typ as object
( customer_id number(6)
, cust_first_name varchar2(20)
, cust_last_name varchar2(20)
, cust_address cust_address_typ
, phone_numbers phone_list_typ
, nls_language varchar2(3)
, nls_territory varchar2(30)
, credit_limit number(9,2)
, cust_email varchar2(30)
, cust_orders order_list_typ
);

В том же самом примере из Oracle Common Schema создается объектное представление для многоуровневых коллекций.

create or replace view oc_customers of customer_typ
with object oid (customer_id)
as select c.customer_id, c.cust_first_name,
c.cust_last_name, c.cust_address,
c.phone_numbers,c.nls_language,
c.nls_territory,c.credit_limit,
c.cust_email,
cast(multiset(select o.order_id, o.order_mode,
make_ref(oc_customers,o.customer_id),
o.order_status,
o.order_total,o.sales_rep_id,
cast(multiset(select
l.order_id,l.line_item_id,
l.unit_price,l.quantity,
make_ref(oc_product_information,
l.product_id) from order_items l
where o.order_id = l.order_id)
as order_item_list_typ)
from orders o
where c.customer_id = o.customer_id)
as order_list_typ)
from customers c;
 Ссылочные типы

Если вы создаете объектную таблицу или объектное представление в СУБД Oracle9i, то можно получить ссылку (или указатель базы данных, pointer) на соответствующий объект-строку (row object). Ссылки важны для моделирования связей и навигации по экземплярам объектов, в частности, в приложениях на стороне клиента.

 Большие объекты

СУБД Oracle9i предоставляет типы LOB (large object, большой объект) для решения проблем хранения изображений, видеоклипов, документов и других видов неструктурированных данных. Большие объекты хранятся таким образом, чтобы было оптимизировано использование пространства памяти и обеспечен эффективный доступ к ним. Конкретнее, большие объекты состоят из указателей (locators) и связанных с ними двоичных и/или символьных данных. Указатели этих объектов хранятся в строках таблиц вместе со значениями других столбцов. Если применяются внутренние большие объекты (BLOB, CLOB и NCLOB), их данные размещаются в отдельной области хранения. Для внешних же объектов (BFILE) их данные хранятся вне базы данных в файлах операционной системы.

 Определяемые пользователями конструкторы

Определяемые пользователями конструкторы исключают проблемы с конструктором значений атрибутов (attribute-value constructor), так как они не должны явно устанавливать значение для каждого атрибута типа. Определяемый пользователем конструктор может иметь любое число параметров любого типа, которые не должны в обязательном порядке непосредственно отображаться в атрибуты типов. В определении конструктора можно устанавливать любые подходящие значения атрибутов. Атрибутам, для которых значения не заданы, будет установлено значение NULL.

 Синонимы типов

Точно так, как можно создавать синонимы таблиц, представлений и других различных объектов схемы, можно создавать синонимы определяемых пользователями типов. Синонимы этих типов обладают теми же преимуществами, что и синонимы других объектов схемы: они предоставляют независимый от местонахождения способ ссылки на объекты схемы. Приложение, использующее синонимы общедоступных типов, можно развернуть без какого-либо изменения любой схемы базы данных. При этом не нужно квалифицировать имя типа именем схемы, в которой этот тип был определен.

 Эволюция типов

Использование типа позволяет пользователю развивать бизнес-логику, зафиксированную в поведении этого типа. Эволюция типов– это механизм, который позволяет пользователю изменять тип и распространять эти изменения на другие объекты схемы, которые ссылаются на модифицированный тип. К числу объектов схемы, которые могут ссылаться на тип, относятся другие типы, подтипы, объекты-строки, объекты-столбцы (column objects), программные блоки (пакеты, функции, процедуры), представления, функциональные индексы и триггеры.

Поддерживаемые операции эволюции типов:

  1. Операции над атрибутами типов:
    • добавление атрибута для типа;
    • удаление атрибута типа;
    • модификация типа атрибута (увеличение его длины, точности или масштаба).
  2. Операции над методами типов:
    • добавление метода для типа;
    • удаление метода типа.
  3. Изменение свойств INSTANTIABLE (абстрактный/не абстрактный тип – не допускает или допускает непосредственное порождение экземпляров объектов) и FINAL (терминальный/нетерминальный тип – нельзя создавать подтипы или можно) объектного типа SQL.
  4. Поддержка явного распространения изменений типа на зависимые от него типы и таблицы.

Эти изменения при эволюции типов являются либо структурными (structural), либо неструктурными (non-structural). Структурные изменения воздействуют на состояние объекта; это, например, добавление или удаление атрибута. Неструктурные изменения не затрагивают состояния объекта. Например, переименование атрибута или добавление метода.

Рассмотрим следующий пример:

CREATE TYPE address_t AS OBJECT (
street VARCHAR(100),
zip_code NUMBER);
CREATE TYPE person_t AS OBJECT (
first_name VARCHAR(50).
last_name VARCHAR(50),
age NUMBER,
address address_t);
CREATE TABLE person_tab OF person_t;

В этом примере таблица person_tab создается со столбцом для каждого атрибута типа person_t, а также с одним столбцом для каждого атрибута адреса (тип address_t). Рассмотрим следующий пример изменения типа:

ALTER TYPE address_t
ADD ATTRIBUTE (country NVARCHAR(100), int_postal_code
NVARCHAR(20)) CASCADE;

Результатом этого изменения будет добавление двух столбцов к таблице person_tab, соответствующих только что добавленным атрибутам. Ключевое слово CASCADE распространяет изменения этого типа на зависимые типы и таблицы.

Связывания для языков программирования

Полная поддержка объектно-реляционной системы типов Oracle доступна в связываниях для ряда языков программирования, включая PL/SQL, Java и C/C++. К экземплярам типов можно получить доступ, и с ними можно манипулировать через интерфейсы прикладного программирования, такие, как JDBC (Java DataBase Connectivity) и OCCI (Oracle C++ Call Interface). Корпорация Oracle предоставляет также инструменты, подобные утилите JPublisher и транслятору объектных типов Object Type Translator (OTT), для отображения иерархий объектных типов в языки Java и C++. Кроме того, в средах этих языков также поддерживается подстановочность экземпляров и ссылок REF.

(Прим. ред. О связывании для языков программирования (language binding) в объектных СУБД, соответствующих стандарту объектных баз данных ODMG, см. например, [5]. О спецификациях связывания SQL для объектных языков программирования, принятых в октябре 2000 г., см. например, [6].)

Отображение объектов между SQL и Java
Интерфейсы JDBC и SQLJ, утилита JPub

Объектно-реляционные возможности предоставляют более естественный и продуктивный способ для поддержания согласованной структуры набора Java-классов на уровне приложения и модели данных на уровне хранения данных. В СУБД Oracle объектно-реляционные возможности тесно интегрированы со средой Java с помощью стандартных интерфейсов прикладного программирования JDBC и SQLJ. Объектные типы SQL могут быть отображены в Java-классы. Утилита JPublisher (JPub) автоматически генерирует файлы для JDBC или SQLJ с определениями Java-классов, реализующих эти отображения. Каждый сгенерированный Java-класс содержит определенные для него методы чтения состояния объектов с сервера базы данных и записи состояния на сервер. В свою очередь, Java-приложения могут использовать эти сгенерированные Java-классы для сохранения объектов в базе данных и их выборки из базы.

(Прим. ред. О стандарте JDBC см. например, [7]. О спецификациях SQLJ см. например, [8].)

Далее представлены фрагменты кода Java-класса, сгенерированные утилитой JPub.

// Создать Java-класс, который реализует интерфейс SQLData

public class JPurchaseOrder implements SQLData

{

public void readSQL (SQLInput stream, String typeName)

throws SQLException {…}

public void writeSQL (SQLOutput stream)

throws SQLException {…}

}

 

Этот Java-класс JPurchaseOrder может быть далее использован в следующей Java-программе для выборки объектов из базы данных.

// Экземпляры объекта можно рассматривать как Java-объекты

ResultSet rs = stmt.executeQuery("select value(p) from

purchase_order_tab p");

rs.next();

JPurchaseOrder jp = (JPurchaseOrder) rs.getObject(1);

String streetName = jp.shipAddr.street;

Объектные типы в SQLJ

В СУБД Oracle9i введена возможность "бесшовно" отображать заданный Java-класс в некоторый объект SQL. Согласно части 2 стандарта SQLJ, SQLJ Object Types (Объектные типы SQLJ), определяется отображение между некоторым объектом SQL и соответствующей реализацией Java-класса. Спецификации SQLJ Object Types находятся в процессе стандартизации в качестве расширения стандарта SQL:99. (Прим. ред. В июле 2002 г. указанное расширение стандарта SQL:1999 было принято в качестве части 13 этого стандарта под названием SQL/JRT, где аббревиатура JRT расшифровывается как Java Routines and Types.)

Рассмотрим следующий пример:

CREATE TYPE ADDRESS_T AS OBJECT EXTERNAL NAME "Address"
LANGUAGE JAVA USING SQLDATA (
STREET VARCHAR(50) EXTERNAL NAME "street",
ZIP_CODE VARCHAR(10) EXTERNAL NAME "zip",
STATIC FUNCTION GET_CITY (VARCHAR zip) RETURN VARCHAR
EXTERNAL NAME "get_city(java.lang.String)
RETURN java.lang.String",
STATIC FUNCTION GET_STATE (VARCHAR zip) RETURN VARCHAR
EXTERNAL NAME "get_state(java.lang.String)
RETURN java.lang.String",
MEMBER FUNCTION CITY RETURN VARCHAR EXTERNAL NAME "getCity()
RETURN java.lang.String",
MEMBER FUNCTION STATE RETURN VARCHAR EXTERNAL NAME
"getState() RETURN java.lang.String");

В данном примере в операторе CREATE TYPE предложение EXTERNAL NAME специфицирует внешнее имя, которое определяет Java-класс, используемый в реализации. Предложение USING специфицирует интерфейс, используемый для доступа к состоянию объекта.

Для каждого атрибута данного объектного типа необязательное предложение EXTERNAL NAME задает имя соответствующего Java-поля. Для методов предложение EXTERNAL NAME определяет имя соответствующей Java-функции и ее сигнатуру.

Приведенная выше информация об отображении хранится как часть метаданных данного типа. Она обеспечивает "бесшовный" доступ к объектам SQL из Java через JDBC, не требуя от пользователя явного применения интерфейса SQLData или регистрации этого класса с помощью отображения типов Java (Java typemap).

Иерархия объектных типов в SQLJ может быть отображена в иерархию наследования Java. Диспетчеризация методов, включая переопределение этих типов, осуществляется в процессе исполнения Java-программы.

Отображение объектов SQL в C++

Интерфейс уровня вызовов 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();
Отображение объектов SQL в XML

Расширяемый язык разметки XML (Extensible Markup Language) – это метаязык, который быстро становится стандартом де-факто для обмена данными между приложениями и областями бизнеса. (Прим. ред. О языке XML см. например, [9-11].) Язык определения схемы для XML-документов, XML Schema, специфицирует структуру XML-документа в терминах типов данных и композицию каждого элемента в этом документе. СУБД Oracle поддерживает эффективные и гибкие механизмы для отображения объектов SQL в XML, и наоборот.

Oracle XML DB

В СУБД Oracle9i Release 2 введена опция Oracle9i XML Database (Oracle XML DB). Она расширяет СУБД Oracle средствами поддержки XML, делая XML-данные и модели содержимого непосредственно доступными приложениям Oracle9i. Oracle XML DB, высокопроизводительная технология хранения и выборки XML-данных, предоставляется в сервере базы данных Oracle9i Release 2. Она основана на модели данных W3C XML (Прим. ред. В спецификации стандарта XML и других стандартов W3C, основанных на этом языке, часто употребляется термин “модель данных XML”. Однако при этом под “моделью данных” понимается лишь структурный аспект этого понятия. Язык XML не определяет полной модели данных. В частности, в нем не предлагаются какие-либо средства манипулирования XML-данными. Он выполняет лишь функции языка определения данных.) и обеспечивает преимущества двух технологий:

  • объектно-реляционной технологии баз данных;
  • XML-технологии.

Oracle XML DB – это "чистая" база данных XML. Она предоставляет инфраструктуру для управления данными, независимую от хранения, содержимого и языков программирования. Хотя она тесно интегрирована с SQL-машиной СУБД Oracle, в ней воплощены концепции, никогда ранее не реализованные в реляционных СУБД. Например, объектная модель XML-документов – XML Document Object Model (DOM) – встроена в ядро СУБД Oracle, так что большинство операций с XML-данными может быть выполнено как часть традиционной обработки данных в базе данных. А это позволяет избежать двухшаговой модели – извлечь и обработать.

Благодаря тесной интеграции с объектно-реляционной технологией Oracle и языком PL/SQL, Oracle XML DB одновременно демонстрирует мощность объектно-реляционных баз данных и гибкость XML.

Генерация XML

Пакет DBMS_XMLGEN может принять любой SQL-запрос и отобразить его результаты в XML. Тем самым, весь результирующий набор, возвращенный этим запросом, преобразуется в единый XML-документ. Этот пакет имеет несколько параметров для управления различными аспектами генерации XML, включая генерацию схемы XML Schema, ассоциированной с этим документом (аналогично описанию функциональности), и ограничение числа выбранных строк. Например, следующий фрагмент кода представляет результаты запроса в форме XML-документа, как показано ниже.

qryCtx := dbms_xmlgen.getContextHandle("select * from
scott.emp");
result := dbms_xmlgen.getXMLClob(qryCtx);
<?xml version="1.0" encoding="SHIFT_JIS"?>
<ROWSET>
<ROW>
<EMPNO>30</EMPNO>
<ENAME>Scott</ENAME>
<SALARY>20000</SALARY>
</ROW>
<ROW>
<EMPNO>30</EMPNO>
<ENAME>Mary</ENAME>
<AGE>40</AGE>
</ROW>
</ROWSET>

Для реляционных данных результаты представляют собой плоский XML-документ без вложенности. Чтобы получить вложенные XML-структуры, можно использовать объектно-реляционные данные. Объект отображается в XML-элемент с атрибутами отображения этого объекта на подэлементы родительского элемента. Экземпляр коллекции также отображается в XML-элемент с элементами коллекции, появляющимися как повторяющиеся экземпляры подэлементов.

Хранение XML-документов

Для облегчения "чистого" (native) хранения и доступа к XML-документам был введен новый тип данных, называемый XMLType. Пользователи могут создавать экземпляры и столбцы этого типа данных и использовать методы типа для извлечения, обхода и трансформации XML-документов.

В столбце типа XMLType можно хранить документы либо в целостном виде (как данные типа CLOB), либо в декомпозированном объектно-реляционном виде. Этот тип позволяет выполнять операции запросов XML-документов: extract() – обход документа и извлечение его фрагмента на основе выражения пути и existsNode() – проверка существования узла, удовлетворяющего заданному условию. Пользователь может также определить текстовый индекс Oracle interMedia по этому столбцу и запрашивать этот XML-документ с применением операции Contains и других операций для работы с текстом.

-- выбрать имя заказчика (custname) из всех сообщений, которые
-- являются срочными(urgent) и имеют в PO заказчика (customer)
SELECT extract(e.msgVal, "/po/cust/custname")
FROM message_tab e
WHERE CONTAINS(e.msgVal, "URGENT") > 0
AND existsNode(e.msgVal,"//po/cust") > 0;

Поддержка объектно-реляционной технологии в JDeveloper

Корпорация Oracle предоставляет мощные инструментальные средства для поддержки объектно-ориентированной разработки приложений. Для Java-разработчиков в среде JDeveloper предлагается два способа интегрированной поддержки разработки приложений, которые используют объектно-реляционную технологию Oracle. В первом случае для отображения доменов в объектные типы Oracle9i и объектов-сущностей (entity objects) в объектные таблицы и объектные представления используется интегрированная среда Oracle Business Components for Java (бизнес-компоненты Oracle для среды Java). Объекты-сущности могут быть развернуты как компоненты Enterprise JavaBeans (EJB) с применением механизма сохраняемости, управляемой контейнером (CMP, Container Managed Persistence). Во втором случае для генерации Java-классов из объектных типов Oracle9i используется мастер JPublisher. Разработчики используют Java-классы, сгенерированные мастером JPublisher, для доступа и манипулирования объектами-строками и объектами-столбцами Oracle9i.

Среда Oracle Business Components for Java

Среда Oracle Business Components for Java отображает ее домены в объектные типы Oracle9i, а объекты-сущности – в объектные таблицы и объектные представления. Мастер JDeveloper может создавать объекты-сущности из объектных таблиц Oracle9i или объектных представлений. Объект-сущность может быть развернут как EJB с применением механизма сохраняемости, управляемой контейнером – CMP.

Механизм сохраняемости, управляемой контейнером с применением объектов Oracle9i

СУБД Oracle9i управляет сохраняемостью компонентов-сущностей EJB, используя таблицы базы данных. Каждый экземпляр компонента-сущности соответствует строке в таблице, и каждое CMP-поле соответствует столбцу в этой таблице. Для класса компонента-сущности также нужен первичный ключ, соответствующий одному или нескольким столбцам этой таблицы, который позволяет осуществлять выборку экземпляров с помощью метода findByPrimaryKey().

Два компонента Business Components for Java соответствуют этим таблицам:

  1. Объект развертывания EJB/9i (deployment object), который очень похож на стандартный объект-сущность и обозначает таблицу, которая управляет сохраняемостью.
  2. Объект-представление (view object), который выбирает релевантные столбцы этой таблицы и присваивает им псевдонимы EJB-полей.

CMP-компоненты могут также использовать классы других бизнес-компонентов: домены, которые позволяют EJB-полям базироваться на объектных типах Oracle, и вторичные объекты-представления, соответствующие методам механизма поиска EJB.

Отображение объектных типов Oracle в CMP-поля

Таблица базы данных, управляющая CMP-сохраняемостью, может включать столбцы, содержащие объектные типы Oracle. В JDeveloper мастер Domain Wizard помогает создавать объекты-домены из объектных типов Oracle.

Мастер JPublisher

В состав JDeveloper входит интерфейс Database Browser (браузер базы данных), который позволяет разработчикам получать доступ к содержимому схем своих баз данных и находить объекты Oracle9i. С помощью этого интерфейса можно запустить мастер JPublisher для генерации классов-адаптеров Java (Java wrapper classes) для объектов Oracle9i. Мастер JPublisher облегчает использование объектов Oracle9i в Java-программах, автоматически генерируя определения соответствующих Java-классов. Сгенерированные мастером JPublisher классы-адаптеры включают методы для преобразования данных из SQL в Java и из Java в SQL, а также методы для чтения и записи значений атрибутов этих объектов. Мастер JPublisher повышает производительность труда разработчиков, обеспечивая в то же время гибкость для расширения сгенерированных классов с целью удовлетворения потребностей заказчиков.

После завершения разработки Java-приложения с использованием мастера JDeveloper оно может быть развернуто в различных целевых архитектурах с помощью сервера базы данных Oracle9i и сервера приложений Oracle9i, которые являются универсальными программными платформами для приложений с высокими требованиями.

Развертывание объектно-ориентированных приложений на интернет-платформах Oracle

Завершив разработку приложения с помощью объектно-реляционной технологии Oracle9i, можно использовать ряд способов его развертывания и управления. Сервер приложений Oracle9i AS (Application Server) и сервер базы данных Oracle9i Database Server предоставляют все необходимое для развертывания и управления приложениями электронного бизнеса. Сервер Oracle9i AS и сервер базы данных Oracle9i Database Server вместе составляют простую, полную и интегрированную интернет-платформу.

  • Простота. Серверы Oracle9i AS и Oracle9i Database Server просто купить, просто инсталлировать и просто сопровождать. Все ключевые сервисы среднего звена программного обеспечения Oracle были интегрированы в Oracle9i AS, обеспечивая пользователям построение и развертывание порталов, транзакционных приложений и средств бизнес-интеллекта в едином продукте. Полный набор сервисов Oracle9i AS доступен сразу после инсталляции. Управление серверами Oracle9i AS и Oracle9i Database Server осуществляется при помощи единого инструмента управления.
  • Полнота. Интернет-платформа Oracle, включающая сервер Oracle9i для управления данными и Oracle9i AS для выполнения приложений – это полное решение для построения и развертывания любого типа веб-приложений, включая управление содержимым, OLTP-приложения, мобильные приложения, приложения бизнес-интеллекта и приложения интеграции на уровне предприятия. Серверы Oracle9i AS и Oracle9i Database Server обеспечивают масштабируемую инфраструктуру с высокой степенью доступности, которая позволяет заказчикам легко адаптироваться к растущему числу пользователей без необходимости переработки их приложений.
  • Интегрированность. Сервер Oracle9i AS – это лучший сервер приложений для сервера базы данных Oracle9i Database Server. Используя общий технологический стек, Oracle9i AS может прозрачно масштабировать сервер базы данных Oracle9i Database Server, кешируя данные и логику приложений в среднем звене. Кроме того, Oracle9i AS в значительной степени наследует свою мощную масштабируемость и свойства высокой доступности от продвинутой технологии сервера базы данных Oracle9i Database Server.

Заключение

Объектно-реляционная технология корпорации Oracle за ряд лет достигла зрелости и обеспечивает полную систему объектных типов, большой набор API, реализующих связывания для различных языков программирования, а также богатый набор утилит и инструментальных средств. Эта полная система объектных типов основана на действующем стандарте ANSI SQL:99. Корпорация Oracle оптимизировала производительность работы с объектными типами в сервере базы данных для объектно-ориентированных приложений. Интерфейсы прикладного программирования Oracle для языков Java, C/C++ и XML обеспечивают непосредственные интерфейсы для системы объектных типов сервера базы данных. Эти API с исчерпывающими функциональными возможностями поддерживают самые последние стандарты доступа к сервисам системы объектных типов базы данных. Сопутствующий богатый набор утилит для объектно-реляционных данных включает средства экспорта и импорта, тиражирования данных, SQL-загрузчик и т.д.

Кроме того, предлагается ряд средств разработки, которые поддерживают объектно-реляционную технологию Oracle для разработки объектно-ориентированного программного обеспечения, таких, как Oracle JDeveloper BC4J (Business Components for Java), и другие продукты от партнеров Oracle. Корпорация Oracle также предлагает высокопроизводительные, надежные и масштабируемые интернет-платформы для развертывания и управления приложениями, а именно, сервер базы данных Oracle9i Database Server и сервер приложений Oracle9i Application Server.

ИТ-индустрия, сталкиваясь с быстрыми изменениями, требует практичных решений проблем обработки различных типов данных в сложных приложениях. Объектно-реляционная технология Oracle решает эти проблемы с помощью наиболее развитого комплекта средств для разработки, развертывания и управления такими приложениями. Корпорация Oracle стала лидером объектно-реляционной технологии. Oracle будет продолжать удовлетворять потребности своих партнеров и заказчиков, предлагая им лучшую объектно-реляционную технологию.

Ссылки к русскому переводу

  1. Кузнецов С. Д. "Концептуальное проектирование реляционных баз данных с использованием языка UML" – http://www.citforum.ru/database/articles/umlbases.shtml
  2. Айзенберг Э. и Мелтон Д. "SQL:1999, ранее известный как SQL3" – Открытые системы, #01/1999, http://www.osp.ru/os/1999/01/52.htm
  3. Айзенберг Э. и Мелтон Д. "Cтандартизация SQL: следующие шаги" – Открытые системы, #11-12/1999, http://www.osp.ru/os/1999/11-12/080.htm
  4. Фернстайн С. "Подставляемость и преобразование объектных типов в иерархии" – Oracle Magazine/Russian Edition, июнь 2002, http://www.oracle.com/ru/oramag/june2002/index.html?dev_subst.html
  5. Калиниченко Л.А. "Стандарт систем управления объектными базами данных ODMG-93: краткий обзор и оценка состояния" – Открытые системы, #1/1996, http://www.osp.ru/dbms/1996/01/46.htm
  6. Айзенберг Э. и Мелтон Д. "Связывания для объектных языков" – Открытые системы, #04/1999, http://www.osp.ru/os/1999/04/10.htm
  7. Орлик С. "Обзор спецификации JDBC" – Системы управления базами данных, #03/1997, http://www.osp.ru/dbms/1997/03/21.htm
  8. Айзенберг Э. и Мелтон Д. "SQLJ – Часть 1: SQL-программы, использующие язык программирования JAVA" – Открытые системы, #09-10/1999, http://www.osp.ru/os/1999/09-10/061.htm
  9. Когаловский М. Р. "XML: возможности и перспективы. Ч. 1. Платформа XML и составляющие ее стандарты" – Директор информационной службы, #01/2001, http://www.osp.ru/cio/2001/01/024.htm
  10. Когаловский М. Р. "XML: возможности и перспективы. Ч. 2. Базы данных XML, семантика XML-документов, перспективы" – #02/2001, Директор информационной службы, http://www.osp.ru/cio/2001/02/016.htm
  11. Когаловский М. Р. "XML: сферы применений" – Директор информационной службы, #04/2001, http://www.osp.ru/cio/2001/04/010.htm
  12. Черняк Л. "Джим Мелтон о судьбе стандарта SQL" – Открытые системы, #06/2003, http://www.osp.ru/os/2003/06/065.htm
Бесплатный конструктор сайтов и Landing Page

Хостинг с DDoS защитой от 2.5$ + Бесплатный SSL и Домен

SSD VPS в Нидерландах под различные задачи от 2.6$

✅ Дешевый VPS-хостинг на AMD EPYC: 1vCore, 3GB DDR4, 15GB NVMe всего за €3,50!

🔥 Anti-DDoS защита 12 Тбит/с!

VPS в России, Европе и США

Бесплатная поддержка и администрирование

Оплата российскими и международными картами

🔥 VPS до 5.7 ГГц под любые задачи с AntiDDoS в 7 локациях

💸 Гифткод CITFORUM (250р на баланс) и попробуйте уже сейчас!

🛒 Скидка 15% на первый платеж (в течение 24ч)

Новости мира IT:

Архив новостей

IT-консалтинг Software Engineering Программирование СУБД Безопасность Internet Сети Операционные системы Hardware

Информация для рекламодателей PR-акции, размещение рекламы — adv@citforum.ru,
тел. +7 495 7861149
Пресс-релизы — pr@citforum.ru
Обратная связь
Информация для авторов
Rambler's Top100 TopList This Web server launched on February 24, 1997
Copyright © 1997-2000 CIT, © 2001-2019 CIT Forum
Внимание! Любой из материалов, опубликованных на этом сервере, не может быть воспроизведен в какой бы то ни было форме и какими бы то ни было средствами без письменного разрешения владельцев авторских прав. Подробнее...