Автор : Владимир Пржиялковский / Дата : 2006-10-01 02:48
Добавить или посмотреть комментарии : (0)
Рейтинг пользователей : 0

... Зажгу свечу пред каждым сундуком,
И все их отопру, и стану сам
Средь них глядеть на блещущие груды.


А. С. Пушкин. Скупой рыцарь


Аннотация

Репозитарий XML DB фактически является древовидно-организованой файловой системой внутри БД, элементами которой выступают ресурсы: каталоги (папки) и файлы. В статье показано, как можно работать с репозитарием XML DB.

Введение

XML DB, созданная в рамках БД Oracle, дает возможность следующего:
- работать с репозитарием;
- регистрировать схему XML для ее использования работе с данными XML в БД;
- создавать внутри СУБД сервлеты для доступа к БД через интернет.
Репозитарий XML DB, фактически является древовидно-организованой файловой системой внутри БД, элементами которой выступают ресурсы: каталоги (папки) и произвольные файлы. Папки можно заводить и удалять, а файлы – заводить, удалять и извлекать.
Технически ресурсы репозитария XML DB организованы в виде
документов XML. Элемент Contents каждого такого документа представляет содержание ресурса, а все остальные элементы являются метаданными, описывающими ресурс.
Средствами доступа к ресурсам, составляющим репозитарий, могут служить:
- системные таблицы RESOURCE_VIEW и PATH_VIEW
- программы на PL/SQL (пакет DBMS_XDB) и на Java
- протоколы HTTP, HTTPS, FTP, WebDAV.
Здесь рассматриваются две первые категории средств, а последняя оставлена для самостоятельных упражнений.

Доступ к ресурсам средствами SQL

Две производные таблицы (из исходных, в схеме XDB) позволяют узнать информацию о ресурсах XML DB: PATH_VIEW и RESOURCE_VIEW:
Код:
SQL> DESCRIBE resource_view
Name          Null?    Type
----------- -------- -----------------------------------------------
RES                  SYS.XMLTYPE(XMLSchema
                     "http://xmlns.oracle.com/xdb/XDBResource.xsd"
                     Element "Resource")
ANY_PATH             VARCHAR2(4000)
RESID                RAW(16)

SQL> DESCRIBE path_view
Name        Null?    Type
----------- -------- -----------------------------------------------
PATH                 VARCHAR2(1024)
RES                  SYS.XMLTYPE(XMLSchema
                     "http://xmlns.oracle.com/xdb/XDBResource.xsd"
                     Element "Resource")
LINK                 SYS.XMLTYPE
RESID                RAW(16)

Обе таблицы хранят список ресурсов с путями доступа, однако благодаря возможности определять связки (links), подобно как в файловой системе, путей доступа к одному ресурсу может оказаться несколько; их-то все и покажет таблица PATH_VIEW, в отличие от RESOURCE_VIEW.
Примеры запросов. Список ресурсов в репозитарии:
Код:
SELECT any_path FROM resource_view;

Описание первого попавшегося ресурса:
Код:
SELECT res FROM resource_view WHERE ROWNUM = 1;

Для просмотра дерева ресурсов, помимо обычных, существуют специальные функции:

UNDER_PATH
EQUALS_PATH
PATH
DEPTH

Выдать описания ресурсов, имеющихся в папке /sys/acls:
Код:
SELECT res
FROM resource_view
WHERE UNDER_PATH ( res, '/sys/acls' ) = 1;

Выдать относительные имена ресурсов, имеющихся в папке /sys/acls (в данном случае это будут имена файлов), и их полные имена:
Код:
SELECT path ( 1 ), any_path
FROM resource_view
WHERE UNDER_PATH ( res, '/sys/acls', 1 ) = 1;

Описание ресурса-папки /sys/acls:
Код:
SELECT res
FROM resource_view
WHERE EQUALS_PATH ( res, '/sys/acls' ) = 1;

Полное описание ресурса-файла /sys/acls/all_all_acl.xml:
Код:
SELECT r.res.GETCLOBVAL ( )
FROM resource_view r
WHERE EQUALS_PATH ( res, '/sys/acls/all_all_acl.xml' ) = 1;

