※ 本記事は、Paul Parkinsonによる”Developing Data-Driven AI Apps: Making Calls to AI Services Directly from the Oracle Database“を翻訳したものです。

2024年1月30日


AIサービスとそれらが消費し、作成するデータが、さまざまなアプリケーションやプロセスにおいてより重要で普及するにつれて、それらが構築されるプラットフォームやアーキテクチャも同様になります。いつものように、「ワン・サイズですべてにフィット」はありませんが、ここで簡単に紹介するのは、このようなデータ・ドリブンAIアプリケーション・アーキテクチャへの最適化されたアプローチです。ここには、すべてのソース・コードと詳細が記載されており、無料の「Oracle AI and Database Servicesによる開発: Gen、Vision、Speech、Language、OML」ワークショップ(すべてのユース・ケースが国連17の持続可能な開発目標に基づいている)がここにあり、さらに多くの例が記載されています。

多くの場合、AIサービスへのコールや、入力または出力であるコンテンツ(テキスト、オーディオ、イメージ、ビデオなど)の取得および永続化の呼出しを伴う特定のAIアプリケーションで、複数のネットワーク・コールを実行する必要があります。その後、永続的な情報がさらに処理および分析され、追加のコール(AIなど)が反応して行われます。

Oracleデータベースでは、Oracle Cloud内か外部かに関係なく、他のサービス(AIなど)へのコールアウトを行うことができます。

かわりにデータベース自体からコールが行われると、次のような様々な利点を持つ最適化されたアーキテクチャが提供されます:

  1. ネットワーク・コールが減少するため、待機時間が短縮されます。
  2. ネットワーク・コールの削減により、信頼性が向上します。
  3. AIおよびその他のデータ(およびTxEventQ使用時のメッセージング)に対するトランザクション(ACID)操作により、べき等/重複処理ロジックなど、および関連する無駄なリソースが不要になります。
  4. 処理の最適化の原因は、データがデータベースに直接格納されているか、オブジェクト・ストアまたはその他のソースに格納されているかどうかです。これは、Oracleデータベースがオブジェクト・ストレージ・バケットに対して堅牢な機能フロントエンドを提供し、データベースには、オブジェクト・ストアやその他のデータ・ソースに配置されているデータに対して同期または最適に動作する多くのオプションがあるためです。
  5. 共通の認証メカニズムと、有名な堅牢なデータベースおよびクラウド・セキュリティ・インフラストラクチャの再利用によるセキュリティの強化。
  6. 中央の場所からコールが行われるため、全体的な構成が削減されます。データベース自体のエントリ・ポイントは、1回のクリックでRestエンドポイント(ORDSを使用)として公開できます。もちろん、様々な言語のドライバを使用してデータベースにアクセスすることもできます。
  7. ベクトル・データベースの利点。このトピックは、自分自身へのブログであり、特にOracleが持っているようにフォローオンとしてリリースし、この分野にいくつかの強力な機能を追加しています。
  8. Oracle Database Machine Learning。Oracleデータベース自体には、さまざまなAIサービスに加えて、長年にわたり機械学習エンジンがありました。OMLはMLのライフサイクルを合理化し、スケーラブルなSQL、R、Python、REST、AutoML、およびノーコード・ツールを30を超えるデータベース内アルゴリズムとともに提供し、データベース内のデータを直接処理することでデータの同期とセキュリティを強化します。
  9. Oracle Autonomous Database Select AIは、自然言語を使用したデータの問合せと、データベースに固有のSQLの生成を可能にします。
  10. Oracle Autonomous Database AI Vector Searchには、新しいベクトル・データ型、ベクトル索引およびベクトル検索SQL演算子が含まれており、これにより、Oracle Databaseはドキュメント、イメージおよびその他の非構造化データのセマンティック・コンテンツをベクトルとして格納し、これらを使用して高速類似性問合せを実行できます。これらの新機能ではRAG(Retrieval Augmented Generation)もサポートされており、高い精度を実現し、LLMトレーニング・データにプライベート・データを含めることでプライベート・データを公開する必要がなくなります。

ここでも、多くの異なるAIアプリケーションのフローと要件がありますが、2つのアプローチの基本的な比較を次のように視覚化できます。:

