Memorizzazione nella cache semantica con un endpoint privato (Private Service Connect)

Questa pagina si applica ad Apigee, ma non ad Apigee hybrid.

Visualizza la documentazione di Apigee Edge.

Questa pagina descrive come configurare e utilizzare i criteri di memorizzazione nella cache semantica di Apigee per attivare il riutilizzo intelligente delle risposte in base alla somiglianza semantica. In questo esempio, le policy eseguono la ricerca di similarità su un indice di ricerca vettoriale di cui è stato eseguito il deployment su un endpoint privato (Private Service Connect). L'utilizzo di queste policy nel proxy API Apigee riduce al minimo le chiamate API di backend ridondanti, la latenza e i costi operativi.

Prima di iniziare

Prima di iniziare, completa le seguenti attività:

  1. In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Roles required to select or create a project

    • Select a project: Selecting a project doesn't require a specific IAM role—you can select any project that you've been granted a role on.
    • Create a project: To create a project, you need the Project Creator role (roles/resourcemanager.projectCreator), which contains the resourcemanager.projects.create permission. Learn how to grant roles.

    Go to project selector

  2. Verify that billing is enabled for your Google Cloud project.

  3. Enable the Compute Engine, AI Platform, and Cloud Storage APIs.

    Roles required to enable APIs

    To enable APIs, you need the serviceusage.services.enable permission. If you created the project, then you likely already have this permission through the Owner role (roles/owner). Otherwise, you can get this permission through the Service Usage Admin role (roles/serviceusage.serviceUsageAdmin). Learn how to grant roles.

    Enable the APIs

  4. Abilita e configura l'API Vertex AI Text Embeddings nel tuo progetto Google Cloud .
  5. Crea (o accedi a) un indice di ricerca vettoriale di cui è stato eseguito il deployment su un endpoint privato (Private Service Connect). Questo tutorial non duplica i passaggi di configurazione della ricerca vettoriale. Consulta Prerequisiti dell'indice di ricerca vettoriale per i requisiti specifici di SemanticCacheLookup e i link alla documentazione della ricerca vettoriale.
  6. Verifica di avere un ambiente Intermedio o Completo disponibile nella tua istanza Apigee. È possibile eseguire il deployment delle policy di memorizzazione nella cache semantica solo negli ambienti intermedio o completo.
  7. Verifica di avere un gruppo di ambienti con un nome host di runtime che puoi utilizzare per inviare richieste al proxy API.

Ruoli obbligatori

Per ottenere le autorizzazioni necessarie per creare e utilizzare le policy di memorizzazione nella cache semantica, chiedi all'amministratore di concederti il ruolo IAM AI Platform User (roles/aiplatform.user) sul account di servizio che utilizzi per il deployment dei proxy Apigee. Per saperne di più sulla concessione dei ruoli, consulta Gestisci l'accesso a progetti, cartelle e organizzazioni.

Potresti anche riuscire a ottenere le autorizzazioni richieste tramite i ruoli personalizzati o altri ruoli predefiniti.

Imposta le variabili di ambiente

Nel progetto Google Cloud che contiene l'istanza Apigee, utilizza il seguente comando per impostare le variabili di ambiente:

export PROJECT_ID=PROJECT_ID
export REGION=REGION
export RUNTIME_HOSTNAME=RUNTIME_HOSTNAME

Dove:

  • PROJECT_ID è l'ID del progetto con la tua istanza Apigee.
  • REGION è la regione Google Cloud dell'istanza Apigee.
  • RUNTIME_HOSTNAME è il nome host del runtime Apigee.

Per verificare che le variabili di ambiente siano impostate correttamente, esegui il comando seguente ed esamina l'output:

echo $PROJECT_ID $REGION $RUNTIME_HOSTNAME

Impostare il progetto

Imposta il Google Cloud progetto nell'ambiente di sviluppo:

    gcloud auth login
    gcloud config set project $PROJECT_ID

Prerequisiti per l'indice Vector Search

Questo tutorial presuppone che tu abbia già (o creerai) un indice di ricerca vettoriale di cui è stato eseguito il deployment su un endpoint privato (Private Service Connect). La creazione, la formattazione e il deployment di un indice di Vector Search sono documentati nelle guide di Vector Search, pertanto questo tutorial non ripete questi passaggi. Segui la documentazione di Vector Search per:

