मैं Oracle SQL में BLOB से पाठ्य सामग्री कैसे प्राप्त करूं


112

मैं एक SQL कंसोल से देखने की कोशिश कर रहा हूं कि Oracle BLOB के अंदर क्या है।

मुझे पता है कि इसमें पाठ का एक बड़ा भाग शामिल है और मैं केवल पाठ देखना चाहता हूं, लेकिन निम्नलिखित प्रश्न केवल यह दर्शाता है कि उस क्षेत्र में एक BLOB है:

select BLOB_FIELD from TABLE_WITH_BLOB where ID = '<row id>';

मुझे जो परिणाम मिल रहा है वह वैसा नहीं है जिसकी मुझे उम्मीद थी:

    BLOB_FIELD
    -----------------------
    oracle.sql.BLOB@1c4ada9

तो मैं किस प्रकार के जादू की घटनाओं को हटाकर बीएलओबी को पाठीय प्रतिनिधित्व में बदल सकता हूं?

पुनश्च: मैं एक SQL कंसोल (ग्रहण डेटा उपकरण) से BLOB की सामग्री को देखने की कोशिश कर रहा हूं, इसका उपयोग कोड में नहीं।

जवाबों:


141

सबसे पहले, आप BLOB के बजाय CLOB / NCLOB कॉलम में टेक्स्ट स्टोर करना चाह सकते हैं, जो कि बाइनरी डेटा के लिए डिज़ाइन किया गया है (आपकी क्वेरी CLOB के साथ काम करेगी, वैसे)।

निम्नलिखित प्रश्न आपको ब्लॉब के अंदर पाठ के पहले 32767 अक्षर (अधिकतम पर) को देखने देगा, बशर्ते सभी वर्ण सेट संगत हों (BLOB में संग्रहीत पाठ का मूल CS, VARCHAR2 के लिए उपयोग किए गए डेटाबेस का CS)

select utl_raw.cast_to_varchar2(dbms_lob.substr(BLOB_FIELD)) from TABLE_WITH_BLOB where ID = '<row id>';

3
दुर्भाग्य से, मैं डेटाबेस स्कीमा को नियंत्रित नहीं करता हूं - मुझे बस बूँद में झांकने की ज़रूरत है ... लेकिन वैसे भी धन्यवाद।
रोलैंड टेप

धन्यवाद मैक, यह ठीक काम करता है --- लेकिन उस "dbms_lob.substr" का उद्देश्य क्या है? --- केवल "select utl_raw.cast_to_varchar2 (BLOB_FIELD) ... का उपयोग करके ..." मुझे वही परिणाम देने लगता है ...?
रोप

4
cast_to_varchar2 इनपुट में एक RAW लेता है ( docs.oracle.com/cd/E11882_01/appdev.112/e25788/… ), जो लंबाई में 32767 बाइट्स तक सीमित है ( docs.oracle.com/cd/E11882_01/appdev.112/e10472) /… )। एक BLOB का आकार में कोई सीमा नहीं होती है, इसलिए यदि आवश्यक हो तो पदार्थ इसे एक सही आकार ( docs.oracle.com/cd/E11882_01/appdev.112/e25788/… ) पर काट देता है।
मैक

34
मेरे लिए काम नहीं करता है - मुझे "ORA-06502: PL / SQL: संख्यात्मक या मूल्य त्रुटि: कच्चा चर लंबाई बहुत लंबा है"। मैं 2000 चार्ट तक पहुंचने के लिए BLOB_FIELD के बाद "2000,1" डाल सकता हूं, लेकिन इससे आगे कुछ भी नहीं।
मार्क

2
यदि मान 4000 से अधिक है, तो यह त्रुटियों को फेंक देगा क्योंकि एसक्यूएल में तार के लिए अधिकतम मूल्य है। आपको रूट (BLOB_FIELD, 4000, 1) जोड़ना होगा। अगर आप को अधिक समय तक पीएल / एसक्यूएल का उपयोग करने की आवश्यकता हो तो (32000 तक) मेरा मानना ​​है
सोनिक सोल

14

तालिका से BLOB फ़ील्ड्स पढ़ने के लिए आप SQL के नीचे का उपयोग कर सकते हैं।

SELECT DBMS_LOB.SUBSTR(BLOB_FIELD_NAME) FROM TABLE_NAME;

मेरे पास BLOB कॉलम है और जहाँ XML डेटा को संपीड़ित और तालिका में संग्रहीत किया जाता है, जब मैं डेटा पढ़ता हूँ, तो यह केवल कुछ संख्याएँ दिखाता है और वास्तविक xml पाठ नहीं, मुझे तालिका से XML पाठ डेटा पढ़ने के लिए क्या करना चाहिए।
BHUVANESH MOHANKUMAR

14

SQL डेवलपर यह कार्यक्षमता भी प्रदान करता है:

परिणाम ग्रिड सेल पर डबल क्लिक करें, और संपादित करें पर क्लिक करें:

यहां छवि विवरण दर्ज करें

फिर पॉप-अप के दाहिने हिस्से पर, "View As Text" (आप चित्र भी देख सकते हैं ..)

यहां छवि विवरण दर्ज करें

और बस!

यहां छवि विवरण दर्ज करें


यह एक महान टिप है - धन्यवाद!
एड ग्राहम 12

7

यदि आप इसे देखने के बजाय पाठ के अंदर खोजना चाहते हैं, तो यह काम करता है:

with unzipped_text as (
  select
    my_id
    ,utl_compress.lz_uncompress(my_compressed_blob) as my_blob
  from my_table
  where my_id='MY_ID'
)
select * from unzipped_text
where dbms_lob.instr(my_blob, utl_raw.cast_to_raw('MY_SEARCH_STRING'))>0;