С запросами последнего типа следует соблюдать осторожность, так как элемент Contents результирующего документа XML хранит для ресурса-файла его содержимое, а оно может оказаться очень большим.
Содержание ресурса-файла /sys/acls/all_all_acl.xml с содержимым в формате XML:
Код:
SELECT r.res.EXTRACT ( '//Contents' )
FROM resource_view r
WHERE EQUALS_PATH ( res, '/sys/acls/all_all_acl.xml' ) = 1;

Другие типы файлов могут хранить описание содержимого в элементе /Resource/Contents/text или /Resource/Contents/binary.

Работа с ресурсами в программе

Заводить, изменять свойства и удалять ресурсы в репозитарии XML DB можно с помощью пакета PL/SQL DBMS_XDB.
Примеры:
Код:
CONNECT scott/tiger
DECLARE retb BOOLEAN;
BEGIN
retb := DBMS_XDB.CREATEFOLDER ( '/public/myfolder' );
retb := DBMS_XDB.CREATERESOURCE (
  '/public/myfolder/file1.txt'
, 'First line' || CHR ( 10 ) || 'Second line'
);
retb := DBMS_XDB.CREATERESOURCE (
  '/public/myfolder/file2.xml'
, '<doc><line>First line</line><line>Second line</line></doc>'
);
END;
/

Проверка:
Код:
SQL> SELECT r.res.EXTRACT ( 'Resource/Contents' ) AS xml
  2  FROM resource_view r
  3  WHERE EQUALS_PATH ( res, '/public/myfolder/file2.xml' ) = 1;

XML
--------------------------------------------------------------
<Contents xmlns="http://xmlns.oracle.com/xdb/XDBResource.xsd">
  <doc xmlns="">
    <line>First line</line>
    <line>Second line</line>
  </doc>
</Contents>


SQL> SELECT r.res.EXTRACT ( 'Resource/Contents/text/text()' ) AS text
  2  FROM resource_view r
  3  WHERE EQUALS_PATH ( res, '/public/myfolder/file1.txt' ) = 1;

TEXT
--------------------------------------------------------------
First line
Second line

Обратите внимание, что XML DB по-разному хранит файл в зависимости от его расширения (упражнение: убедитесь, что XML DB интерпретирует содержимое, в зависимости именно от расширения файла, а не содержимого). Соответствие расширений файлов типам MIME устанавливается и выясняется в файле-ресурсе /xdbconfig.xml.
Создание связи (link):
Код:
BEGIN
DBMS_XDB.LINK (
  '/public/myfolder/file1.txt'
, '/public'
, 'myfolderfile1.txt'
);
END;
/

Проверка:
Код:
SQL> SELECT r.res.EXTRACT ( 'Resource/Contents/text/text()' ) AS text
  2  FROM resource_view r
  3  WHERE EQUALS_PATH ( res, '/public/myfolderfile1.txt' ) = 1
SQL> /

TEXT
----------------------------------------------------------------
First line
Second line

SQL> SELECT
  2    p.path AS path
  3  , p.link.extract('/LINK/ChildName/text()') AS link
  4  FROM path_view p
  5* WHERE UNDER_PATH ( p.res, '/public' ) = 1
SQL> /

PATH                                          LINK
--------------------------------------------- ---------------------
/public/myfolder                              myfolder
/public/myfolderfile1.txt                     file1.txt
/public/myfolder/file1.txt                    file1.txt
/public/myfolder/file2.xml                    file2.xml

Обратите внимание на два пути доступа в репозитарии к одному и тому же файлу (ресурсу).
Удаление:
Код:
CALL DBMS_XDB.DELETERESOURCE ( '/public/myfolderfile1.txt' );
CALL DBMS_XDB.DELETERESOURCE ( '/public/myfolder/file1.txt' );
CALL DBMS_XDB.DELETERESOURCE ( '/public/myfolder/file2.xml' );
CALL DBMS_XDB.DELETERESOURCE ( '/public/myfolder' );


