DBMS_CLOUD Tipi complessi di pacchetti Avro, ORC e Parquet

Descrive il mapping dei tipi di dati complessi Avro, ORC e Parquet ai tipi di dati Oracle.

Autonomous Database supporta tipi di dati complessi, inclusi i seguenti tipi complessi:

  • strutt

  • lista

  • mappa

  • sindacale

  • array

Quando si specifica un tipo di file di origine Avro, ORC o Parquet e il file di origine include colonne complesse, le query di Autonomous Database restituiscono JSON per le colonne complesse. Ciò semplifica l'elaborazione dei risultati delle query; puoi utilizzare le potenti funzioni di analisi JSON di Oracle in modo coerente tra i tipi di file e i tipi di dati. La tabella riportata di seguito mostra il formato per i tipi complessi in Autonomous Database.

Nota

I campi complessi vengono mappati alle colonne VARCHAR2 e vengono applicati i limiti di dimensione VARCHAR2.
Digita Parquet ORC Avro Oracle
Lista: sequenza di valori Elenca Elenca Array VARCHAR2 (formato JSON)
Mappa: lista di oggetti con chiave singola Mappa Mappa Mappa VARCHAR2 (formato JSON)
Unione: valori di tipo diverso Non disponibile Unione Unione VARCHAR2 (formato JSON)
Oggetto: zero o più coppie chiave-valore Struttura Struttura Registra VARCHAR2 (formato JSON)

Se i file di origine ORC, Parquet o Avro contengono tipi complessi, è possibile eseguire una query sull'output JSON per questi tipi complessi comuni. Ad esempio, quanto segue mostra un file ORC, movie-info.orc, con un tipo complesso (lo stesso tipo complesso di gestione si applica per i file di origine Parquet e Avro).

Si consideri il file movie-info.orc con lo schema seguente:

id    int
original_title string
overview       string
poster_path    string
release_date   string
vote_count     int
runtime        int
popularity     double
genres         array<struct<id:int,name:string>

Si noti che ogni filmato viene classificato da più genres utilizzando un array di genres. L'array genres è un valore array di structs e ogni elemento ha un valore id (int) e un valore name (string). L'array genres è considerato un tipo complesso. È possibile creare una tabella su questo file ORC utilizzando DBMS_CLOUD.CREATE_EXTERNAL_TABLE come indicato di seguito.

BEGIN
DBMS_CLOUD.CREATE_EXTERNAL_TABLE(
        table_name =>'movie_info',
        credential_name =>'OBJ_STORE_CRED',
        file_uri_list =>'https://objectstorage.us-phoenix-1.oraclecloud.com/n/mytenancy/b/movies/o/movie-info.orc',
        format => '{"type":"orc", "schema": "first"}');
END;
/

Quando si crea la tabella esterna, il database genera automaticamente le colonne in base allo schema nel file ORC (se si utilizza Avro o Parquet, si applica lo stesso). Per questo esempio, DBMS_CLOUD.CREATE_EXTERNAL_TABLE crea una tabella nel database come indicato di seguito.

CREATE TABLE "ADMIN"."MOVIE_INFO" 
    ( "ID"
      NUMBER(10,0), 
      "ORIGINAL_TITLE"  VARCHAR2(4000 BYTE) COLLATE "USING_NLS_COMP", 
      "OVERVIEW"        VARCHAR2(4000 BYTE) COLLATE "USING_NLS_COMP", 
      "POSTER_PATH"     VARCHAR2(4000 BYTE) COLLATE "USING_NLS_COMP", 
      "RELEASE_DATE"    VARCHAR2(4000 BYTE) COLLATE "USING_NLS_COMP", 
      "VOTE_COUNT"      NUMBER(10,0), 
      "RUNTIME"         NUMBER(10,0), 
      "POPULARITY"      BINARY_DOUBLE, 
      "GENRES"          VARCHAR2(4000 BYTE) COLLATE "USING_NLS_COMP"
    )  DEFAULT COLLATION "USING_NLS_COMP"
    ORGANIZATION EXTERNAL 
     ( TYPE      ORACLE_BIGDATA
       DEFAULT DIRECTORY "DATA_PUMP_DIR"
       ACCESS PARAMETERS
       ( com.oracle.bigdata.credential.name=OBJ_STORE_CRED
         com.oracle.bigdata.fileformat=ORC
   )
       LOCATION
        (
      'https://objectstorage.us-phoenix-1.oraclecloud.com/n/mytenancy/b/movies/o/movie-info.orc'
           )
     )
   REJECT LIMIT UNLIMITED 
   PARALLEL;
 )

