Compare commits
1 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 1e9af90582 |
@@ -98,6 +98,8 @@ Allow group ampminsights-app to read objects in compartment <nome-do-comparti
|
||||
<tr><td><code>OCI_REGION</code></td><td>Passo 4 acima (campo <code>region</code>), ex.: <code>sa-saopaulo-1</code>.</td></tr>
|
||||
<tr><td><code>OS_NAMESPACE</code></td><td>Passo 6 acima. Só necessário se for usar o modelo ONNX (Seção 4 do script 1).</td></tr>
|
||||
<tr><td><code>OS_BUCKET</code></td><td>Nome que você escolher para o bucket que vai criar na Seção 4 do script 1.</td></tr>
|
||||
<tr><td><code>GENAI_REGION</code></td><td>Região do OCI Generative AI (Seção 5+) — pode ser diferente de <code>OCI_REGION</code>. Padrão <code>us-chicago-1</code>; troque se sua tenancy não alcançar essa região (ver <a href="09-operacao-observabilidade.html">Operação & observabilidade</a>).</td></tr>
|
||||
<tr><td><code>AI_LOG_RETENTION_DAYS</code></td><td>Preenchido automaticamente (90 dias) — dias de retenção do log de chamadas de IA/embeddings.</td></tr>
|
||||
<tr><td>Chave privada (.pem)</td><td>Passo 7 acima — colada direto na Seção 3 do script 1, nunca na tabela de configuração.</td></tr>
|
||||
<tr><td>Credenciais do export APEX (<code>apex_cred</code>, <code>RAG_CRED</code>, compartimento no remote server <code>apex_genai</code>)</td><td>Mesmos valores de tenancy/compartimento acima — preenchidos na importação do app (ver <a href="05-passo-a-passo-apex.html">Passo a passo: aplicação APEX</a>).</td></tr>
|
||||
</table>
|
||||
|
||||
@@ -112,9 +112,15 @@ GRANT CREATE CREDENTIAL TO AMPMINSIGHTS;
|
||||
GRANT CREATE JOB TO AMPMINSIGHTS;
|
||||
|
||||
-- 1.6) Regras de rede (ACL) para o schema poder chamar o endpoint do OCI
|
||||
-- Generative AI usado neste script (regiao us-chicago-1). Se voce for
|
||||
-- usar outra regiao de Generative AI, ajuste o host abaixo (e repita
|
||||
-- este bloco para cada host adicional que for necessario).
|
||||
-- Generative AI usado neste script (regiao us-chicago-1 por padrao - o
|
||||
-- mesmo valor que vai para o parametro GENAI_REGION da SECAO 2, que
|
||||
-- ainda nao existe neste ponto do script, por isso o host aqui e
|
||||
-- digitado direto). Nem toda tenancy alcanca us-chicago-1 (ex.: algumas
|
||||
-- tenancies com escopo regional restrito, como America Latina, podem
|
||||
-- so alcancar sa-saopaulo-1) - se for o seu caso, troque o host abaixo
|
||||
-- pela regiao que a sua tenancy alcanca, E use o mesmo valor no
|
||||
-- parametro GENAI_REGION da SECAO 2 (repita este bloco para cada host
|
||||
-- adicional que for necessario).
|
||||
BEGIN
|
||||
DBMS_NETWORK_ACL_ADMIN.APPEND_HOST_ACE(
|
||||
host => 'inference.generativeai.us-chicago-1.oci.oraclecloud.com',
|
||||
@@ -217,6 +223,14 @@ INSERT INTO TB_26AI_TECH_PARAMS (PARAM_NAME, PARAM_VALUE, DESCRIPTION) VALUES
|
||||
('OS_BUCKET', '<SUBSTITUA_PELO_NOME_DO_BUCKET_QUE_VOCE_VAI_CRIAR>',
|
||||
'Nome do bucket de Object Storage onde o modelo ONNX sera armazenado (ver SECAO 4).');
|
||||
|
||||
INSERT INTO TB_26AI_TECH_PARAMS (PARAM_NAME, PARAM_VALUE, DESCRIPTION) VALUES
|
||||
('AI_LOG_RETENTION_DAYS', '90',
|
||||
'Dias de retencao do log de chamadas de IA/embeddings (TB_26AI_TECH_LOG) - ver docs/09-operacao-observabilidade.html para a query de purga.');
|
||||
|
||||
INSERT INTO TB_26AI_TECH_PARAMS (PARAM_NAME, PARAM_VALUE, DESCRIPTION) VALUES
|
||||
('GENAI_REGION', 'us-chicago-1',
|
||||
'Regiao do OCI Generative AI usada pelo RAG/insights/embeddings (SECAO 5+). Pode ser diferente da OCI_REGION (que e a regiao "de casa" do seu tenancy/bucket) - o Generative AI so roda em regioes especificas. Se a sua tenancy nao alcancar us-chicago-1 (comum em tenancies com escopo regional restrito, ex. America Latina), troque para uma regiao que a sua tenancy alcance (ex. sa-saopaulo-1) E repita a ACL da SECAO 1.6 para o novo host - confirme antes com "oci generative-ai model-collection list-models" ou o Console OCI que o modelo usado (meta.llama-4-maverick-17b-128e-instruct-fp8) ainda esta ativo para uso on-demand na regiao escolhida, ja que a disponibilidade de modelos varia por regiao e muda com o tempo.');
|
||||
|
||||
COMMIT;
|
||||
|
||||
-- Confira: nenhuma linha abaixo deve ainda mostrar um valor "<SUBSTITUA...>"
|
||||
@@ -532,14 +546,15 @@ criação de um profile de SELECT AI (que já lê região e compartimento da tab
|
||||
<pre><code class="lang-sql">-- Rode os 3 blocos abaixo para confirmar que a credencial e a rede estao OK
|
||||
-- antes de seguir para as tabelas e o PL/SQL da aplicacao.
|
||||
|
||||
-- 5.1) Teste de embedding (Cohere, via OCI Generative AI)
|
||||
-- 5.1) Teste de embedding (Cohere, via OCI Generative AI). A URL usa a
|
||||
-- regiao configurada em GENAI_REGION (SECAO 2), nao um valor fixo.
|
||||
SELECT VECTOR_SERIALIZE(
|
||||
DBMS_VECTOR_CHAIN.UTL_TO_EMBEDDING(
|
||||
TO_CLOB('Teste simples para gerar um embedding.'),
|
||||
JSON('{
|
||||
"provider": "ocigenai",
|
||||
"credential_name": "OCI_CRED",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
@@ -547,13 +562,14 @@ SELECT VECTOR_SERIALIZE(
|
||||
) AS embedding
|
||||
FROM dual;
|
||||
|
||||
-- 5.2) Teste de geracao de texto (Llama 4, via OCI Generative AI)
|
||||
-- 5.2) Teste de geracao de texto (Llama 4, via OCI Generative AI). Mesma
|
||||
-- logica: a URL usa a regiao configurada em GENAI_REGION (SECAO 2).
|
||||
SELECT DBMS_VECTOR_CHAIN.UTL_TO_GENERATE_TEXT(
|
||||
TO_CLOB('Responda somente com a palavra: sucesso'),
|
||||
JSON('{
|
||||
"provider": "ocigenai",
|
||||
"credential_name": "OCI_CRED",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8",
|
||||
"chatRequest": {
|
||||
"temperature": 0.1,
|
||||
@@ -565,27 +581,28 @@ SELECT DBMS_VECTOR_CHAIN.UTL_TO_GENERATE_TEXT(
|
||||
FROM dual;
|
||||
|
||||
-- 5.3) Teste de SELECT AI (perguntas em linguagem natural sobre as views/
|
||||
-- tabelas do schema). O bloco abaixo le EMBEDDING_COMPARTMENT da tabela
|
||||
-- de configuracao (SECAO 2). As tabelas/view referenciadas abaixo sao
|
||||
-- criadas na SECAO 6 - rode este bloco depois de criar V_26AI_TECH e
|
||||
-- TB_26AI_TECH_CMDB.
|
||||
-- tabelas do schema). O bloco abaixo le EMBEDDING_COMPARTMENT e
|
||||
-- GENAI_REGION da tabela de configuracao (SECAO 2). As tabelas/view
|
||||
-- referenciadas abaixo sao criadas na SECAO 6 - rode este bloco depois
|
||||
-- de criar V_26AI_TECH e TB_26AI_TECH_CMDB.
|
||||
--
|
||||
-- A regiao do OCI Generative AI abaixo (us-chicago-1) e fixa de
|
||||
-- proposito, igual nos testes 5.1/5.2 e na ACL da SECAO 1.6 - nao
|
||||
-- precisa (nem deve) ser trocada pelo valor de OCI_REGION da tabela de
|
||||
-- configuracao, ja que o servico so esta disponivel em algumas regioes
|
||||
-- especificas da OCI.
|
||||
-- A regiao do OCI Generative AI abaixo vem do parametro GENAI_REGION -
|
||||
-- nao precisa (nem deve) ser trocada pelo valor de OCI_REGION da tabela
|
||||
-- de configuracao (sao coisas diferentes de proposito), ja que o
|
||||
-- servico so esta disponivel em algumas regioes especificas da OCI.
|
||||
DECLARE
|
||||
v_compartment TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
BEGIN
|
||||
SELECT param_value INTO v_compartment FROM TB_26AI_TECH_PARAMS WHERE param_name = 'EMBEDDING_COMPARTMENT';
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
DBMS_CLOUD_AI.CREATE_PROFILE(
|
||||
profile_name => 'OCI_CRED2',
|
||||
attributes => '{
|
||||
"provider": "oci",
|
||||
"credential_name": "OCI_CRED",
|
||||
"region": "us-chicago-1",
|
||||
"region": "' || v_genai_region || '",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8",
|
||||
"temperature": 0,
|
||||
"comments": true,
|
||||
@@ -835,19 +852,89 @@ LEFT OUTER JOIN
|
||||
GROUP BY nome
|
||||
HAVING count(1) = 1 )
|
||||
) c
|
||||
ON ( upper(v.ASSET_NAME) = upper(c.nome) AND c.AMBIENTE IS NOT NULL );</code></pre>
|
||||
ON ( upper(v.ASSET_NAME) = upper(c.nome) AND c.AMBIENTE IS NOT NULL );
|
||||
|
||||
-- Log de chamadas de IA/embeddings (sucesso e erro) - nao guarda prompt/
|
||||
-- resposta completos, so metadados de uso. Ver docs/09-operacao-observabilidade.html.
|
||||
CREATE TABLE "TB_26AI_TECH_LOG"
|
||||
( "LOG_ID" NUMBER GENERATED ALWAYS AS IDENTITY MINVALUE 1 MAXVALUE 9999999999999999999999999999 INCREMENT BY 1 START WITH 1 CACHE 20 NOORDER NOCYCLE NOKEEP NOSCALE NOT NULL ENABLE,
|
||||
"LOG_TS" TIMESTAMP(6) WITH TIME ZONE DEFAULT SYSTIMESTAMP NOT NULL ENABLE,
|
||||
"CALLING_OBJECT" VARCHAR2(128),
|
||||
"OPERATION" VARCHAR2(30),
|
||||
"SOURCE_TYPE" VARCHAR2(10),
|
||||
"SOURCE_ID" VARCHAR2(200),
|
||||
"PROVIDER" VARCHAR2(30),
|
||||
"MODEL_NAME" VARCHAR2(100),
|
||||
"APP_USER" VARCHAR2(100),
|
||||
"STATUS" VARCHAR2(10),
|
||||
"ERROR_CODE" NUMBER,
|
||||
"ERROR_MESSAGE" VARCHAR2(4000),
|
||||
"DURATION_MS" NUMBER,
|
||||
"PROMPT_CHARS" NUMBER,
|
||||
"RESPONSE_CHARS" NUMBER,
|
||||
CONSTRAINT "TB_26AI_TECH_LOG_PK" PRIMARY KEY ("LOG_ID") USING INDEX ENABLE
|
||||
);
|
||||
|
||||
CREATE INDEX "TB_26AI_TECH_LOG_TS_IX" ON "TB_26AI_TECH_LOG" ("LOG_TS");
|
||||
CREATE INDEX "TB_26AI_TECH_LOG_ST_IX" ON "TB_26AI_TECH_LOG" ("STATUS","LOG_TS");
|
||||
|
||||
COMMENT ON TABLE "TB_26AI_TECH_LOG" IS 'Log de cada chamada a Generative AI/embeddings feita pelo ampmInsights (sucesso ou erro) - nao guarda prompt/resposta completos, so metadados de uso (modelo, duracao, tamanho, status, erro). Usada para troubleshooting e monitoramento de consumo - ver docs/09-operacao-observabilidade.html.';</code></pre>
|
||||
</div>
|
||||
<h2>Seção 7 · PL/SQL de geracao de embeddings, RAG e insights (ampmInsights)</h2>
|
||||
<p>Cria as funções e a procedure descritas em <a href="02-arquitetura.html">Arquitetura</a>:
|
||||
<code>fnc_26ai_embed</code>, <code>fnc_26ai_tech_rag</code>, <code>FNC_26AI_TECH_MCP_V1</code>,
|
||||
<code>FNC_26ai_rag</code> e <code>prc_26ai_tech</code>. É um bloco longo (a maior parte é o texto dos
|
||||
prompts de IA) — copie e cole inteiro de uma vez.</p>
|
||||
<p>Cria <code>PRC_26AI_TECH_LOG</code> (log de cada chamada de IA/embedding — ver
|
||||
<a href="09-operacao-observabilidade.html">Operação & observabilidade</a>) e as funções e a
|
||||
procedure descritas em <a href="02-arquitetura.html">Arquitetura</a>: <code>fnc_26ai_embed</code>,
|
||||
<code>fnc_26ai_tech_rag</code>, <code>FNC_26AI_TECH_MCP_V1</code>, <code>FNC_26ai_rag</code> e
|
||||
<code>prc_26ai_tech</code>. É um bloco longo (a maior parte é o texto dos prompts de IA) — copie e
|
||||
cole inteiro de uma vez.</p>
|
||||
<div class="code-block">
|
||||
<div class="code-bar">
|
||||
<span class="code-label">Seção 7 — copiar e colar</span>
|
||||
<button class="copy-btn" type="button">Copiar</button>
|
||||
</div>
|
||||
<pre><code class="lang-sql">CREATE OR REPLACE FUNCTION fnc_26ai_embed( p_string IN VARCHAR2,
|
||||
<pre><code class="lang-sql">CREATE OR REPLACE PROCEDURE PRC_26AI_TECH_LOG (
|
||||
p_calling_object IN VARCHAR2,
|
||||
p_operation IN VARCHAR2,
|
||||
p_status IN VARCHAR2,
|
||||
p_source_type IN VARCHAR2 DEFAULT NULL,
|
||||
p_source_id IN VARCHAR2 DEFAULT NULL,
|
||||
p_provider IN VARCHAR2 DEFAULT NULL,
|
||||
p_model_name IN VARCHAR2 DEFAULT NULL,
|
||||
p_error_code IN NUMBER DEFAULT NULL,
|
||||
p_error_message IN VARCHAR2 DEFAULT NULL,
|
||||
p_duration_ms IN NUMBER DEFAULT NULL,
|
||||
p_prompt_chars IN NUMBER DEFAULT NULL,
|
||||
p_response_chars IN NUMBER DEFAULT NULL
|
||||
) AS
|
||||
PRAGMA AUTONOMOUS_TRANSACTION;
|
||||
/*
|
||||
Projeto: ampmInsights
|
||||
Objetivo: registrar em TB_26AI_TECH_LOG cada chamada a Generative AI/
|
||||
embeddings (sucesso ou erro), para troubleshooting e
|
||||
monitoramento de consumo (ver docs/09-operacao-observabilidade.html).
|
||||
Autonomous transaction: pode ser chamada de dentro de functions invocadas
|
||||
em contexto SQL sem interferir na transacao do chamador; nunca propaga erro
|
||||
(uma falha ao logar nao pode derrubar a chamada real de IA).
|
||||
*/
|
||||
BEGIN
|
||||
INSERT INTO TB_26AI_TECH_LOG (
|
||||
calling_object, operation, source_type, source_id, provider, model_name,
|
||||
app_user, status, error_code, error_message, duration_ms, prompt_chars,
|
||||
response_chars
|
||||
) VALUES (
|
||||
p_calling_object, p_operation, p_source_type, p_source_id, p_provider,
|
||||
p_model_name, NVL(V('APP_USER'), SYS_CONTEXT('USERENV','SESSION_USER')),
|
||||
p_status, p_error_code, SUBSTR(p_error_message, 1, 4000), p_duration_ms,
|
||||
p_prompt_chars, p_response_chars
|
||||
);
|
||||
COMMIT;
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
NULL; -- logging nunca pode quebrar a chamada real
|
||||
END;
|
||||
/
|
||||
|
||||
CREATE OR REPLACE FUNCTION fnc_26ai_embed( p_string IN VARCHAR2,
|
||||
p_emb_type IN VARCHAR2 DEFAULT 'COHERE',
|
||||
p_credential IN VARCHAR2 DEFAULT 'OCI_CRED')
|
||||
RETURN CLOB
|
||||
@@ -891,7 +978,7 @@ BEGIN
|
||||
dbms_vector_chain.utl_to_text( v_string ),
|
||||
json('{ "provider": "ocigenai",
|
||||
"credential_name": "' || p_credential || '",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
@@ -929,12 +1016,34 @@ BEGIN
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
DBMS_OUTPUT.PUT_LINE('Erro: ' || SQLCODE || ' - ' || SQLERRM);
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'FNC_26AI_EMBED',
|
||||
p_operation => 'EMBEDDING',
|
||||
p_status => 'ERROR',
|
||||
p_provider => 'vLLM',
|
||||
p_error_code => SQLCODE,
|
||||
p_error_message => SQLERRM
|
||||
);
|
||||
END;
|
||||
|
||||
END IF;
|
||||
|
||||
RETURN v_embedding;
|
||||
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
-- Cobre os ramos ONNX/COHERE (o vLLM ja trata e loga o proprio erro
|
||||
-- acima e nao propaga). Loga e repropaga sem mudar o comportamento
|
||||
-- existente.
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'FNC_26AI_EMBED',
|
||||
p_operation => 'EMBEDDING',
|
||||
p_status => 'ERROR',
|
||||
p_provider => p_emb_type,
|
||||
p_error_code => SQLCODE,
|
||||
p_error_message => SQLERRM
|
||||
);
|
||||
RAISE;
|
||||
END;
|
||||
/
|
||||
|
||||
@@ -959,9 +1068,12 @@ RETURN CLOB IS
|
||||
output CLOB;
|
||||
query_vec VECTOR;
|
||||
v_llm VARCHAR2(20) := 'LLAMA4'; -- [ LLAMA4 | OPENAI ]
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
|
||||
BEGIN
|
||||
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
-- embedding da pergunta do usuario
|
||||
query_vec := to_vector( fnc_26ai_embed ( p_string => p_query, p_emb_type => 'COHERE' ) ) ;
|
||||
|
||||
@@ -987,7 +1099,7 @@ BEGIN
|
||||
params_genai := '{
|
||||
"provider" : "ocigenai",
|
||||
"credential_name" : "' || p_credential || '",
|
||||
"url" : "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"url" : "https://inference.generativeai.' || v_genai_region || '.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8"}';
|
||||
|
||||
ELSIF v_llm = 'OPENAI' THEN
|
||||
@@ -1055,6 +1167,20 @@ Formato obrigatorio de saida:
|
||||
|
||||
RETURN output;
|
||||
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
-- Nao havia handler antes; loga e repropaga (comportamento de
|
||||
-- propagar o erro ao chamador continua o mesmo).
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'FNC_26AI_TECH_RAG',
|
||||
p_operation => 'RAG',
|
||||
p_status => 'ERROR',
|
||||
p_source_type => p_source_type,
|
||||
p_provider => 'ocigenai',
|
||||
p_error_code => SQLCODE,
|
||||
p_error_message => SQLERRM
|
||||
);
|
||||
RAISE;
|
||||
END;
|
||||
/
|
||||
|
||||
@@ -1087,10 +1213,16 @@ RETURN CLOB AS
|
||||
Objetivo: funcao global de chamada ao LLM (Llama 4, via OCI Generative AI)
|
||||
usada pelo RAG e pela geracao de insights.
|
||||
*/
|
||||
v_gen_ai_endpoint VARCHAR2(500) := 'https://inference.generativeai.us-chicago-1.oci.oraclecloud.com';
|
||||
v_gen_ai_endpoint VARCHAR2(500);
|
||||
v_gen_ai_model VARCHAR2(500) := 'meta.llama-4-maverick-17b-128e-instruct-fp8';
|
||||
resp DBMS_CLOUD_TYPES.RESP;
|
||||
v_t0 PLS_INTEGER := DBMS_UTILITY.GET_TIME;
|
||||
v_result CLOB;
|
||||
BEGIN
|
||||
SELECT 'https://inference.generativeai.' || param_value || '.oci.oraclecloud.com'
|
||||
INTO v_gen_ai_endpoint
|
||||
FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
resp := dbms_cloud.send_request(
|
||||
credential_name => p_oci_cred,
|
||||
uri => v_gen_ai_endpoint || '/20231130/actions/chat',
|
||||
@@ -1119,10 +1251,34 @@ BEGIN
|
||||
))
|
||||
))
|
||||
);
|
||||
RETURN json_value( dbms_cloud.get_response_text(resp) , '$.chatResponse.choices[0].message.content[0].text') ;
|
||||
v_result := json_value( dbms_cloud.get_response_text(resp) , '$.chatResponse.choices[0].message.content[0].text') ;
|
||||
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'FNC_26AI_RAG',
|
||||
p_operation => 'CHAT',
|
||||
p_status => 'OK',
|
||||
p_provider => 'ocigenai',
|
||||
p_model_name => v_gen_ai_model,
|
||||
p_duration_ms => (DBMS_UTILITY.GET_TIME - v_t0) * 10,
|
||||
p_prompt_chars => LENGTH(p_ai_prompt),
|
||||
p_response_chars => LENGTH(v_result)
|
||||
);
|
||||
|
||||
RETURN v_result;
|
||||
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'FNC_26AI_RAG',
|
||||
p_operation => 'CHAT',
|
||||
p_status => 'ERROR',
|
||||
p_provider => 'ocigenai',
|
||||
p_model_name => v_gen_ai_model,
|
||||
p_error_code => SQLCODE,
|
||||
p_error_message => SQLERRM,
|
||||
p_duration_ms => (DBMS_UTILITY.GET_TIME - v_t0) * 10,
|
||||
p_prompt_chars => LENGTH(p_ai_prompt)
|
||||
);
|
||||
RETURN 'Nao foi possivel gerar um texto com base nas informacoes.';
|
||||
END;
|
||||
/
|
||||
@@ -1167,8 +1323,11 @@ AS
|
||||
v_response CLOB;
|
||||
v_json CLOB;
|
||||
v_error CLOB;
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
BEGIN
|
||||
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
IF p_source_type = 'VUL' THEN -- vulnerabilidades
|
||||
|
||||
v_pre_prompt :='Voce e um analista senior de dados e operacoes.
|
||||
@@ -1565,7 +1724,7 @@ Retorne um JSON valido (sem comentarios), espelhando o relatorio:
|
||||
( v_response ) ,
|
||||
json('{ "provider": "ocigenai",
|
||||
"credential_name": "' || p_oci_cred || '",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || v_genai_region || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
@@ -1579,21 +1738,52 @@ Retorne um JSON valido (sem comentarios), espelhando o relatorio:
|
||||
)
|
||||
) AS et;
|
||||
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'PRC_26AI_TECH',
|
||||
p_operation => 'EMBEDDING',
|
||||
p_status => 'OK',
|
||||
p_source_type => p_source_type,
|
||||
p_source_id => p_rowid,
|
||||
p_provider => 'ocigenai',
|
||||
p_model_name => 'cohere.embed-v4.0',
|
||||
p_prompt_chars => LENGTH(v_response)
|
||||
);
|
||||
|
||||
END IF;
|
||||
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'PRC_26AI_TECH',
|
||||
p_operation => 'INSIGHT_PIPELINE',
|
||||
p_status => 'OK',
|
||||
p_source_type => p_source_type,
|
||||
p_source_id => p_rowid
|
||||
);
|
||||
|
||||
COMMIT;
|
||||
|
||||
EXCEPTION
|
||||
WHEN OTHERS THEN
|
||||
v_error := sqlerrm;
|
||||
PRC_26AI_TECH_LOG(
|
||||
p_calling_object => 'PRC_26AI_TECH',
|
||||
p_operation => 'INSIGHT_PIPELINE',
|
||||
p_status => 'ERROR',
|
||||
p_source_type => p_source_type,
|
||||
p_source_id => p_rowid,
|
||||
p_error_code => SQLCODE,
|
||||
p_error_message => v_error
|
||||
);
|
||||
-- Antes, o erro tecnico (sqlerrm) era gravado direto em insight_report e
|
||||
-- ficava visivel pro usuario de negocio no modal. Agora o erro completo
|
||||
-- vai so pro log (TB_26AI_TECH_LOG); o usuario ve uma mensagem amigavel.
|
||||
IF p_source_type = 'VUL' THEN
|
||||
UPDATE TB_26AI_TECH_v2
|
||||
SET insight_report = v_error,
|
||||
SET insight_report = 'Nao foi possivel gerar o insight para este registro no momento.',
|
||||
insight_json = null
|
||||
WHERE rowid = p_rowid;
|
||||
ELSIF p_source_type = 'SYS' THEN
|
||||
UPDATE TB_26AI_TECH_SYS
|
||||
SET insight_report = v_error,
|
||||
SET insight_report = 'Nao foi possivel gerar o insight para este registro no momento.',
|
||||
insight_json = null
|
||||
WHERE rowid = p_rowid;
|
||||
END IF;
|
||||
|
||||
@@ -50,7 +50,8 @@ rapidamente qualquer problema, e o checklist abaixo para os casos mais comuns.</
|
||||
<tr><td><code>ORA-00942</code> em qualquer objeto <code>TB_26AI_TECH_*</code></td><td>Conectado como <code>ADMIN</code> em vez de <code>AMPMINSIGHTS</code>.</td><td>Rode <code>SELECT USER FROM DUAL;</code> — tem que voltar <code>AMPMINSIGHTS</code>. Reconecte e repita a seção que falhou.</td></tr>
|
||||
<tr><td>"AI Insight"/chat sempre retorna um texto genérico de indisponibilidade</td><td>Credencial <code>OCI_CRED</code> ausente ou quebrada.</td><td><code>SELECT credential_name FROM user_credentials WHERE credential_name = 'OCI_CRED';</code> — se não retornar linha, refaça a Seção 3 conectado como <code>AMPMINSIGHTS</code>. Depois, confira o motivo exato na consulta de "Erros recentes" abaixo.</td></tr>
|
||||
<tr><td>Erro de rede/timeout ao chamar o Generative AI</td><td>ACL de rede (Seção 1.6) não cobre o host correto.</td><td><code>SELECT host, privilege FROM dba_host_aces WHERE principal = 'AMPMINSIGHTS';</code> — deve listar <code>inference.generativeai.us-chicago-1.oci.oraclecloud.com</code> com <code>RESOLVE</code> e <code>CONNECT</code>.</td></tr>
|
||||
<tr><td><code>ORA-20404</code> ("Object not found", domínio <code>oci.my$cloud_domain</code>)</td><td>Perfil de SELECT AI usando a região "de casa" do tenancy em vez da região do Generative AI.</td><td>A região do Generative AI já vem fixa (<code>us-chicago-1</code>) na Seção 5.3 do <a href="04-passo-a-passo-banco.html">Passo a passo: banco de dados</a> — não troque pelo valor de <code>OCI_REGION</code>.</td></tr>
|
||||
<tr><td><code>ORA-20404</code> ("Object not found", domínio <code>oci.my$cloud_domain</code>)</td><td>Perfil de SELECT AI usando a região "de casa" do tenancy (<code>OCI_REGION</code>) em vez da região do Generative AI.</td><td>Use o valor de <code>GENAI_REGION</code> (Seção 2), não <code>OCI_REGION</code> — ver Seção 5.3 do <a href="04-passo-a-passo-banco.html">Passo a passo: banco de dados</a>.</td></tr>
|
||||
<tr><td><code>ORA-20404</code> com URL bem formada (região correta no domínio)</td><td>A tenancy não alcança a região configurada em <code>GENAI_REGION</code>, ou o modelo não está mais disponível para uso on-demand nessa região (a disponibilidade de modelos varia por região e muda com o tempo).</td><td>Rode <code>oci generative-ai model-collection list-models --compartment-id <seu-compartimento> --region <regiao-candidata> --capability CHAT --all</code> (ou o Console OCI) e confirme que o modelo usado está <code>ACTIVE</code> e sem <code>time-on-demand-retired</code> preenchido nessa região; ajuste <code>GENAI_REGION</code> (e a ACL da Seção 1.6 para o novo host) para uma região que sua tenancy alcance e que ainda sirva o modelo on-demand.</td></tr>
|
||||
</table>
|
||||
</div>
|
||||
|
||||
|
||||
@@ -103,9 +103,15 @@ GRANT CREATE CREDENTIAL TO AMPMINSIGHTS;
|
||||
GRANT CREATE JOB TO AMPMINSIGHTS;
|
||||
|
||||
-- 1.6) Regras de rede (ACL) para o schema poder chamar o endpoint do OCI
|
||||
-- Generative AI usado neste script (regiao us-chicago-1). Se voce for
|
||||
-- usar outra regiao de Generative AI, ajuste o host abaixo (e repita
|
||||
-- este bloco para cada host adicional que for necessario).
|
||||
-- Generative AI usado neste script (regiao us-chicago-1 por padrao - o
|
||||
-- mesmo valor que vai para o parametro GENAI_REGION da SECAO 2, que
|
||||
-- ainda nao existe neste ponto do script, por isso o host aqui e
|
||||
-- digitado direto). Nem toda tenancy alcanca us-chicago-1 (ex.: algumas
|
||||
-- tenancies com escopo regional restrito, como America Latina, podem
|
||||
-- so alcancar sa-saopaulo-1) - se for o seu caso, troque o host abaixo
|
||||
-- pela regiao que a sua tenancy alcanca, E use o mesmo valor no
|
||||
-- parametro GENAI_REGION da SECAO 2 (repita este bloco para cada host
|
||||
-- adicional que for necessario).
|
||||
BEGIN
|
||||
DBMS_NETWORK_ACL_ADMIN.APPEND_HOST_ACE(
|
||||
host => 'inference.generativeai.us-chicago-1.oci.oraclecloud.com',
|
||||
@@ -201,6 +207,10 @@ INSERT INTO TB_26AI_TECH_PARAMS (PARAM_NAME, PARAM_VALUE, DESCRIPTION) VALUES
|
||||
('AI_LOG_RETENTION_DAYS', '90',
|
||||
'Dias de retencao do log de chamadas de IA/embeddings (TB_26AI_TECH_LOG) - ver docs/09-operacao-observabilidade.html para a query de purga.');
|
||||
|
||||
INSERT INTO TB_26AI_TECH_PARAMS (PARAM_NAME, PARAM_VALUE, DESCRIPTION) VALUES
|
||||
('GENAI_REGION', 'us-chicago-1',
|
||||
'Regiao do OCI Generative AI usada pelo RAG/insights/embeddings (SECAO 5+). Pode ser diferente da OCI_REGION (que e a regiao "de casa" do seu tenancy/bucket) - o Generative AI so roda em regioes especificas. Se a sua tenancy nao alcancar us-chicago-1 (comum em tenancies com escopo regional restrito, ex. America Latina), troque para uma regiao que a sua tenancy alcance (ex. sa-saopaulo-1) E repita a ACL da SECAO 1.6 para o novo host - confirme antes com "oci generative-ai model-collection list-models" ou o Console OCI que o modelo usado (meta.llama-4-maverick-17b-128e-instruct-fp8) ainda esta ativo para uso on-demand na regiao escolhida, ja que a disponibilidade de modelos varia por regiao e muda com o tempo.');
|
||||
|
||||
COMMIT;
|
||||
|
||||
-- Confira: nenhuma linha abaixo deve ainda mostrar um valor "<SUBSTITUA...>"
|
||||
@@ -340,14 +350,15 @@ WHERE model_name = 'CLIP_VIT_LARGE_PATCH14_TXT';
|
||||
-- Rode os 3 blocos abaixo para confirmar que a credencial e a rede estao OK
|
||||
-- antes de seguir para as tabelas e o PL/SQL da aplicacao.
|
||||
|
||||
-- 5.1) Teste de embedding (Cohere, via OCI Generative AI)
|
||||
-- 5.1) Teste de embedding (Cohere, via OCI Generative AI). A URL usa a
|
||||
-- regiao configurada em GENAI_REGION (SECAO 2), nao um valor fixo.
|
||||
SELECT VECTOR_SERIALIZE(
|
||||
DBMS_VECTOR_CHAIN.UTL_TO_EMBEDDING(
|
||||
TO_CLOB('Teste simples para gerar um embedding.'),
|
||||
JSON('{
|
||||
"provider": "ocigenai",
|
||||
"credential_name": "OCI_CRED",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
@@ -355,13 +366,14 @@ SELECT VECTOR_SERIALIZE(
|
||||
) AS embedding
|
||||
FROM dual;
|
||||
|
||||
-- 5.2) Teste de geracao de texto (Llama 4, via OCI Generative AI)
|
||||
-- 5.2) Teste de geracao de texto (Llama 4, via OCI Generative AI). Mesma
|
||||
-- logica: a URL usa a regiao configurada em GENAI_REGION (SECAO 2).
|
||||
SELECT DBMS_VECTOR_CHAIN.UTL_TO_GENERATE_TEXT(
|
||||
TO_CLOB('Responda somente com a palavra: sucesso'),
|
||||
JSON('{
|
||||
"provider": "ocigenai",
|
||||
"credential_name": "OCI_CRED",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8",
|
||||
"chatRequest": {
|
||||
"temperature": 0.1,
|
||||
@@ -373,27 +385,28 @@ SELECT DBMS_VECTOR_CHAIN.UTL_TO_GENERATE_TEXT(
|
||||
FROM dual;
|
||||
|
||||
-- 5.3) Teste de SELECT AI (perguntas em linguagem natural sobre as views/
|
||||
-- tabelas do schema). O bloco abaixo le EMBEDDING_COMPARTMENT da tabela
|
||||
-- de configuracao (SECAO 2). As tabelas/view referenciadas abaixo sao
|
||||
-- criadas na SECAO 6 - rode este bloco depois de criar V_26AI_TECH e
|
||||
-- TB_26AI_TECH_CMDB.
|
||||
-- tabelas do schema). O bloco abaixo le EMBEDDING_COMPARTMENT e
|
||||
-- GENAI_REGION da tabela de configuracao (SECAO 2). As tabelas/view
|
||||
-- referenciadas abaixo sao criadas na SECAO 6 - rode este bloco depois
|
||||
-- de criar V_26AI_TECH e TB_26AI_TECH_CMDB.
|
||||
--
|
||||
-- A regiao do OCI Generative AI abaixo (us-chicago-1) e fixa de
|
||||
-- proposito, igual nos testes 5.1/5.2 e na ACL da SECAO 1.6 - nao
|
||||
-- precisa (nem deve) ser trocada pelo valor de OCI_REGION da tabela de
|
||||
-- configuracao, ja que o servico so esta disponivel em algumas regioes
|
||||
-- especificas da OCI.
|
||||
-- A regiao do OCI Generative AI abaixo vem do parametro GENAI_REGION -
|
||||
-- nao precisa (nem deve) ser trocada pelo valor de OCI_REGION da tabela
|
||||
-- de configuracao (sao coisas diferentes de proposito), ja que o
|
||||
-- servico so esta disponivel em algumas regioes especificas da OCI.
|
||||
DECLARE
|
||||
v_compartment TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
BEGIN
|
||||
SELECT param_value INTO v_compartment FROM TB_26AI_TECH_PARAMS WHERE param_name = 'EMBEDDING_COMPARTMENT';
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
DBMS_CLOUD_AI.CREATE_PROFILE(
|
||||
profile_name => 'OCI_CRED2',
|
||||
attributes => '{
|
||||
"provider": "oci",
|
||||
"credential_name": "OCI_CRED",
|
||||
"region": "us-chicago-1",
|
||||
"region": "' || v_genai_region || '",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8",
|
||||
"temperature": 0,
|
||||
"comments": true,
|
||||
@@ -752,7 +765,7 @@ BEGIN
|
||||
dbms_vector_chain.utl_to_text( v_string ),
|
||||
json('{ "provider": "ocigenai",
|
||||
"credential_name": "' || p_credential || '",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || (SELECT param_value FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION') || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
@@ -842,9 +855,12 @@ RETURN CLOB IS
|
||||
output CLOB;
|
||||
query_vec VECTOR;
|
||||
v_llm VARCHAR2(20) := 'LLAMA4'; -- [ LLAMA4 | OPENAI ]
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
|
||||
BEGIN
|
||||
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
-- embedding da pergunta do usuario
|
||||
query_vec := to_vector( fnc_26ai_embed ( p_string => p_query, p_emb_type => 'COHERE' ) ) ;
|
||||
|
||||
@@ -870,7 +886,7 @@ BEGIN
|
||||
params_genai := '{
|
||||
"provider" : "ocigenai",
|
||||
"credential_name" : "' || p_credential || '",
|
||||
"url" : "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"url" : "https://inference.generativeai.' || v_genai_region || '.oci.oraclecloud.com/20231130/actions/chat",
|
||||
"model": "meta.llama-4-maverick-17b-128e-instruct-fp8"}';
|
||||
|
||||
ELSIF v_llm = 'OPENAI' THEN
|
||||
@@ -984,12 +1000,16 @@ RETURN CLOB AS
|
||||
Objetivo: funcao global de chamada ao LLM (Llama 4, via OCI Generative AI)
|
||||
usada pelo RAG e pela geracao de insights.
|
||||
*/
|
||||
v_gen_ai_endpoint VARCHAR2(500) := 'https://inference.generativeai.us-chicago-1.oci.oraclecloud.com';
|
||||
v_gen_ai_endpoint VARCHAR2(500);
|
||||
v_gen_ai_model VARCHAR2(500) := 'meta.llama-4-maverick-17b-128e-instruct-fp8';
|
||||
resp DBMS_CLOUD_TYPES.RESP;
|
||||
v_t0 PLS_INTEGER := DBMS_UTILITY.GET_TIME;
|
||||
v_result CLOB;
|
||||
BEGIN
|
||||
SELECT 'https://inference.generativeai.' || param_value || '.oci.oraclecloud.com'
|
||||
INTO v_gen_ai_endpoint
|
||||
FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
resp := dbms_cloud.send_request(
|
||||
credential_name => p_oci_cred,
|
||||
uri => v_gen_ai_endpoint || '/20231130/actions/chat',
|
||||
@@ -1090,8 +1110,11 @@ AS
|
||||
v_response CLOB;
|
||||
v_json CLOB;
|
||||
v_error CLOB;
|
||||
v_genai_region TB_26AI_TECH_PARAMS.PARAM_VALUE%TYPE;
|
||||
BEGIN
|
||||
|
||||
SELECT param_value INTO v_genai_region FROM TB_26AI_TECH_PARAMS WHERE param_name = 'GENAI_REGION';
|
||||
|
||||
IF p_source_type = 'VUL' THEN -- vulnerabilidades
|
||||
|
||||
v_pre_prompt :='Voce e um analista senior de dados e operacoes.
|
||||
@@ -1488,7 +1511,7 @@ Retorne um JSON valido (sem comentarios), espelhando o relatorio:
|
||||
( v_response ) ,
|
||||
json('{ "provider": "ocigenai",
|
||||
"credential_name": "' || p_oci_cred || '",
|
||||
"url": "https://inference.generativeai.us-chicago-1.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"url": "https://inference.generativeai.' || v_genai_region || '.oci.oraclecloud.com/20231130/actions/embedText",
|
||||
"model": "cohere.embed-v4.0"
|
||||
}')
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user