2015-09-12 6 views
1

Хорошее время суток для всех. Я столкнулся с огромной проблемой во время моей работы на предыдущей неделе. Здесь ia сделка:Импорт blob через SAS из ORACLE DB

Мне нужно загрузить exel-файл (blob) из базы данных ORACLE через SAS. Я использую:

  1. Первый шаг я должен получить данные из оракула. Я использовал строительство (блоб файл почти 100kb):

    proc sql; 
    connect to oracle; 
    create table SASTBL as 
    select * from connection to oracle (
    select dbms_lob.substr(myblobfield,1,32767) as blob_1, 
    dbms_lob.substr(myblobfield,32768,32767) as blob_2, 
    dbms_lob.substr(myblobfield,65535,32767) as blob_3, 
    dbms_lob.substr(myblobfield,97302,32767) as blob_4 
    
        from my_tbl; 
    ); 
    quit; 
    

И результат:

blob_1 = 70020202020202...02 
    blob_2 = 02020202020...02 
    blob_3 = 02020202...02 

Я не понимаю, почему поле состоит из (всего файла «02»)

И длина любой переменной в sas составляет 1024 (вместо 37767) $ HEX2024. Если я возьму:

dbms_lob.substr (my_blob_field, 2000,900) из того же объекта, результат будет месиво более похоже на правду: блоба = "A234ABC4536AE7 ...."

Вопрос 1. Как я могу получить двоичные данные из поля blob правильно через SAS? Какая у меня ошибка?

спасибо.

EDIT 1:

я получаю информацию, но не более строка 2000 кб.

+0

Может у ou connect by [libname] (https://support.sas.com/documentation/cdl/en/acreldb/63647/HTML/default/viewer.htm#a001355231.htm): 'libname oracledata odbc datasrc = orasrvr1 user =" имя пользователя "password =" password "; '- при необходимости? – Parfait

+0

Из любопытства, какая информация хранится в блоке? Изображение? Вложение файлов? Что-то другое? –

+0

@RobertPenridge тип файла - офисный документ (exel, doc) – bobby1232

ответ

0

Используйте параметр DBMAX_TEXT заявление CONNECT (или Имя_библиотеки), чтобы получить до 32 767 символов. Значение по умолчанию, вероятно, равно 1024.

+0

Я добавил DBMAX_TEXT = 32767 на соединение, длина переменной изменилась на 2000 $ HEX4000, она еще не закрыта на 32767 – bobby1232

0

PROC SQL использует SQL для взаимодействия с наборами данных SAS (создавать таблицы, таблицы запросов, сводные данные, подключаться извне и т. Д.). Процедура в основном соответствует стандарту ANSI с несколькими расширениями SAS. Каждый RDMS расширяет ANSI, включая Oracle, с обработкой XML, например, сохранение содержимого в столбце blob. Возможно, SAS не может правильно прочитать специфичный для Oracle (не ANSI) двоичный большой тип объекта. Обычно SAS обрабатывает строку, числовое число, дату и время и несколько других типов.

В качестве альтернативы рассмотрите возможность сохранения содержимого XML из Oracle наружно как .xml файл и использовать XML двигатель SAS для чтения контента в SAS набора данных:

** STORING XML CONTENT; 
libname tempdata xml 'C:\Path\To\XML\File.xml'; 

** APPEND CONTENT TO SAS DATASET; 
data Work.XMLData; 
    set tempdata.NodeName;  /* CHANGE TO REPEAT PARENT NODE OF XML. */ 
run; 
+0

Я не могу хранить содержимое xml из oracle извне, потому что у меня нет прямого подключения к oracle db, onlu через SAS. – bobby1232

0

Добавление в качестве другого ответа, поскольку я еще не могу прокомментировать ... проблема, с которой вы столкнулись, заключается в том, что возвращение dbms_lob.substr на самом деле является varchar, поэтому SAS ограничивает его до 2000. Чтобы этого избежать, вы можете обернуть его в to_clob (...) И установить опцию DBMAX_TEXT, как ранее было сказано.

Другой альтернативой является ниже ...

Приведенный ниже код является эффективным способом для извлечения одной записи с большой CLOB. Вместо того, чтобы вычислять, сколько полей разбивает клоб в результате получения очень широкой записи, вместо этого разбивает его на несколько строк. См. Ожидаемый вывод внизу.

Отказ от ответственности: хотя он эффективен, он может быть неэффективным, т. Е. Не может хорошо масштабироваться для нескольких строк, общепринятым подходом является строковая конвейерная PLSQL. Это, как говорится, ниже меня из щепоткой, если вы не можете сделать процедуру ...

PROC SQL; 
connect to oracle (authdomain=YOUR_Auth path=devdb DBMAX_TEXT=32767); 
create table clob_chunks (compress=yes) as 
select * 
from connection to Oracle (
    SELECT id 
     , key 
     , level clob_order 
     , regexp_substr(clob_value, '.{1,32767}', 1, level, 'n') clob_chunk 
    FROM (
     SELECT id, key, clob_value 
     FROM schema.table 
     WHERE id = 123 
    ) 
    CONNECT BY LEVEL <= regexp_count(clob_value, '.{1,32767}',1,'n') 
) 
order by id, key, clob_order; 

disconnect from oracle; 

QUIT; 

Ожидаемый результат:

ID KEY CHUNK CLOB 
1 1 1 short_clob 
2 2 1 long clob chunk1of3 
2 2 2 long clob chunk2of3 
2 2 3 long clob chunk3of3 
3 3 1 another_short_one 

Объяснение:

  1. DBMAX_TEXT говорит SAS, чтобы настроить значение по умолчанию 1024 для поля clob.
  2. Регулярное выражение {1,32767} сообщает Oracle, что он должен совпадать хотя бы один раз, но не более 32767 раз. Это разделяет вход и фиксирует последний фрагмент, который, вероятно, будет иметь длину до 32767.
  3. Regexp_substr вытаскивает кусок из clob (param1), начиная с начала clob (param2), пропускаясь до уровня уровня (param3) и обрабатывая clob как одну большую строку (param4 'n').
  4. Соединитесь, повторно запустив регулярное выражение, чтобы подсчитать куски, чтобы остановить уровень, увеличивающийся за пределами конца клоа.

Ссылки:

+0

. Если вы можете ответить на вопрос, вам не нужно оставлять комментарии. Ваш пост в порядке. Если, однако, вы не можете ответить на вопрос, вы не должны публиковать его как авайер. Поэтому нет необходимости объяснять себя :) –

Смежные вопросы