Quando crei l'indice, deve soddisfare i seguenti requisiti specifici di SemanticCacheLookup:

  • L'indice deve utilizzare STREAM_UPDATE ("indexUpdateMethod": "STREAM_UPDATE") in modo che le chiamate upsertDatapoints della norma SemanticCachePopulate diventino interrogabili quasi in tempo reale.
  • L'indice dimensions deve corrispondere alla dimensionalità dell'output del modello di incorporamento che utilizzi nel criterio SemanticCacheLookup. Questo tutorial utilizza gemini-embedding-001, che produce incorporamenti a 3072 dimensioni per impostazione predefinita. Se tronchi l'output a una dimensionalità inferiore (ad esempio, 768 o 1536), imposta dimensions sullo stesso valore.
  • Crea l'indice con la misura della distanza (distanceMeasureType) che corrisponde al <DistanceMeasureType> della tua policy. L'elemento <SimilaritySearch><VertexAI><DistanceMeasureType> nel criterio SemanticCacheLookup è facoltativo e il valore predefinito è DOT_PRODUCT_DISTANCE; è supportato anche COSINE_DISTANCE. La misura della distanza dell'indice e la policy <DistanceMeasureType> devono essere le stesse.

Il seguente esempio minimo crea un indice compatibile. Per il corpo completo della richiesta e tutte le opzioni disponibili, consulta Creare e gestire un indice:

ACCESS_TOKEN=$(gcloud auth print-access-token) && curl -X POST \
  "https://$REGION-aiplatform.googleapis.com/v1/projects/$PROJECT_ID/locations/$REGION/indexes" \
  -H "Authorization: Bearer $ACCESS_TOKEN" \
  -H "Content-Type: application/json" \
  -d '{
    "displayName": "semantic-cache-index",
    "metadata": {
      "config": {
        "dimensions": 3072,
        "distanceMeasureType": "DOT_PRODUCT_DISTANCE"
      }
    },
    "indexUpdateMethod": "STREAM_UPDATE"
  }'

Prendi nota del valore numerico INDEX_ID restituito nella risposta; lo utilizzerai nel criterio SemanticCachePopulate. Dopo aver creato l'indice, crea un endpoint dell'indice Private Service Connect e implementa l'indice.

Quando crei l'endpoint dell'indice Private Service Connect, deve soddisfare i seguenti requisiti specifici di SemanticCacheLookup:

  • projectAllowlist deve includere il progetto Apigee che avvia la connessione:
    • Apigee: utilizza il progetto tenant Apigee. Recupera l'ID progetto tenant dall'API Organizations (campo apigeeProjectId).
    projectAllowlist non può essere modificato dopo la creazione dell'endpoint dell'indice. Se inserisci nella lista consentita il progetto sbagliato, devi eliminare e ricreare l'endpoint dell'indice.

Prendi nota del valore numerico INDEX_ENDPOINT_ID dell'endpoint dell'indice.

Configura il account di servizio per il proxy Apigee

Il proxy Apigee utilizza un account di servizio per le chiamate REST di Vertex AI: l'API Embeddings nella policy SemanticCacheLookup, upsertDatapoints nella policy SemanticCachePopulate e la destinazione del modello. Concedi a questo account di servizio il ruolo AI Platform User (roles/aiplatform.user):

gcloud projects add-iam-policy-binding $PROJECT_ID \
  --member="serviceAccount:SERVICE_ACCOUNT" \
  --role="roles/aiplatform.user"

dove SERVICE_ACCOUNT è l'indirizzo email del account di servizio utilizzato dal proxy. Fai riferimento a questo account di servizio quando esegui il deployment del proxy nel Passaggio 4: importa ed esegui il deployment del proxy API.

Panoramica

Le policy di memorizzazione nella cache semantica aiutano gli utenti Apigee con i modelli LLM a gestire in modo intelligente prompt identici o semanticamente simili in modo efficiente, riducendo al minimo le chiamate API di backend e il consumo di risorse.

I criteri SemanticCacheLookup e SemanticCachePopulate vengono collegati ai flussi di richiesta e risposta, rispettivamente, di un proxy API Apigee. Quando il proxy riceve una richiesta, il criterio SemanticCacheLookup estrae il prompt dell'utente dalla richiesta e lo converte in una rappresentazione numerica utilizzando l'API Text Embeddings. Una ricerca di similarità semantica viene eseguita utilizzando Vector Search per trovare prompt simili. Se viene trovato un punto dati del prompt simile, viene eseguita una ricerca nella cache. Se vengono trovati dati memorizzati nella cache, la risposta memorizzata nella cache viene restituita al client.

