Cara melakukan pengujian lokal agen ADK yang menulis ke Google Spreadsheet sebelum men-deploy ke Cloud Run

1. Pengantar

Ringkasan

Dalam postingan ini, Anda akan membangun agen Gemini menggunakan Google Agent Development Kit (ADK) dan FastAPI. Sebelum deployment, Anda akan mengonfigurasi Kredensial Default Aplikasi (ADC) untuk melakukan pengujian secara lokal menggunakan akun layanan yang sama dengan identitas layanan Cloud Run.

Untuk berkomunikasi dengan Google Spreadsheet, aplikasi Anda memerlukan Token Akses OAuth dengan cakupan yang sesuai untuk mengakses spreadsheet. Anda akan mempelajari cara mendapatkan token akses ini saat berjalan secara lokal dan di Cloud Run dengan ADC:

Catatan Terminologi:

Anda mungkin lebih memahami istilah "mengambil alih identitas" atau "mengambil alih izin yang sama". Di Google Cloud, dengan meniru identitas akun layanan, akun utama yang diautentikasi dapat mengakses apa pun yang dapat diakses oleh akun layanan. Hanya akun utama terautentikasi dengan izin yang sesuai yang dapat meniru identitas akun layanan. Anda dapat membaca selengkapnya di sini https://docs.cloud.google.com/iam/docs/service-account-overview#impersonation

Yang akan Anda pelajari

  • Cara mengonfigurasi Kredensial Default Aplikasi (ADC) untuk lingkungan lokal Anda
  • Cara membuat agen ADK yang dapat membaca dan menulis ke Google Spreadsheet
  • Cara men-deploy agen ke Cloud Run

2. Penyiapan dan Persyaratan

Prasyarat

  • Anda login ke Konsol Cloud.
  • Anda telah men-deploy layanan Cloud Run sebelumnya. Misalnya, Anda dapat mengikuti cara men-deploy layanan Cloud Run untuk memulai.

Menetapkan Variabel Lingkungan

Anda dapat menetapkan variabel lingkungan yang akan digunakan di seluruh codelab ini.

Anda dapat menemukan ID Spreadsheet di URL Google Spreadsheet saat Anda menyalin link Bagikan, misalnya https://docs.google.com/spreadsheets/d/YOUR_SPREADSHEET_ID/edit?usp=sharing

PROJECT_ID=<YOUR-PROJECT-ID>
REGION=<YOUR_REGION>
SPREADSHEET_ID=<YOUR_SPREADSHEET_ID>
SA_NAME=sheet-agent-sa
SERVICE_ACCOUNT_EMAIL=$SA_NAME@$PROJECT_ID.iam.gserviceaccount.com

Mengaktifkan Google Cloud API yang Diperlukan

gcloud services enable \
  sheets.googleapis.com \
  aiplatform.googleapis.com \
  artifactregistry.googleapis.com \
  cloudbuild.googleapis.com \
  run.googleapis.com \
  logging.googleapis.com \
  --project=$PROJECT_ID

Buat Akun Layanan

Pertama, buat Akun Layanan dengan perintah berikut.

gcloud iam service-accounts create $SA_NAME \
    --description="Service account for spreadsheet agent codelab" \
    --display-name="Spreadsheet Agent Service Account" \
    --project=$PROJECT_ID

Selanjutnya, berikan peran Vertex AI User ke Akun Layanan (diperlukan untuk model Gemini di Vertex AI)

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

Beri identitas gcloud Anda izin untuk meniru identitas Akun Layanan (diperlukan untuk pengembangan lokal). Anda dapat melihat identitas gcloud Anda dengan menjalankan gcloud auth list

USER_EMAIL=$(gcloud config get-value account)

gcloud iam service-accounts add-iam-policy-binding $SERVICE_ACCOUNT_EMAIL \
    --member="user:$USER_EMAIL" \
    --role="roles/iam.serviceAccountTokenCreator" \
    --project=$PROJECT_ID
  1. Buka Google Spreadsheet di browser.
  2. Klik tombol Bagikan.
  3. Tempelkan email Akun Layanan $SERVICE_ACCOUNT_EMAIL dan beri akses Editor.

3. Membuat aplikasi

Pertama, buat direktori untuk kode sumber dan cd ke direktori tersebut.

mkdir local-adk-sheets-codelab && cd $_

Kemudian, buat file main.py dengan konten berikut:

import os
from fastapi import FastAPI, HTTPException
from pydantic import BaseModel
from google.auth import default
from googleapiclient.discovery import build
from google.adk.agents.llm_agent import Agent
from google.adk.runners import InMemoryRunner

# 1. Environment and Global Google Sheets Client Setup (ADC)
SPREADSHEET_ID = os.environ.get("SPREADSHEET_ID")
if not SPREADSHEET_ID:
    raise ValueError("SPREADSHEET_ID environment variable is missing. Please set it before running.")

credentials, _ = default(scopes=['https://www.googleapis.com/auth/spreadsheets'])
sheets_api = build('sheets', 'v4', credentials=credentials).spreadsheets()

# 2. Tools
def read_spreadsheet(range_name: str) -> dict:
    """Reads values from the Google Spreadsheet for a given range.
   
    Args:
        range_name: The A1 notation or R1C1 notation of the range to retrieve, e.g., 'Sheet1!A1:D10'.
    """
    return sheets_api.values().get(spreadsheetId=SPREADSHEET_ID, range=range_name).execute()

