Appliquer l'isolation de la mémoire des utilisateurs finaux avec Deep Data Security
Ce guide explique comment appliquer l'isolement de l'utilisateur final pour une application Oracle AI Agent Memory avec OCI IAM et Oracle Deep Data Security.
Avertissement : environnement de formation uniquement. Ne déployez pas cet exemple en production.
L'application utilise le serveur de développement de Flask, une banque de sessions en mémoire, des clés secrètes de fichier d'environnement et une gestion simplifiée du cycle de vie des jetons. Les scripts de configuration de la base de données modifient les paramètres et les privilèges du fournisseur d'identités à l'échelle de la base de données. Utilisez uniquement des utilisateurs jetables et une base de données Oracle Autonomous AI Database isolée et hors production.
Ce guide crée une application Web délibérément petite :
- Les utilisateurs se connectent avec le flux de code d'autorisation OAuth 2.0 OCI IAM.
- Cette page répertorie uniquement les mémoires visibles par l'utilisateur connecté.
- Un formulaire ajoute une mémoire et expose sa cible
username. Alice peut stocker une mémoire pour Alice, mais Oracle AI Database rejette la tentative d'Alice d'en stocker une pour Bob.
La route ne compare pas Alice et Bob lui-même. Il transmet le jeton de l'utilisateur final à Oracle AI Database, où Oracle Deep Data Security applique la stratégie de ligne propre de la mémoire de l'agent.
Ce guide présente un déploiement. Pour bénéficier de toutes les fonctionnalités de sécurité prises en charge, notamment toutes les stratégies, tous les principaux, toutes les fonctions d'administration, toutes les API de contexte d'exécution, tous les audits et toutes les dates de révocation, reportez-vous à la référence de sécurité et à l'API Deep Data Security.
Dans ce guide, vous allez :
- inscrire une ressource de base de données et une application Web dans un domaine dʼidentité OCI IAM ;
- ajouter la demande de jeton
groupOCI IAM utilisée pour activer les rôles de données de base de données ; - configurer des comptes de base de données dʼadministrateur de sécurité, de propriétaire de schéma et de pool dʼapplications distincts ;
- créer une banque de mémoire d'agent et accorder sa propre stratégie de ligne à un groupe OCI IAM ;
- Exécuter l'application Web et vérifier l'isolement des utilisateurs par la base de données.
Comprendre la chaîne de confiance
Le navigateur et l'application utilisent deux jetons d'accès OAuth différents :
- Le jeton d'utilisateur final identifie Alice ou Bob et inclut les groupes IAM de l'utilisateur.
- Le jeton d'accès à la base de données, obtenu par l'application confidentielle via les informations d'identification client, prouve que l'application peut accéder à la ressource de base de données.
Oracle AI Database valide les deux jetons avant d'associer le contexte de sécurité de l'utilisateur final.
Oracle documente ce modèle à deux jetons dans Comprendre le flux d'authentification et les prérequis et le cycle de vie complet dans le contexte de sécurité de l'utilisateur final.
Prérequis
Vous devez :
- une version isolée d'Oracle Autonomous AI Database qui prend en charge Oracle Deep Data Security ;
- un domaine d'identité OCI IAM dans la même location, avec le droit de gérer les applications, les utilisateurs, les groupes et les réclamations personnalisées ;
- un compte dʼadministrateur de sécurité de base de données existant, normalement
ADMINsur Autonomous AI Database ; - SQL*Plus sur
PATHet une configuration de portefeuille ou de connexion TLS de base de données Autonomous AI ; - Python 3.10 à 3.14,
uvet ce référentiel.
Oracle Deep Data Security est une autorisation détaillée appliquée par la base de données. Reportez-vous à Qu'est-ce qu'Oracle Deep Data Security.
Configurer le domaine d'identité OCI IAM
Tous les services OCI IAM fonctionnent dans un domaine d'identité. Enregistrez son URL de domaine, par exemple https://idcs-<id>.identity.oraclecloud.com:443.
La procédure pas à pas Oracle faisant autorité est Configurer OCI IAM pour l'accès résolu par l'application. Les valeurs de l'exemple suivant correspondent à l'exemple de fichier d'environnement fourni avec ce guide.
Inscrire la ressource de base de données
Dans Domaine d'identité > Applications intégrées :
- Ajoutez une application confidentielle nommée
OracleDB. - Configurez-le en tant que serveur de ressources :
- Public principal :
OracleDB - Portée :
DB_ACCESS_SCOPE
- Public principal :
- Configurez-le en tant que client et autorisez les informations d'identification client.
- Activer.
- Enregistrez son ID d'application, son ID client et sa clé secrète client.
La portée de base de données entièrement qualifiée est l'audience concaténée avec le nom de la portée :
OracleDBDB_ACCESS_SCOPE
Suivez Inscription de la base de données dans OCI IAM pour obtenir les libellés de console en cours et la description des champs.
Enregistrer l'application Web
Ajoutez une deuxième application confidentielle nommée OracleAgentMemoryWeb :
- Activer Mettre en œuvre les octrois en tant qu'autorisation.
- Configurez-le en tant que serveur de ressources :
- Public principal :
OracleAgentMemoryWeb - Portée :
APP_ACCESS_SCOPE - Durée de vie du jeton d'accès :
3600secondes pour cet exercice
- Public principal :
- Configurez-le en tant que client avec les autorisations suivantes :
- Code d'autorisation
- Informations d'identification client
- Ajoutez cette URL de réacheminement exacte :
http://127.0.0.1:8000/auth/callback - Dans les ressources client, accordez l'accès aux deux éléments suivants :
OracleDBDB_ACCESS_SCOPEOracleAgentMemoryWebAPP_ACCESS_SCOPE
- Activez l'application et enregistrez son ID client et sa clé secrète client.
L'application utilise le code d'autorisation avec state et PKCE S256. OCI IAM documente la configuration client requise dans Inscription de l'application dans OCI IAM et fournit un exemple de code d'autorisation PKCE.
Ajouter la réclamation de groupe
Oracle AI Database active les rôles de données mis en correspondance en externe à partir de la demande group du jeton de l'utilisateur final. Les demandes personnalisées OCI IAM sont configurées via l'API REST de domaine d'identité, et non via la console.
En tant qu'administrateur de domaine d'identité, téléchargez un jeton d'accès personnel de courte durée qui peut appeler des API de domaine d'identité. Exécutez ensuite :
export OCI_IAM_DOMAIN_URL='https://<identity-domain-host>:443'
export OCI_IAM_ADMIN_TOKEN='<short-lived-personal-access-token>'
curl --fail-with-body \
-X POST "$OCI_IAM_DOMAIN_URL/admin/v1/CustomClaims" \
-H "Authorization: Bearer $OCI_IAM_ADMIN_TOKEN" \
-H "Content-Type: application/scim+json" \
-d '{
"schemas": [
"urn:ietf:params:scim:schemas:oracle:idcs:CustomClaim"
],
"name": "group",
"value": "$user.groups.*.display",
"expression": true,
"mode": "always",
"tokenType": "AT",
"allScopes": true
}'
Une demande réussie renvoie une valeur HTTP 201. Ne créez pas de doublon si le domaine a déjà cette réclamation. Reportez-vous à Configuration de demandes personnalisées pour les informations de groupe dans OCI IAM.
Créer Alice, Bob et le groupe d'applications
- Créez un groupe nommé
ORACLEAGENTMEMORY_USERS. - Créez les utilisateurs de test
aliceetbob. - Affectez les deux utilisateurs à
ORACLEAGENTMEMORY_USERS. - Affectez le groupe à
OracleAgentMemoryWeb.
La base de données mappera ultérieurement ce nom de groupe avec un rôle de données. Les noms de groupe sont comparés sans tenir compte de la casse, mais ils utilisent la même orthographe tout au long de la configuration. Reportez-vous à Création d'utilisateurs et affectation de groupes dans OCI IAM.
Préparer l'environnement
Téléchargez l'application Web complète, deepsec_oci_iam_webapp.zip. L'archive contient également des scripts de configuration et d'inspection de base de données autonomes appartenant à cet exemple. Ils n'importent ni ne package de scripts à partir de la suite de tests SDK.
Extrayez l'archive, entrez son répertoire de projet et créez des fichiers d'environnement de configuration et d'exécution locaux :
unzip deepsec_oci_iam_webapp.zip
cd deepsec_oci_iam_webapp
cp deepsec.env.example .deepsec.env
cp deepsec.runtime.env.example .deepsec.runtime.env
python -c "import secrets; print(secrets.token_hex(32))"
Placez la valeur générée dans OAM_WEB_SECRET_KEY et renseignez tous les espaces réservés requis dans les deux fichiers. Les deux noms de fichiers sont ignorés par Git.
Le répertoire database_scripts contient :
| Fichier | Responsabilité |
|---|---|
_common.sh |
Aide privée qui charge .deepsec.env, valide les valeurs requises, recherche SQL*Plus et exporte TNS_ADMIN lorsqu'elle est configurée. Ne l'exécutez pas directement. |
db_ociiam_setup.sh |
Active l'authentification externe OCI IAM pour la base de données Autonomous AI cible et remplace OCI_IAM_DOMAIN_DB_CRED$. |
db_deepsec_user_setup.sh |
Crée les utilisateurs de propriétaire de schéma et de pool d'applications et accorde leurs listes d'autorisation de privilèges documentées. |
db_list_all_data_roles.sh |
Effectue une inspection en lecture seule des rôles Deep Data Security, des correspondances IAM, des autorisations d'accès aux données, des prédicats, des objets protégés, des utilisateurs finaux et des identités d'application. |
.deepsec.env est utilisé uniquement par la configuration de la base de données. Il inclut les mots de passe d'administrateur de sécurité et de propriétaire de schéma. .deepsec.runtime.env est chargé par le processus Flask et exclut intentionnellement les deux mots de passe privilégiés. N'exportez pas le fichier de configuration dans le shell qui démarre l'application Web. Pour utiliser différents chemins, définissez OAM_DEEPSEC_ENV_FILE pour la configuration ou OAM_WEB_ENV_FILE pour le processus Web.
Les valeurs IAM importantes sont mises en correspondance comme suit :
| Variable d'environnement | Valeur OCI IAM |
|---|---|
OAM_DEEPSEC_OCI_DB_APP_ID |
ID application de l'application de base de données |
OAM_DEEPSEC_OCI_DB_CLIENT_ID |
ID client de l'application de base de données |
OAM_DEEPSEC_OCI_DB_CLIENT_SECRET |
Clé secrète client de l'application de base de données |
OAM_WEB_OCI_CLIENT_ID |
ID client de l'application Web |
OAM_WEB_OCI_CLIENT_SECRET |
Clé secrète client de l'application Web |
OAM_WEB_OCI_END_USER_SCOPE |
OracleAgentMemoryWebAPP_ACCESS_SCOPE |
OAM_WEB_OCI_DATABASE_ACCESS_SCOPE |
OracleDBDB_ACCESS_SCOPE |
OAM_DEEPSEC_CONFIG_DIR n'est nécessaire que lorsque le DSN est un alias TNS dont tnsnames.ora n'est pas autrement repérable. L'emplacement du portefeuille et le mot de passe sont facultatifs lorsque sqlnet.ora et le DSN fournissent déjà tout ce dont python-oracledb a besoin. Pour les options de connexion à la base de données Autonomous AI, reportez-vous à Connexion d'applications Python à un portefeuille.
Configurez également un fournisseur d'intégration. L'application répertorie et ajoute uniquement des mémoires, mais la mémoire de l'agent crée toujours des incorporations lorsqu'elle stocke le contenu de la mémoire. Le modèle utilise un modèle compatible OpenAI comme exemple ; remplacez le modèle, la base d'API, la clé et la dimension par les valeurs de votre fournisseur.
Configurer les trois comptes de base de données
Avertissement : les commandes de cette section modifient les paramètres d'authentification externe et les privilèges de compte à l'échelle de la base de données. Examinez d'abord les scripts. Ne les exécutez pas sur une base de données partagée ou de production.
Utilisez trois utilisateurs de base de données distincts :
| Responsabilité | Exemple de compte | Travail autorisé |
|---|---|---|
| Administrateur de sécurité | ADMIN |
Active l'intégration OCI IAM et crée, accorde, révoque, répertorie et supprime les rôles de données et les autorisations d'accès aux données. Il n'est jamais utilisé pour les requêtes Web. |
| Propriétaire du schéma géré | OAM_SCHEMA_OWNER |
Crée des tables de mémoire d'agent, des index, des procédures et des travaux de planificateur. Il est utilisé uniquement pour les opérations de cycle de vie de schéma. |
| Utilisateur de la BdD d'application | OAM_APP_DB_USER |
Ouvre les sessions et joint les contextes de sécurité de l'utilisateur final. Il ne reçoit aucun privilège SELECT, INSERT, UPDATE ou DELETE ordinaire. |
Cette séparation entraîne la fermeture d'une demande sans contexte d'utilisateur final valide. Le guide de configuration de base de données d'Oracle recommande CREATE SESSION et CREATE END USER SECURITY CONTEXT pour le compte de pool de connexions. Reportez-vous à Configuration de la base de données pour l'intégration IAM.
L'exemple utilise le compte Autonomous AI Database ADMIN pour la configuration. Un compte d'administrateur de sécurité personnalisé doit pouvoir créer et modifier les deux utilisateurs de base de données et accorder leurs privilèges système répertoriés. Etant donné que les tables de mémoire d'agent appartiennent à un schéma distinct, l'administration des stratégies requiert CREATE ANY DATA GRANT, DROP ANY DATA GRANT et ADMINISTER ANY DATA GRANT plutôt que seulement CREATE DATA GRANT dans le schéma de l'administrateur. Elle doit également être autorisée à créer et à supprimer les rôles de données utilisés par les stratégies.
Activer la validation de jeton OCI IAM
Vérifier et exécuter :
bash database_scripts/db_ociiam_setup.sh
Le script se connecte en tant qu'administrateur de sécurité et :
- appelle
DBMS_CLOUD_ADMIN.ENABLE_EXTERNAL_AUTHENTICATIONavec l'ID et l'URL de domaine d'identité de l'application de base de données ; - crée les informations d'identification
OCI_IAM_DOMAIN_DB_CRED$cryptées avec l'ID client et la clé secrète de l'application de base de données ; - imprime les paramètres de fournisseur d'identités qui en résultent.
Un seul fournisseur d'identités externe peut être actif. L'exemple de script utilise force => TRUE pour mettre à jour les paramètres OCI IAM, ce qui peut perturber une autre configuration d'authentification externe. Oracle documente les appels Autonomous Database exacts dans Configuration de la base de données pour l'intégration IAM.
Créer le propriétaire et les utilisateurs du pool
Vérifier et exécuter :
bash database_scripts/db_deepsec_user_setup.sh
Le script ne modifie pas ADMIN. Il crée les utilisateurs propriétaire et de pool d'applications et accorde les droits suivants :
-- Managed-schema owner
CREATE SESSION, CREATE TABLE, CREATE SEQUENCE,
CREATE VIEW, CREATE PROCEDURE, CREATE JOB
-- Runtime application pool
CREATE SESSION, CREATE END USER SECURITY CONTEXT
Le propriétaire reçoit un quota sur le tablespace DATA de la base de données Autonomous AI. L'utilisateur du pool ne reçoit aucun privilège direct sur les tables du propriétaire. Pour que l'exemple reste centré sur les instructions requises, le script ne recherche pas les utilisateurs existants ni n'inspecte leurs privilèges actuels. Utilisez les nouveaux noms de compte ; le script s'arrête si l'utilisateur existe déjà ou si une autre instruction SQL échoue.
Créer la stratégie de stockage et de ligne propre
Installez l'exemple d'environnement autonome :
uv sync
Exécutez ensuite le programme de paramétrage :
uv run python scripts/setup_memory.py
Cette commande est intentionnellement destructive uniquement pour OAM_WEB_MEMORY_STORE_ID. Elle :
- se connecte en tant que propriétaire du schéma pour recréer le schéma de mémoire dʼagent ;
- se connecte en tant qu'administrateur de sécurité pour ajouter la stratégie de ligne propre et l'accorder à
ORACLEAGENTMEMORY_USERS.
Les appels d'administration d'ajout et d'octroi sont idempotents. Le fait de les réexécuter remplace les mêmes définitions et affectations de stratégie gérée, et de réessayer de réparer le DDL partiellement géré laissé par une tentative interrompue.
La stratégie crée un rôle de données mis en correspondance en externe pour le groupe OCI IAM et les autorisations de données dont le prédicat de ligne compare les valeurs user_id stockées à ORA_END_USER_CONTEXT.username. Oracle documente la syntaxe de mise en correspondance dans CREATE DATA ROLE et l'autorisation de ligne dans Créer des autorisations de données.
Examinez le résultat :
bash database_scripts/db_list_all_data_roles.sh
Vous devez voir le rôle mis en correspondance par IAM, les autorisations d'accès aux données de mémoire d'agent et leurs tables de schéma de propriétaire protégées. Ce script d'inspection interroge uniquement les vues de catalogue ; il ne crée, ne modifie ni ne supprime les objets Deep Data Security.
Utiliser un modèle d'intégration dans la base de données avec Deep Sec
Cette section s'applique lorsque l'application utilise OracleDBEmbedder avec la valeur par défaut provider="database" et un modèle d'intégration stocké dans Oracle AI Database, généralement un modèle ONNX importé tel que DMUSER.DOC_MODEL. Dans cette configuration, l'intégration directe utilise l'opérateur SQL VECTOR_EMBEDDING d'Oracle. Le modèle requiert donc le privilège SELECT ON MINING MODEL décrit ci-dessous.
OracleDBEmbedder prend également en charge les fournisseurs distants via DBMS_VECTOR_CHAIN.UTL_TO_EMBEDDING, par exemple avec provider="openai". Ces configurations appellent toujours la demande d'intégration à partir d'Oracle AI Database, mais elles n'accèdent pas à un modèle d'exploration de données résidant dans la base de données. Les instructions SELECT ON MINING MODEL de cette section ne s'appliquent pas. Les opérations de mémoire de l'agent doivent toujours être exécutées dans un fichier OracleMemoryEndUserSecurityContext.
Une stratégie de mémoire d'agent accorde l'accès aux tables de mémoire d'agent. Il n'accorde pas l'accès à un modèle d'intégration Oracle AI Database. Le modèle a besoin de son propre privilège de base de données : SELECT ON MINING MODEL.
N'accordez pas ce privilège à l'utilisateur de pool d'applications. Lors d'une demande, Deep Sec autorise l'utilisateur via le rôle de données mis en correspondance à partir du groupe OCI IAM, et non via les privilèges normaux de l'utilisateur du pool. Un privilège accordé uniquement à l'utilisateur du pool n'est donc pas disponible alors qu'un contexte de sécurité de l'utilisateur final est actif.
Créez un rôle de données mis en correspondance pour chaque groupe IAM qui doit utiliser le modèle. Attribuez à ce rôle de données un rôle de base de données normal qui a accès au modèle. Exécutez l'instruction SQL suivante en tant qu'administrateur de la sécurité de base de données ou compte autorisé à créer des rôles et à accorder l'accès au modèle. Remplacez les noms d'exemple par les noms de votre application :
-- This must exactly match the OCI IAM group passed to OciGroupPrincipal.
CREATE DATA ROLE APP_MEMORY_USERS_DATA_ROLE
MAPPED TO 'IAM_OAUTH_GROUP=YOUR_IAM_GROUP';
-- This ordinary database role carries access to one embedding model.
CREATE ROLE APP_DOC_MODEL_ROLE;
GRANT SELECT ON MINING MODEL YOUR_USER.DOC_MODEL
TO APP_DOC_MODEL_ROLE;
-- Give model access to the IAM group's Deep Sec data role.
GRANT APP_DOC_MODEL_ROLE TO APP_MEMORY_USERS_DATA_ROLE;
L'application utilise ensuite le même nom de groupe lorsqu'elle octroie des stratégies de mémoire d'agent :
grant_agent_memory_policies(
admin_connection,
owner_schema="OAM_SCHEMA_OWNER",
memory_store_id="MEMORY",
principals=[OciGroupPrincipal("YOUR_IAM_GROUP")],
policies=[UserOwnRowsDeepDataSecurityPolicy()],
)
grant_agent_memory_policies() recherche le rôle existant mis en correspondance avec YOUR_IAM_GROUP et ajoute les autorisations d'accès aux données de la table de mémoire d'agent à ce même rôle. Ce rôle ne crée pas de second rôle. Lors de l'exécution, un utilisateur dont le jeton OCI IAM contient YOUR_IAM_GROUP peut accéder à la fois aux lignes de mémoire d'agent autorisées et à DMUSER.DOC_MODEL.
Si l'application a déjà appelé grant_agent_memory_policies() avant cette configuration de modèle, la mémoire de l'agent a déjà créé le rôle de données mis en correspondance. Ne créez pas un autre rôle mappé pour le même groupe. Recherchez le rôle existant et accordez-lui le rôle de modèle ordinaire :
SELECT data_role
FROM sys.dba_data_roles
WHERE UPPER(mapped_to) = UPPER('IAM_OAUTH_GROUP=YOUR_IAM_GROUP');
GRANT APP_DOC_MODEL_ROLE TO <DATA_ROLE_RETURNED_BY_THE_QUERY>;
Conservez chaque opération OracleDBEmbedder d'exécution dans OracleMemoryEndUserSecurityContext. N'utilisez pas le propriétaire du schéma, une connexion administrateur distincte ou une connexion sans contexte de sécurité de l'utilisateur final pour exécuter des incorporations pour une demande utilisateur. Cela contournerait la limite d'autorisation de Deep Sec.
Comprendre l'application
Le projet téléchargeable, deepsec_oci_iam_webapp.zip, contient l'application Web complète et les scripts de base de données. Les pièces d'application clés sont délibérément petites.
Démarrer et terminer OAuth
La route de connexion crée des valeurs state et PKCE aléatoires. Seul l'ID de session opaque est placé dans un cookie HttpOnly, SameSite=Lax ; les jetons restent dans la banque de sessions de démonstration locale du processus.
def start_authorization(config: RuntimeConfig) -> AuthorizationRequest:
"""Build a state-bound Authorization Code request with PKCE."""
state = secrets.token_urlsafe(32)
code_verifier = secrets.token_urlsafe(64)
challenge = (
base64.urlsafe_b64encode(hashlib.sha256(code_verifier.encode()).digest())
.rstrip(b"=")
.decode("ascii")
)
query = urllib.parse.urlencode(
{
"client_id": config.oauth_client_id,
"response_type": "code",
"redirect_uri": config.redirect_uri,
"scope": config.end_user_scope,
"state": state,
"code_challenge": challenge,
"code_challenge_method": "S256",
}
)
return AuthorizationRequest(
url=f"{config.domain_url}/oauth2/v1/authorize?{query}",
state=state,
code_verifier=code_verifier,
)
def exchange_authorization_code(
config: RuntimeConfig,
code: str,
code_verifier: str,
) -> EndUserToken:
"""Exchange one browser authorization code for an end-user token."""
payload = _token_request(
config,
{
"grant_type": "authorization_code",
"code": code,
"redirect_uri": config.redirect_uri,
"code_verifier": code_verifier,
},
)
access_token, expires_at = _required_access_token(payload)
return EndUserToken(
access_token=access_token,
username=_display_username(access_token),
expires_at=expires_at,
)
Le callback compare state en temps constant et échange le code avec les mêmes URI de redirection et vérificateur PKCE. L'application obtient séparément un jeton d'accès à la base de données :
def get(self, config: RuntimeConfig) -> str:
"""Return a current database-access token."""
with self._lock:
if self._token is not None and time.time() < self._expires_at - 60:
return self._token
payload = _token_request(
config,
{
"grant_type": "client_credentials",
"scope": config.database_access_scope,
},
)
self._token, self._expires_at = _required_access_token(payload)
return self._token
OCI IAM documente les deux demandes de jeton dans Validation de la configuration OCI IAM.
Portée de chaque opération de mémoire d'agent
L'application combine les deux jetons dans un contexte de sécurité utilisateur final python-oracledb. Il étend ensuite chaque initialisation et opération de stockage avec OracleMemoryEndUserSecurityContext :
def list_visible_memories(
config: RuntimeConfig,
pool: Any,
user_context: Any,
) -> list[Any]:
"""List rows visible to the effective OCI IAM end user."""
with OracleMemoryEndUserSecurityContext(user_context):
store = create_runtime_store(config, pool)
return store.list("memory", limit=100)
def add_memory(
config: RuntimeConfig,
pool: Any,
user_context: Any,
content: str,
target_username: str,
) -> None:
"""Attempt to insert a row for the username supplied by the browser."""
with OracleMemoryEndUserSecurityContext(user_context):
store = create_runtime_store(config, pool)
store.add(
contents=[content],
record_type="memory",
user_ids=[target_username],
)
La banque d'exécution utilise SchemaPolicy.NO_CHECK car la création, la validation, les mises à niveau et les recréations de schéma appartiennent au chemin de configuration du propriétaire de schéma. Le kit SDK rejette une autre stratégie de schéma tant que le contexte de l'utilisateur final est actif et rejette les opérations ultérieures sur cette banque d'exécution protégée lorsqu'aucun contexte n'est actif. Les fonctions d'administration de la sécurité rejettent également les connexions qui comportent un contexte utilisateur.
Pour chaque opération de base de données de la mémoire de l'agent, le gestionnaire de contexte :
- acquiert une connexion physique à partir du pool dʼapplications ;
- associe et vérifie le contexte de sécurité de l'utilisateur final prévu ;
- exécute du code SQL sous cette identité ;
- efface et vérifie le contexte avant de renvoyer la connexion.
Le compte de base de données du pool ne dispose pas des privilèges de table de restauration. L'API de charge utile python-oracledb est documentée dans Création de la charge utile de contexte de sécurité de l'utilisateur final. La référence de sécurité et d'API Deep Data Security explique le contrat complet du gestionnaire de contexte.
Laissez la base de données décider
Le routage transmet le nom d'utilisateur soumis sans modification. Il détecte et désactive les erreurs de base de données, mais il ne contient aucun branchement d'autorisation username == signed_in_user :
@web.route("/", methods=["GET", "POST"])
def index() -> Response | tuple[str, int]:
"""Show visible memories and let the user attempt one insert."""
config, pool, _ = _extensions()
_, session = _session()
if session is None or session.end_user_token is None:
return render_template("index.html", session=None, memories=[])
message = None
status = 200
try:
user_context = _security_context(config, session)
if request.method == "POST":
if not hmac.compare_digest(
request.form.get("csrf_token", ""),
session.csrf_token,
):
return render_template("error.html", message="The form expired."), 400
content = request.form.get("content", "").strip()
target_username = request.form.get("username", "").strip()
if not content or not target_username:
message = "Content and username are required."
status = 400
elif len(content) > 4000 or len(target_username) > 255:
message = "The submitted memory is too large."
status = 400
else:
try:
add_memory(
config,
pool,
user_context,
content,
target_username,
)
message = "Memory added."
except oracledb.DatabaseError:
#Keep listing permitted rows after the deliberately denied write.
message = "Oracle AI Database denied this operation for the effective end user."
status = 403
memories = list_visible_memories(config, pool, user_context)
except oracledb.DatabaseError:
#Never expose raw database errors, token contents, or submitted values.
message = "Oracle AI Database denied this operation for the effective end user."
memories = []
status = 403
except OAuthError:
message = "The login session expired. Sign in again."
memories = []
status = 401
return (
render_template(
"index.html",
session=session,
memories=memories,
message=message,
),
status,
)
Jinja échappe au contenu de mémoire affiché. Les exceptions de base de données brutes, les réponses OAuth, les jetons et les valeurs soumises ne sont jamais affichées.
Exécuter et vérifier l'application
Démarrez le serveur de développement Flask :
uv run python run.py
Ouvrez http://127.0.0.1:8000.
Vérifiez la limite d'autorisation :
- Connectez-vous avec Alice.
- Ajoutez
Alice's first memoryavec le nom utilisateur préremplialice. - Confirmez que la mémoire apparaît sous Mémoires visibles.
- Ajoutez
Alice tries to write for Bobmais remplacez le nom utilisateur parbob. - Confirmez qu'Oracle AI Database refuse l'opération.
- Déconnectez-vous, connectez-vous en tant que Bob et confirmez que la mémoire d'Alice n'est pas visible.
- Ajoutez une mémoire en tant que Bob, reconnectez-vous en tant qu'Alice et confirmez que la mémoire de Bob n'est pas visible.
Cela démontre deux contrôles indépendants :
SELECTrenvoie uniquement les lignes dontuser_idcorrespond à l'identité effective.INSERTne peut pas créer de ligne dontuser_idappartient à une autre identité.
Pour les opérations de production, configurez l'audit unifié Oracle pour l'administration Deep Sec et les actions de contexte de sécurité de l'utilisateur final que votre organisation doit conserver. Compte également pour le contrat de durée de révocation documenté : la révocation de stratégie SDK est validée avant le retour de l'appel d'administration, tandis que la suppression d'un utilisateur d'un groupe OCI IAM ne réécrit pas de jeton d'accès déjà émis. Reportez-vous à Sécurité profonde des données pour obtenir des conseils d'audit, un comportement d'expiration de jeton et des liens vers la documentation Oracle Deep Sec et OCI IAM correspondante.
Si la connexion réussit mais que la base de données refuse chaque opération, examinez le jeton de l'utilisateur final et vérifiez que group contient ORACLEAGENTMEMORY_USERS. Le dépannage des privilèges et des accès de sécurité des données profonds d'Oracle explique également comment un administrateur peut inspecter les rôles de données actifs.
Quelle production nécessite encore
Avertissement : La réalisation de ce guide ne rend pas l'exemple prêt pour la production.
Avant d'adapter la conception, remplacez ou ajoutez au moins :
- un serveur WSGI de production derrière TLS, une configuration proxy sécurisée et des cookies sécurisés ;
- un stockage de session côté serveur chiffré durable avec des contrôles dʼexpiration, de rotation, de propagation de déconnexion et de simultanéité ;
- un magasin secret géré au lieu de fichiers dotenv ;
- comportement de rafraîchissement ou de réauthentification, gestion de la révocation de jetons et expiration tenant compte de l'horloge ;
- limitation du débit, délais d'expiration des demandes, journalisation d'audit sans jetons ni contenu utilisateur, et surveillance opérationnelle ;
- CSRF spécifique au déploiement, stratégie de sécurité de contenu, en-têtes de sécurité, contraintes d'entrée et gestion des erreurs ;
- les procédures de migration et de changement de politique qui n'utilisent pas
RECREATE; - séparer les identités de déploiement et les limites réseau pour l'administration, la migration de schéma et l'exécution ;
- tests de simultanéité d'accès, d'annulation, de suppression de contexte et de changement d'identité pour la configuration réelle du serveur et du pool.
Conservez l'invariant de base : le compte de pool d'exécution ne dispose pas de privilèges LMD de table directe et chaque demande de mémoire d'agent s'exécute dans un fichier OracleMemoryEndUserSecurityContext vérifié.