Se la ricerca di somiglianze non restituisce un prompt precedente simile, il modello LLM genera contenuti in risposta al prompt dell'utente e popola la cache di Apigee con la risposta. Viene creato un ciclo di feedback per aggiornare le voci dell'indice di ricerca vettoriale in preparazione per le richieste future.

In questo scenario, l'indice Vector Search viene implementato su un endpoint privato (Private Service Connect) tramite gRPC. Per ulteriori dettagli sul supporto di Private Service Connect per la ricerca vettoriale, consulta Eseguire query sugli indici di accesso privato ai servizi o Private Service Connect.

Le sezioni seguenti descrivono i passaggi per creare e configurare i criteri di memorizzazione nella cache semantica:

  1. Verifica le risorse e ottieni i valori necessari ad Apigee.
  2. Connettiti al collegamento servizio.
  3. Crea il bundle del proxy API.
  4. Importa e implementa il proxy API.
  5. Testa le policy di memorizzazione nella cache semantica.

Passaggio 1: verifica le risorse e ottieni i valori necessari ad Apigee

Prima di configurare Apigee, verifica che l'endpoint dell'indice di Vector Search sia abilitato per Private Service Connect e che l'indice sia sottoposto a deployment. Poi leggi i due valori utilizzati dal proxy Apigee: il collegamento del servizio e DEPLOYED_INDEX_ID.

Verifica che l'indice sia stato implementato e che l'endpoint esponga un collegamento al servizio Private Service Connect:

gcloud ai index-endpoints describe INDEX_ENDPOINT_ID \
  --project=$PROJECT_ID --region=$REGION \
  --format="value(deployedIndexes.privateEndpoints.serviceAttachment)"

Il comando restituisce un nome risorsa di collegamento del servizio nel formato projects/TENANT_PROJECT/regions/REGION/serviceAttachments/SERVICE_ATTACHMENT_NAME. In questa guida, questo valore viene indicato come SERVICE_ATTACHMENT. Se il comando restituisce un valore vuoto, l'indice non è ancora stato eseguito il deployment su un endpoint Private Service Connect. Torna a Prerequisiti dell'indice Vector Search e termina il deployment dell'indice prima di continuare.

Leggi DEPLOYED_INDEX_ID dell'indice di cui è stato eseguito il deployment sull'endpoint:

gcloud ai index-endpoints describe INDEX_ENDPOINT_ID \
  --project=$PROJECT_ID --region=$REGION \
  --format="value(deployedIndexes.id)"

In questa guida, questo valore viene indicato come DEPLOYED_INDEX_ID. Lo utilizzi nel criterio SemanticCacheLookup nel Passaggio 3: crea il bundle del proxy API.

Per ulteriori informazioni sul deployment e sull'esecuzione di query sugli endpoint di indice privati, consulta Eseguire il deployment di un indice su un endpoint Private Service Connect e Eseguire query su indici di accesso a Private Services o Private Service Connect.

Passaggio 2: connettiti all'allegato del servizio

Questo passaggio fornisce l'host privato a cui chiama il proxy <GrpcEndpoint>. Su Apigee, crea un collegamento dell'endpoint Apigee. Il collegamento dell'endpoint è il lato consumer di Private Service Connect di Apigee: si connette al collegamento di servizio Vector Search e ti fornisce un host privato che il proxy chiama.

curl -X POST \
  -H "Authorization: Bearer $(gcloud auth print-access-token)" \
  -H "Content-Type: application/json" \
  -d '{
        "location": "'"$REGION"'",
        "serviceAttachment": "SERVICE_ATTACHMENT"
      }' \
  "https://apigee.googleapis.com/v1/organizations/$PROJECT_ID/endpointAttachments?endpointAttachmentId=ENDPOINT_ATTACHMENT"

Esegui il polling finché state dell'allegato non è ACTIVE e il relativo connectionState non è ACCEPTED, quindi annota l'host:

curl -s -H "Authorization: Bearer $(gcloud auth print-access-token)" \
  "https://apigee.googleapis.com/v1/organizations/$PROJECT_ID/endpointAttachments/ENDPOINT_ATTACHMENT"

La risposta contiene l'host nel campo host. In questa guida, questo valore viene chiamato TARGET_HOST.