Упражнение.
Проверьте реакцию XML DB на попытку удалить несуществующий файл или непустую папку.
В отличие от производных таблиц (view) словаря-стправочника в Oracle, производные таблицы RESOURCE_VIEW и PATH_VIEW обновляемы. Это позвляет, например, удалить связь также и командой DELETE, или переместить существующий ресурс в другую папку обычной операцией UPDATE:
Код:
UPDATE path_view
SET путь = новый_путь
WHERE equals_path ( res, путь ) = 1;

Пример помещения в репозитарий файла ОС:
Код:
CONNECT / AS SYSDBA
CREATE DIRECTORY courses AS 'c:crs';
GRANT READ ON DIRECTORY courses TO scott;
CONNECT scott/tiger
DECLARE retb BOOLEAN;
BEGIN
retb :=
DBMS_XDB.CREATERESOURCE (
  '/public/OracleXML.doc'
, BFILENAME ( 'COURSES', 'OracleXML.doc' )
);
END;
/

Проверка:
Код:
SQL> SELECT res AS resource_description
  2  FROM resource_view
  3  WHERE EQUALS_PATH ( res, '/public/OracleXML.doc' ) = 1
  4  ;

RESOURCE_DESCRIPTION
-----------------------------------------------------------------
<Resource xmlns="http://xmlns.oracle.com/xdb/XDBResource.xsd">
  <CreationDate>2006-09-05T12:47:57.547000</CreationDate>
  <ModificationDate>2006-09-05T12:47:57.547000</ModificationDate>
  <DisplayName>OracleXML.doc</DisplayName>
  <Language>en-US</Language>
  <CharacterSet>WINDOWS-1251</CharacterSet>
  <ContentType>application/msword</ContentType>
  <RefCount>1</RefCount>
</Resource>

Технически файлы репозитария размещаются служебных таблицах БД (документы XML) или в объектах LOB (файлы всех остальных типов). Использование формата MIME для хранения двоичных файлов не является самым экономным.

Разграничение доступа