def update_spreadsheet(range_name: str, values: list[list[str]]) -> dict:
    """Updates the Google Spreadsheet range with the specified grid of values.
   
    Args:
        range_name: The A1 notation or R1C1 notation of the range to update, e.g., 'Sheet1!C2'.
        values: A list of lists of strings representing the grid of values to write.
    """
    return sheets_api.values().update(
        spreadsheetId=SPREADSHEET_ID,
        range=range_name,
        valueInputOption="USER_ENTERED",
        body={"values": values}
    ).execute()

# 3. Agent Definition
MODEL_NAME = os.environ.get("GEMINI_MODEL", "gemini-3.1-flash-lite")
root_agent = Agent(
    name="spreadsheet_agent",
    model=MODEL_NAME,
    instruction="""You are a helpful spreadsheet assistant.
    You can read and write to the user's Google Spreadsheet using the tools provided.
    Always use the appropriate tools when the user asks you to read or update a spreadsheet.
    When updating a range, make sure the values parameter is a list of lists (e.g. [[value]]).
    Be concise and helpful in your responses.""",
    description="An agent that can read and write to a specific Google Spreadsheet.",
    tools=[read_spreadsheet, update_spreadsheet]
)

# 4. FastAPI Application Setup
app = FastAPI()

class ChatRequest(BaseModel):
    prompt: str

@app.post("/chat")
async def chat_endpoint(request: ChatRequest):
    try:
        async with InMemoryRunner(app_name="sheets_agent_app", agent=root_agent) as runner:
            events = await runner.run_debug(request.prompt, quiet=True)
           
            # Extract the final response text
            texts = [
                "".join(p.text for p in e.content.parts if p.text)
                for e in reversed(events) if e.content and e.content.parts
            ]
            return {"response": next((t for t in texts if t), "No response from agent.")}
    except Exception as e:
        raise HTTPException(status_code=500, detail=str(e))

Selanjutnya, buat file requirements.txt dengan konten berikut:

fastapi>=0.100.0
uvicorn>=0.22.0
google-adk>=1.27.1
google-auth
google-api-python-client

4. Menguji layanan secara lokal

gcloud auth application-default login --impersonate-service-account=$SERVICE_ACCOUNT_EMAIL
GOOGLE_GENAI_USE_VERTEXAI=1 GOOGLE_CLOUD_PROJECT=$PROJECT_ID SPREADSHEET_ID=$SPREADSHEET_ID uvicorn main:app --host 0.0.0.0 --port 8080

Sekarang, uji agen Anda dari terminal lain:

curl -X POST http://localhost:8080/chat \
    -H "Content-Type: application/json" \
    -d '{"prompt": "Update spreadsheet '$SPREADSHEET_ID' at range Sheet1!A1 with the value hello world"}'

Server akan merespons: {"response":"The spreadsheet at Sheet1!A1 has been updated with the value \"hello world\"."}

5. Men-deploy ke Cloud Run

Setelah mengetahui bahwa akun layanan Anda memiliki izin yang sesuai untuk mengakses spreadsheet, Anda akan men-deploy ke Cloud Run, menggunakan akun layanan sebagai identitas layanan.

gcloud run deploy local-adk-sheets-codelab \
    --source . \
    --region=$REGION \
    --set-env-vars GOOGLE_GENAI_USE_VERTEXAI=1,GOOGLE_CLOUD_PROJECT=$PROJECT_ID,GOOGLE_CLOUD_LOCATION=global,SPREADSHEET_ID=$SPREADSHEET_ID \
    --service-account $SERVICE_ACCOUNT_EMAIL \
    --no-allow-unauthenticated \
    --project=$PROJECT_ID

Setelah deployment selesai, kirim perintah ke layanan Cloud Run Anda.

# Retrieve the Service URL
SERVICE_URL=$(gcloud run services describe local-adk-sheets-codelab --region $REGION --format 'value(status.url)')
curl -X POST $SERVICE_URL/chat \
    -H "Authorization: bearer $(gcloud auth print-identity-token)" \
    -H "Content-Type: application/json" \
    -d '{"prompt": "Update spreadsheet '$SPREADSHEET_ID' at range Sheet1!A1 with the value hello world"}'

Anda akan menerima respons {"response":"OK. I've updated cell A1 in Sheet1 with \"hello world\"."}

Sekarang buka Spreadsheet Google Anda. Anda akan melihat nilai "hello world" di sel pertama.

6. Selamat!

Selamat, Anda telah menyelesaikan codelab.

Apa selanjutnya?

Sebaiknya pelajari dokumentasi berikut untuk memperluas kemampuan agen Anda:

Yang telah kita bahas

  • Cara mengonfigurasi Kredensial Default Aplikasi (ADC) untuk lingkungan lokal Anda
  • Cara membuat agen ADK yang dapat membaca dan menulis ke Google Spreadsheet
  • Cara men-deploy agen ke Cloud Run

7. Pembersihan

Untuk menghindari biaya yang tidak disengaja (misalnya, jika fungsi Cloud Run ini tidak sengaja dipanggil lebih banyak daripada alokasi pemanggilan Cloud Run bulanan Anda di tingkat gratis), Anda dapat menghapus layanan Cloud Run atau menghapus project.

Untuk menghapus layanan Cloud Run, buka Cloud Run di Konsol Cloud di https://console.cloud.google.com/run/, lalu hapus layanan local-adk-sheets-codelab yang Anda buat di codelab ini.

Jika Anda memilih untuk menghapus seluruh project, Anda dapat membuka https://console.cloud.google.com/cloud-resource-manager, memilih project yang Anda buat di Langkah 2, lalu memilih Hapus. Jika menghapus project, Anda harus mengubah project di Cloud SDK. Anda dapat melihat daftar semua project yang tersedia dengan menjalankan gcloud projects list.