Per connetterti al collegamento al servizio Vector Search dal tuo proxy, puoi utilizzare:

  • L'indirizzo IP:utilizza l'indirizzo IP restituito nel campo host direttamente come TARGET_HOST (ad esempio, 7.0.3.4).
  • Un record DNS privato:se hai configurato una zona DNS privata in Cloud DNS nel tuo progetto Google Cloud con il peering DNS ad Apigee, puoi creare un record A nella tua zona privata che punta all'indirizzo IP del collegamento dell'endpoint e utilizzare quel nome di dominio (ad esempio vectorsearch.example.com) come TARGET_HOST. Per saperne di più, consulta Utilizzare un record DNS e Connessione con zone di peering DNS privato.

Passaggio 3: crea il pacchetto del proxy API

Crea il bundle proxy

Crea il seguente layout di directory:

apiproxy/
├── PROXY_NAME.xml
├── proxies/default.xml
├── targets/default.xml
└── policies/
    ├── SCL-1.xml
    └── SCP-1.xml

policies/SCL-1.xml: la policy SemanticCacheLookup. Il blocco <SimilaritySearch> utilizza <PrivateServiceConnect><GrpcEndpoint> (nessun <URL>).

Nota: regole <GrpcEndpoint>:

  • Il formato è grpc://TARGET_HOST:PORT; lo schema deve essere grpc://. grpcs:// (TLS) non è supportato in questa versione.
  • La porta è 10000 per Vector Search. Gli endpoint del data plane di Private Service Connect gestiscono gRPC sulla porta 10000, quindi l'endpoint è sempre grpc://TARGET_HOST:10000.
  • TARGET_HOST può essere l'indirizzo IP del collegamento dell'endpoint (dal passaggio 2) o un record DNS personalizzato creato nella tua zona DNS privata.
  • L'hop gRPC è in testo normale e non autenticato (protetto dall'isolamento di rete).
<SemanticCacheLookup async="false" continueOnError="false" enabled="true" name="SCL-1">
  <DisplayName>SCL-1</DisplayName>
  <IgnoreUnresolvedVariables>false</IgnoreUnresolvedVariables>
  <UserPromptSource>{jsonPath('$.contents[-1].parts[-1].text',request.content,true)}</UserPromptSource>
  <Embeddings>
    <VertexAI>
      <URL>https://REGION-aiplatform.googleapis.com/v1/projects/PROJECT_ID/locations/REGION/publishers/google/models/gemini-embedding-001:predict</URL>
    </VertexAI>
  </Embeddings>
  <SimilaritySearch>
    <VertexAI>
      <PrivateServiceConnect>
        <GrpcEndpoint>grpc://TARGET_HOST:10000</GrpcEndpoint>
      </PrivateServiceConnect>
      <DeployedIndexID>DEPLOYED_INDEX_ID</DeployedIndexID>
      <Threshold>0.95</Threshold>
    </VertexAI>
  </SimilaritySearch>
</SemanticCacheLookup>

policies/SCP-1.xml: la policy SemanticCachePopulate. Populate è solo REST e deve utilizzare <URL> (rifiuta <PrivateServiceConnect> al momento del deployment):

<SemanticCachePopulate async="false" continueOnError="true" enabled="true" name="SCP-1">
  <DisplayName>SCP-1</DisplayName>
  <IgnoreUnresolvedVariables>true</IgnoreUnresolvedVariables>
  <SimilaritySearch>
    <VertexAI>
      <URL>https://REGION-aiplatform.googleapis.com/v1/projects/PROJECT_ID/locations/REGION/indexes/INDEX_ID:upsertDatapoints</URL>
    </VertexAI>
  </SimilaritySearch>
  <TTLInSeconds>3600</TTLInSeconds>
</SemanticCachePopulate>

targets/default.xml: il target del modello. La destinazione chiama un'API di Google, quindi ha bisogno di un token; <GoogleAccessToken> utilizza il account di servizio del deployment:

<TargetEndpoint name="default">
  <PreFlow name="PreFlow"><Request/><Response/></PreFlow>
  <PostFlow name="PostFlow"><Request/><Response/></PostFlow>
  <HTTPTargetConnection>
    <Authentication>
      <GoogleAccessToken>
        <Scopes>
          <Scope>https://www.googleapis.com/auth/cloud-platform</Scope>
        </Scopes>
      </GoogleAccessToken>
    </Authentication>
    <URL>https://REGION-aiplatform.googleapis.com/v1/projects/PROJECT_ID/locations/REGION/publishers/google/models/gemini-2.5-flash:generateContent</URL>
  </HTTPTargetConnection>
</TargetEndpoint>

proxies/default.xml: esegui la policy SemanticCacheLookup sulla richiesta e la policy SemanticCachePopulate sulla risposta:

<ProxyEndpoint name="default">
  <PreFlow name="PreFlow">
    <Request><Step><Name>SCL-1</Name></Step></Request>
    <Response><Step><Name>SCP-1</Name></Step></Response>
  </PreFlow>
  <PostFlow name="PostFlow"><Request/><Response/></PostFlow>
  <HTTPProxyConnection>
    <BasePath>/PROXY_NAME</BasePath>
  </HTTPProxyConnection>
  <RouteRule name="default">
    <TargetEndpoint>default</TargetEndpoint>
  </RouteRule>
</ProxyEndpoint>

PROXY_NAME.xml: il descrittore del bundle:

<APIProxy name="PROXY_NAME">
  <BasePaths>/PROXY_NAME</BasePaths>
  <Policies><Policy>SCL-1</Policy><Policy>SCP-1</Policy></Policies>
  <ProxyEndpoints><ProxyEndpoint>default</ProxyEndpoint></ProxyEndpoints>
  <TargetEndpoints><TargetEndpoint>default</TargetEndpoint></TargetEndpoints>
</APIProxy>

Passaggio 4: importa e implementa il proxy API

Comprimi il bundle, importalo per creare una nuova revisione ed esegui il deployment della revisione con il tuo account di servizio:

TOKEN=$(gcloud auth print-access-token)
(cd BUNDLE_DIR && zip -r ../PROXY_NAME.zip apiproxy)
curl -X POST -H "Authorization: Bearer $TOKEN" \
  -F "file=@PROXY_NAME.zip" \
  "https://apigee.googleapis.com/v1/organizations/$PROJECT_ID/apis?action=import&name=PROXY_NAME"
curl -X POST -H "Authorization: Bearer $TOKEN" \
  "https://apigee.googleapis.com/v1/organizations/$PROJECT_ID/environments/ENV/apis/PROXY_NAME/revisions/REVISION/deployments?override=true&serviceAccount=SERVICE_ACCOUNT"

Dove:

  • BUNDLE_DIR è la directory che contiene la cartella apiproxy/. L'archivio deve contenere la cartella apiproxy/ nella directory principale.
  • ENV è l'ambiente Apigee in cui esegui il deployment del proxy. L'ambiente deve essere un ambiente Intermedio o Completo.
  • REVISION è il numero di revisione restituito dalla chiamata di importazione.
  • SERVICE_ACCOUNT è l'indirizzo email del account di servizio che utilizzi per il deployment del proxy.

Attendi che i report sul deployment indichino READY:

curl -s -H "Authorization: Bearer $TOKEN" \
  "https://apigee.googleapis.com/v1/organizations/$PROJECT_ID/environments/ENV/apis/PROXY_NAME/revisions/REVISION/deployments" | jq .state

Passaggio 5: testa i criteri di memorizzazione nella cache semantica

Invia un nuovo prompt. Si tratta di un fallimento della cache: il modello viene chiamato e la risposta viene memorizzata nella cache.

curl -X POST "https://$RUNTIME_HOSTNAME/PROXY_NAME" \
  -H "Content-Type: application/json" \
  -d '{"contents":[{"role":"user","parts":[{"text":"Explain in one sentence why the sky appears blue."}]}]}'

Invia di nuovo lo stesso prompt. Si tratta di un successo della cache: la risposta viene fornita dalla cache e il modello non viene chiamato.

curl -i -X POST "https://$RUNTIME_HOSTNAME/PROXY_NAME" \
  -H "Content-Type: application/json" \
  -d '{"contents":[{"role":"user","parts":[{"text":"Explain in one sentence why the sky appears blue."}]}]}'

Nell'hit, la risposta include l'intestazione Cached-content: true, la stessa risposta e una latenza notevolmente inferiore.

Puoi anche verificare la memorizzazione nella cache con una sessione di debug. In caso di hit, la policy SemanticCacheLookup imposta le seguenti variabili di flusso:

Variabile Valore in un hit
SemanticCacheLookup.SCL-1.dense_embeddings Il vettore di embedding del prompt.
SemanticCacheLookup.SCL-1.is_nearest_neighbor_hit true
SemanticCacheLookup.SCL-1.cache_hit true
SemanticCacheLookup.SCL-1.cached_llm_response La risposta memorizzata nella cache.

In caso di hit, il target del modello non viene richiamato: il flusso viene interrotto e viene restituita la risposta memorizzata nella cache.

Risoluzione dei problemi

Per il riferimento completo agli errori, consulta le norme SemanticCacheLookup.

Passaggi successivi