Репозитарий XML DB использует собственную схему защиты доступа, access control list (ACL), созданной в рамках модели ACL для WebDAV ( http://greenbytes.de/tech/webdav/rfc3744.html ). Основными понятиями ACL являются:
- Участник безопасности (principal). В XML DB это пользователь БД, роль БД или пользователь/роль справочника LDAP.
- Привилегия. Может быть атомарной (atomic; например read-contents, update или dav:lock) и составной (aggregate, состоящей из других привилегий; например all, dav:all или dav:read-acl). (Полный перечень имеющихся в XML DB привилегий имеется в документации).
- Access control entry (ACE). Запись о предоставлении или запрету привилегии участнику. Делается в тексте ACL.
В XML DB имеются несколько встроенных ACL, заданных следующими ресурсами:

/sys/acls/all_all_acl.xml
/sys/acls/all_owner_acl.xml
/sys/acls/bootstrap_acl.xml
/sys/acls/ro_all_acl.xml

ACL файла /public/OracleXML.doc в программе можно узнать так:
Код:
SELECT r.res.EXTRACT ( 'Resource/ACL' ) AS text
FROM resource_view r
WHERE EQUALS_PATH ( res, '/public/OracleXML.doc' ) = 1;

Пример замены ACL ресурса:
Код:
BEGIN DBMS_XDB.SETACL (
  '/public/OracleXML.doc'
, '/sys/acls/all_all_acl.xml'
);
END;
/

Создадим в БД роль и создадим в XML DB соответствующий ей файл ACL:
Код:
CONNECT / AS SYSDBA

CREATE ROLE mygroup;

CONNECT xdb/xdb

DECLARE
aclxml VARCHAR2 ( 4000 ) :=
'
<acl description="All privileges to MYGROUP, no to others"
     xmlns="http://xmlns.oracle.com/xdb/acl.xsd" 
     xmlns:dav="DAV:"
     xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
     xsi:schemaLocation="http://xmlns.oracle.com/xdb/acl.xsd
                         http://xmlns.oracle.com/xdb/acl.xsd"
>
  <ace>
    <principal>MYGROUP</principal>
    <grant>true</grant>
    <privilege>
      <all/>
    </privilege>
  </ace>
</acl>
'
;
retb BOOLEAN;

BEGIN
retb :=
DBMS_XDB.CREATERESOURCE ( '/sys/acls/all_mygroup_acl.xml', aclxml )
;
END;
/

Защитим файл /public/OracleXML.doc созданым ACL:
Код:
CONNECT scott/tiger

BEGIN
DBMS_XDB.SETACL (
  '/public/OracleXML.doc'
, '/sys/acls/all_mygroup_acl.xml'
);
END;
/
COMMIT;

Проверим видимость ресурса пользователем SCOTT. Для удобства создадим сначала файл с запросом:
Код:
SELECT any_path
FROM resource_view
WHERE UNDER_PATH ( res, '/public' ) = 1
/
SAVE publicpaths

Проверка:
Код:
SQL> CONNECT scott/tiger
Connected.
SQL> @publicpaths

no rows selected

SQL> CONNECT / as sysdba
Connected.
SQL> GRANT mygroup TO scott;

Grant succeeded.

SQL> CONNECT scott/tiger
Connected.
SQL> @publicpaths

ANY_PATH
------------------------------------------
/public/OracleXML.doc

При включении пользователя в группу ресурс стал виден.

Тип XDBURITYPE для работы с ресурсами

Для работы с ресурсами репозитария можно использовать системный подтип XDBURITYPE абстрактного типа URITYPE. В частности, методы типа XDBURITYPE позволяют извлекать из репозитария содержимое ресурсов.
Пример определения длины файла /public/OracleXML.doc:
Код:
SELECT
  DBMS_LOB.GETLENGTH (
    XDBURITYPE ( '/public/OracleXML.doc' ).GETBLOB ( )
  ) AS bytes
FROM dual;

Результат:
Код:
BYTES
----------
    504320

Таким же образом можно извлечь большой файл (содержимое, а не длину) в переменную программы.
Одно из применений типа XDBURITYPE – дать возможность ссылаться на данные в репозитарии XBM DB из полей обычных таблиц. Пример:
Код:
CREATE TABLE projects AS
  SELECT
    1 AS pid
  , XDBURITYPE ( '/public/OracleXML.doc' ) AS description
  FROM dual;

SELECT
  DBMS_LOB.GETLENGTH ( p.description.GETBLOB ( ) ) AS bytes
FROM projects p;

Получим:
Код:
BYTES
----------
    504320

Обратите внимание, что сослаться на файл в репозитарии из БД можно и через тип HTTPURITYPE, однако в этом случае в ссылке появится имя компьютера и номер порта – признаки, внешние по отношению в содержимому БД, неконтролируемые средствами БД и, в отличие от ссылок извне, по сути ненужные.

Другие возможности

Любой ресурс репозитария можно перевести в режим версионного доступа (version control resource, VCR). С этой целью, и с целью самого доступа, следует использовать особый пакет DBMS_XDB_VERSION.
Любой ресурс репозитария можно снабдить собственным описанием (метаданными; в дополнение к «системным» метаданным), добавив в его описание XML («системное») свои элементы. Для этой цели можно использовать разные средства:
- в PL/SQL – процедуры пакета DBMS_XDB: APPENDRESOURCEMETADATA, UPDATERESOURCEMETADATA, DELETERESOURCEMETADATA, PURGERESOURCEMETADATA;
- в SQL – операции INSERT, UPDATE, DELETE применительно к полю RES (производной) таблицы RESOURCE_VIEW;
- методом PROPPATCH протокола WebDAV.
Подробности имеются в документации по Oracle.



Владимир Пржиялковский
Преподаватель технологий Oracle
http://www.ccas.ru/prz/

Комментарии :

Комментариев нет

© Surgutnet.ru 2005—2010
All rights reserved.
Перепечатка материалов с данного сервера возможна только с ОБЯЗАТЕЛЬНЫМ указанием АКТИВНОЙ ссылки на данный сайт
или с письменного разрешения владельцев материалов.

Расположение посетителей сайта


SQL общее время: 0.008 секунд - SQL запросов: 18 - Среднее время SQL: 0.00044 секунд
Страница создана за 0.295 секунд