मेरा_यहाँ क्या है?
अंजन

यह मेरे लिए काम नहीं कर रहा है, मेरे पास BLOB स्तंभ है और जहाँ XML डेटा को संकुचित और तालिका में संग्रहीत किया जाता है, जब मैं डेटा पढ़ता हूँ, तो यह केवल कुछ संख्याएँ दिखाता है और वास्तविक xml पाठ नहीं, मुझे XML पाठ पढ़ने के लिए क्या करना चाहिए तालिका से डेटा।
BHUVANESH MOHANKUMAR

3

बार्न के जवाब ने मेरे लिए संशोधन के साथ काम किया क्योंकि मेरा कॉलम संपीड़ित नहीं है। त्वरित और गंदा समाधान:

select * from my_table
where dbms_lob.instr(my_UNcompressed_blob, utl_raw.cast_to_raw('MY_SEARCH_STRING'))>0;

3

मैंने कुछ समय के लिए इससे संघर्ष किया और पीएल / एसक्यूएल समाधान को लागू किया, लेकिन बाद में एहसास हुआ कि टॉड में आप परिणाम ग्रिड सेल पर बस डबल क्लिक कर सकते हैं, और यह पाठ में सामग्री के साथ एक संपादक लाता है। (मैं टॉड v11 पर हूं)

यहां छवि विवरण दर्ज करें


1

यदि आपका पाठ DEFLATE एल्गोरिथम का उपयोग करते हुए बूँद के अंदर संपीड़ित है और यह काफी बड़ा है, तो आप इसे पढ़ने के लिए इस फ़ंक्शन का उपयोग कर सकते हैं

CREATE OR REPLACE PACKAGE read_gzipped_entity_package AS

FUNCTION read_entity(entity_id IN VARCHAR2)
  RETURN VARCHAR2;

END read_gzipped_entity_package;
/

CREATE OR REPLACE PACKAGE BODY read_gzipped_entity_package IS

FUNCTION read_entity(entity_id IN VARCHAR2) RETURN VARCHAR2
IS
    l_blob              BLOB;
    l_blob_length       NUMBER;
    l_amount            BINARY_INTEGER := 10000; -- must be <= ~32765.
    l_offset            INTEGER := 1;
    l_buffer            RAW(20000);
    l_text_buffer       VARCHAR2(32767);
BEGIN
    -- Get uncompressed BLOB
    SELECT UTL_COMPRESS.LZ_UNCOMPRESS(COMPRESSED_BLOB_COLUMN_NAME)
    INTO   l_blob
    FROM   TABLE_NAME
    WHERE  ID = entity_id;

    -- Figure out how long the BLOB is.
    l_blob_length := DBMS_LOB.GETLENGTH(l_blob);

    -- We'll loop through the BLOB as many times as necessary to
    -- get all its data.
    FOR i IN 1..CEIL(l_blob_length/l_amount) LOOP

        -- Read in the given chunk of the BLOB.
        DBMS_LOB.READ(l_blob
        ,             l_amount
        ,             l_offset
        ,             l_buffer);

        -- The DBMS_LOB.READ procedure dictates that its output be RAW.
        -- This next procedure converts that RAW data to character data.
        l_text_buffer := UTL_RAW.CAST_TO_VARCHAR2(l_buffer);

        -- For the next iteration through the BLOB, bump up your offset
        -- location (i.e., where you start reading from).
        l_offset := l_offset + l_amount;
    END LOOP;
    RETURN l_text_buffer;
EXCEPTION
    WHEN OTHERS THEN
        DBMS_OUTPUT.PUT_LINE('!ERROR: ' || SUBSTR(SQLERRM,1,247));
END;

END read_gzipped_entity_package;
/

फिर टेक्स्ट पाने के लिए सिलेक्ट रन करें

SELECT read_gzipped_entity_package.read_entity('entity_id') FROM DUAL;

आशा है कि यह किसी की मदद करेगा।


1

इस SQL ​​का उपयोग BLOB के पहले 2000 चार्ट प्राप्त करने के लिए करें।

SELECT utl_raw.cast_to_varchar2(dbms_lob.substr(<YOUR_BLOB_FIELD>,2000,1)) FROM <YOUR_TABLE>;

नोट: ऐसा इसलिए है, क्योंकि Oracle BLOB के रूपांतरण को संभालने में सक्षम नहीं होगा जो कि लंबाई 2000 से अधिक है।


0

आप यह कोशिश कर सकते हैं:

SELECT TO_CHAR(dbms_lob.substr(BLOB_FIELD, 3900)) FROM TABLE_WITH_BLOB;

हालांकि, यह 4000 बाइट तक सीमित होगा


-2

मेरे लिए काम किया,

चयन करें ((सम्मिलित करें (सम्मिलित करें (सम्मिलित करें (hex (BLOB_FIELD)), 9,0, '-'), 14,0, '-'), 19,0, '-'), 24,0, '( '))) TABLE_WITH_BLOB से FIELD_ID के रूप में जहां ID =' पंक्ति आईडी ';


यदि यह आपके लिए काम करता है तो आप ओरेकल का उपयोग नहीं कर रहे हैं, जो ओपी है और इसीलिए उत्तर को वैध ओरेकल सिंटैक्स होना चाहिए।
एपीसी

-4

TO_CHARफ़ंक्शन का उपयोग करें ।

select TO_CHAR(BLOB_FIELD) from TABLE_WITH_BLOB where ID = '<row id>'

धर्मान्तरित NCHAR, NVARCHAR2, CLOB, या NCLOBडेटाबेस वर्ण सेट करने के लिए डेटा। लौटाया गया मान हमेशा होता है VARCHAR2


चयन DBMS_LOB.SUBSTR (BLOB_FIELD) TABLE_WITH_BLOB से;
संभ
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.