Ora è possibile eseguire una query sui dati del filmato:

SELECT original_title, release_date, genres 
     FROM movie_info 
     WHERE release_date > '2000'
     ORDER BY original_title;

Viene prodotto l'output seguente:


original_title              release_date   genres
(500) Days of Summer        2009           [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},{"id":17,"name":"Horror"},{"id":19,"name":"Western"},{"id":18,"name":"War"},{"id":15,"name":"Romance"}]
10,000 BC                   2008           [{"id":6,"name":"Comedy"}]
11:14                       2003           [{"id":9,"name":"Thriller"},{"id":14,"name":"Family"}]
127 Hours                   2010           [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"}]
13 Going on 30              2004           [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"},{"id":18,"name":"War"},{"id":15,"name":"Romance"}]
1408                        2007           [{"id":45,"name":"Sci-Fi"},{"id":6,"name":"Comedy"},{"id":17,"name":"Horror"},{"id":6,"name":"Comedy"},{"id":18,"name":"War"}]

Si noti che il tipo complesso genres viene restituito come array JSON.

Per rendere più utili i dati JSON, è possibile trasformare la colonna utilizzando le funzioni JSON di Oracle. Ad esempio, è possibile utilizzare la notazione "." JSON e le funzioni di trasformazione più potenti come JSON_TABLE.

Per informazioni sulla notazione ".", vedere Simple Dot-Notation Access to JSON Data.

Per informazioni su JSON_TABLE, vedere Funzione SQL/JSON JSON_TABLE.

Nell'esempio riportato di seguito viene illustrata una query sulla tabella che acquisisce ogni valore dell'array e trasforma il valore in una riga nel set di risultati.
SELECT original_title, release_date, m.genre_name, genres
    FROM movie_info mi,
       JSON_TABLE(mi.genres, '$.name[*]'
        COLUMNS (genre_name VARCHAR2(25) PATH
      '$')                 
                 ) AS m
 WHERE rownum < 10;

Il valore JSON_TABLE crea una riga per ogni valore dell'array, pensa all'outer join e la struttura viene analizzata per estrarre il nome del genere. Viene prodotto l'output seguente:


original_title                   release_date         genre_name        genres
(500) Days of Summer             2009                 Drama             [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
(500) Days of Summer             2009                 Comedy            [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
(500) Days of Summer             2009                 Horror            [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
(500) Days of Summer             2009                 Western           [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
(500) Days of Summer             2009                 War               [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
(500) Days of Summer             2009                 Romance           [{"id":3,"name":"Drama"},{"id":6,"name":"Comedy"},
                                                                        {"id":17,"name":"Horror"},{"id":19,"name":"Western"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
10,000 BC                        2008                 Comedy            [{"id":6,"name":"Comedy"}]
11:14                            2003                 Family            [{"id":9,"name":"Thriller"},{"id":14,"name":"Family"}]
11:14                            2003                 Thriller          [{"id":9,"name":"Thriller"},{"id":14,"name":"Family"}]
127 Hours                        2010                 Comedy            [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"}]
127 Hours                        2010                 Drama             [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"}]
13 Going on 30                   2004                 Romance           [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
13 Going on 30                   2004                 Comedy            [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
13 Going on 30                   2004                 War               [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]
13 Going on 30                   2004                 Drama             [{"id":6,"name":"Comedy"},{"id":3,"name":"Drama"},
                                                                        {"id":18,"name":"War"},{"id":15,"name":"Romance"}]