Developing Data-Driven AI Apps: Making Calls to AI Services Directly from the Oracle Database

The Code

データベースで複数の異なる言語を実行できるため、そこで様々なアプリケーション・ロジックを実行できます。これには、Java、JavaScriptおよびPL/SQLが含まれます。ここでは、PL/SQLの例を示し、OCIコンソールの「Database Actions」→「SQL」ページから、SQLclコマンドライン・ツール(OCI Cloud Shellに事前インストールされているか、ダウンロードできる)から、SQLDeveloper、VS Code(Oracleに便利なプラグインがある)から実行できます。

AIやその他のサービスを呼び出す方法もいくつかあります。データベースのUTL_HTTPパッケージを使用した標準Restコール、またはJavaScriptからのフェッチなどは、1つのアプローチです。AIサービスがOCI (Oracle Cloud)内で実行されている場合は、すべての主要言語用に記述されたOCI SDKも使用できます。DBMS_CLOUD.send_requestパッケージは、(たとえば、DBMS_CLOUD_OCI_AIV_AI_SERVICE_VISIONなどのより具体的なOCI SDKコールではなく)すべてのOCIサービス・コールに対して最もシンプルで動的なアプローチとして使用されています。

まず、すべてのクラウド・サービス・コールに対して参照および再利用できる資格証明を作成し、OCIアカウント/構成からの情報を単純に含めます。

BEGIN
dbms_cloud.create_credential (
 credential_name => 'OCI_KEY_CRED',
 user_ocid => 'ocid1.user.oc1..[youruserocid]',
 tenancy_ocid => 'ocid1.tenancy.oc1..[yourtenancyocid]',
 private_key => '[yourprivatekey - you can read this from file or put the contents of your pem without header, footer, and line wraps]'
 fingerprint => '[7f:yourfingerprint]'
);
END;

次に、主なプログラム/機能を見る前に、AIの結果を保存するテーブルをすぐに見てみましょう。この場合、表には、AIコール・リターンからのJSONの列と、クイック・リファレンスや検索などのためにJSONのキー・フィールドから作成されるテキスト・フィールドの両方が含まれます。ここでも、表構造、SQL/リレーショナルとJSONの使用などはすべて異なる場合があります。また、これは、様々なデータ・モデルとデータ型を使用できるOracleの多目的データベースの素晴らしい例です。たとえば、OracleデータベースのJSON二面性(JSON Duality)機能は、SQL/リレーショナル、JSONおよびMongoDB APIを使用して同じデータにアクセスできるため、チェックアウトする価値があります。

CREATE TABLE aivision_results
    (id RAW (16) NOT NULL,
     date_loaded TIMESTAMP WITH TIME ZONE,
     label varchar2(20),
     textfromai varchar2(32767),
     jsondata CLOB
     CONSTRAINT ensure_aivision_results_json CHECK (jsondata IS JSON));
/

そして今度は、アーキテクチャの中心となるシンプルな機能です… ここでは、作成した資格証明と(AI)サービス操作エンドポイントのURL (この場合はOracle Vision AIサービスのanalyzeImage操作)を使用したDBMS_CLOUD.send_requestへのコールを示します。本体のJSONペイロードは、使用するサービスの機能、その他の構成、および操作の引数で構成されます。この場合、イメージのオブジェクト・ストレージの場所(もう1つのオプションは、ペイロードの一部としてイメージ・バイト配列を直接/インライン化することです)が含まれます。

次に、JSONの結果がレスポンスから取得され、その特定の要素が便宜上テキスト・フィールドに解析され、前述のようにJSON、テキストなどが保持されます。

CREATE OR REPLACE FUNCTION VISIONAI_TEXTDETECTION (
    p_endpoint VARCHAR2,
    p_compartment_ocid VARCHAR2,
    p_namespaceName VARCHAR2,
    p_bucketName VARCHAR2,
    p_objectName VARCHAR2,
    p_featureType VARCHAR2,
    p_label VARCHAR2
) RETURN VARCHAR2 IS
    resp DBMS_CLOUD_TYPES.resp;
    json_response CLOB;
    v_textfromai VARCHAR2(32767);
BEGIN
    resp := DBMS_CLOUD.send_request(
        credential_name => 'OCI_KEY_CRED',
        uri => p_endpoint || '/20220125/actions/analyzeImage',
        method => 'POST',
        body => UTL_RAW.cast_to_raw(
            JSON_OBJECT(
                'features' VALUE JSON_ARRAY(
                    JSON_OBJECT('featureType' VALUE p_featureType)
                ),
                'image' VALUE JSON_OBJECT(
                    'source' VALUE 'OBJECT_STORAGE',
                    'namespaceName' VALUE p_namespaceName,
                    'bucketName' VALUE p_bucketName,
                    'objectName' VALUE p_objectName
                ),
                'compartmentId' VALUE p_compartment_ocid
            )
        )
    );
    json_response := DBMS_CLOUD.get_response_text(resp);
    SELECT LISTAGG(text, ', ') WITHIN GROUP (ORDER BY ROWNUM)
    INTO v_textfromai
    FROM JSON_TABLE(json_response, '$.imageText.words[*]'
        COLUMNS (
            text VARCHAR2(100) PATH '$.text'
        )
    );
    INSERT INTO aivision_results (id, date_loaded, label, textfromai, jsondata)
    VALUES (SYS_GUID(), SYSTIMESTAMP, p_label, v_textfromai, json_response);
    RETURN v_textfromai;
EXCEPTION
    WHEN OTHERS THEN
        RAISE;
END VISIONAI_TEXTDETECTION;
/

また、次のものを使用して、Restエンドポイントとして関数をプログラム的に公開することもできます。

BEGIN
    ORDS.ENABLE_OBJECT(
        P_ENABLED      => TRUE,
        P_SCHEMA      => 'AIUSER',
        P_OBJECT      =>  'VISIONAI_OBJECTDETECTION',
        P_OBJECT_TYPE      => 'FUNCTION',
        P_OBJECT_ALIAS      => 'VISIONAI_OBJECTDETECTION',
        P_AUTO_REST_AUTH      => FALSE
    );
    COMMIT;
END;
/

AI結果の分析とテキスト検索

このアーキテクチャは、すべてのAI結果の分析とテキスト検索を便利かつ効率的にします。ここからは、より多くの処理と分析が行われます。AI結果の使いやすいテキスト検索を提供する3つのステートメントを見てみましょう。

  • まず、aivision_results表にテキスト検索用の索引を作成します。
  • 次に、強力なcontains機能を使用して特定の文字列を検索する関数を作成します。または、追加またはオプションでDBMS_SEARCHパッケージを使用して複数の表を検索し、結果のrefcursorを返すこともできます。
  • 最後に、関数をRestエンドポイントとして公開します。

それは簡単です。

create index aivisionresultsindex on aivision_results(textfromai) indextype is ctxsys.context;
/
CREATE OR REPLACE FUNCTION VISIONAI_RESULTS_TEXT_SEARCH(p_sql IN VARCHAR2) RETURN SYS_REFCURSOR AS refcursor SYS_REFCURSOR;
BEGIN
    OPEN refcursor FOR
        select textfromai from AIVISION_RESULTS where contains ( textfromai, p_sql ) > 0;
    RETURN refcursor;
END VISIONAI_RESULTS_TEXT_SEARCH;
/
BEGIN
    ORDS.ENABLE_OBJECT(
        P_ENABLED      => TRUE,
        P_SCHEMA      => 'AIUSER',
        P_OBJECT      =>  'VISIONAI_RESULTS_TEXT_SEARCH',
        P_OBJECT_TYPE      => 'FUNCTION',
        P_OBJECT_ALIAS      => 'VISIONAI_RESULTS_TEXT_SEARCH',
        P_AUTO_REST_AUTH      => FALSE
    );
    COMMIT;
END;
/

結論…

これは、AIサービスをデータベースから直接コールしてデータ・ドリブンのAIアプリを開発するためのアーキテクチャ・パターンを示すクイック・ブログでした。

読んでくれてありがとうございます。そしてあなたが持っている質問やフィードバックを私に知らせてください。