콘텐츠로 이동

Google Chat

필수 Secret 오버레이
모델 제공자 key(예제에서는 OPENAI_API_KEY)와 서비스 계정 JSON Secret values-google-chat.yaml

언제 사용하나요?

팀이 Google Chat에서 Hermes와 대화할 때 사용합니다. 이벤트는 Cloud Pub/Sub pull 구독으로 들어오므로 파드는 Google API로 나가는 연결만 만듭니다. 들어오는 Service, Ingress, 공개 엔드포인트가 필요 없고, 예제는 모든 리스너를 꺼둡니다.

v2026.9.14 이상이 필요합니다. 이 릴리스부터 공식 이미지에 Google Chat 의존성이 들어 있어, 새 파드가 첫 부팅 때 아무것도 설치하지 않습니다.

Google Cloud 사전 준비

Workspace 쪽은 업스트림 Google Chat 설정 가이드를 따르세요. 가장 자주 틀리는 부분은 IAM 바인딩이고, 서로 다른 두 리소스에 걸립니다:

  • topic에: chat-api-push@system.gserviceaccount.com에 Pub/Sub Publisher가 필요합니다. 없으면 Google Chat이 이벤트를 전달할 수 없습니다.
  • subscription에: 사용자의 서비스 계정에 Pub/Sub Subscriber와 Pub/Sub Viewer가 필요합니다. Hermes가 시작할 때 구독을 확인합니다.

프로젝트 수준의 Pub/Sub 역할은 주지 마세요. Chat 앱 자체는 연결 설정을 Cloud Pub/Sub로 하고 topic을 가리키게 합니다.

설치

먼저 서비스 계정 JSON을 Secret에 넣습니다. 오버레이가 이를 읽기 전용으로 마운트하고 GOOGLE_CHAT_SERVICE_ACCOUNT_JSON이 그 파일을 가리키게 합니다:

kubectl create secret generic google-chat-sa \
  --namespace hermes-agent \
  --from-file=sa.json=/path/to/key.json

helm upgrade --install hermes-agent ./charts/hermes-agent \
  --namespace hermes-agent --create-namespace \
  -f charts/hermes-agent/values-google-chat.yaml \
  --set-string env.OPENAI_API_KEY='<real-value>' --wait

Secret 볼륨의 기본 모드(0644)면 Hermes 런타임 사용자(uid 10000)가 key를 읽을 수 있습니다. defaultMode를 0440으로 좁힌다면 podSecurityContext.fsGroup: 10000도 설정하세요.

배포 전 조정

extraEnv의 프로젝트 ID, 전체 구독 이름, 허용 이메일을 바꾸세요. GOOGLE_CHAT_ALLOWED_USERS는 좁게 유지하세요: 목록에 있는 사람은 에이전트가 파드 안에서 명령을 실행하게 만들 수 있습니다. GOOGLE_CHAT_HOME_CHANNEL은 선택이며 cron 출력이 갈 곳만 정합니다.

일반 텍스트 메시지는 이 오버레이만으로 동작합니다. 네이티브 파일 첨부는 사용자별 OAuth 설정(채팅에서 /setup-files, 업스트림 가이드 Step 10)이 따로 필요하며, 이 예제는 이를 구성하지 않습니다.

확인한 범위

오버레이는 CI에서 다른 모든 values-*.yaml과 함께 렌더링됩니다. 고정된 이미지에서 Google Chat 어댑터가 시작되어 마운트된 경로의 서비스 계정 파일을 읽는 것까지 확인했습니다. 실제 Google Workspace 메시지 왕복은 Workspace 테넌트가 필요해 그 확인에 포함되지 않았습니다.

원본 YAML 열기

전체 오버레이

charts/hermes-agent/values-google-chat.yaml
# values-google-chat.yaml
#
# Hermes Agent as a Google Chat bot, receiving events over a Cloud Pub/Sub
# PULL subscription. Pub/Sub pull means outbound connections only: no inbound
# Service, Ingress or public endpoint is needed, so the listeners stay off.
# Requires hermes-agent >= v2026.9.14, whose published image ships the
# google-chat dependencies (no first-boot install).
#
# Prerequisites (upstream guide, "Google Chat Setup"):
#   https://hermes-agent.nousresearch.com/docs/user-guide/messaging/google_chat
# - A Google Workspace Chat app whose connection setting is Cloud Pub/Sub.
# - A Pub/Sub topic. On the TOPIC, grant `Pub/Sub Publisher` to
#   chat-api-push@system.gserviceaccount.com, or Chat can never deliver.
# - A pull subscription. On the SUBSCRIPTION, grant your own service account
#   `Pub/Sub Subscriber` AND `Pub/Sub Viewer` (Hermes checks the subscription
#   at startup). Do not grant project-level Pub/Sub roles.
#
# The service-account JSON is a FILE, mounted from a Secret you create:
#
#   kubectl create secret generic google-chat-sa \
#     --namespace hermes-agent \
#     --from-file=sa.json=/path/to/key.json
#
#   helm upgrade --install hermes-agent ./charts/hermes-agent \
#     --namespace hermes-agent --create-namespace \
#     -f charts/hermes-agent/values-google-chat.yaml \
#     --set-string env.OPENAI_API_KEY='sk-<real>' --wait
#
# Everything below is a placeholder. Never commit real project IDs, emails,
# space IDs or keys.

config:
  model:
    # Any provider works; OpenAI is only the example. `openai` is NOT valid
    # here (it aliases to OpenRouter), the built-in key is `openai-api`.
    provider: openai-api
    default: gpt-4o-mini
  terminal:
    backend: local

env:
  OPENAI_API_KEY: "sk-DUMMY_replace_me_000000000000000000000000"

# Google Chat settings are not secret, so they go in as plain env vars. The
# only credential is the mounted service-account file.
extraEnv:
  - name: GOOGLE_CHAT_PROJECT_ID
    value: "REPLACE_ME_GCP_PROJECT"
  - name: GOOGLE_CHAT_SUBSCRIPTION_NAME
    value: "projects/REPLACE_ME_GCP_PROJECT/subscriptions/hermes-chat-events-sub"
  # Path inside the container to the JSON mounted below.
  - name: GOOGLE_CHAT_SERVICE_ACCOUNT_JSON
    value: /var/run/secrets/google-chat/sa.json
  # Explicit allowlist of Workspace emails that may talk to the bot. Keep it
  # narrow: this bot can run commands inside the pod.
  - name: GOOGLE_CHAT_ALLOWED_USERS
    value: "you@example.com"
  # Optional: default destination for cron job output.
  # - name: GOOGLE_CHAT_HOME_CHANNEL
  #   value: "spaces/REPLACE_ME"

# The Secret volume's default mode (0644) lets the Hermes runtime user
# (uid 10000) read the key. If you set a tighter defaultMode such as 0440,
# also give the pod `podSecurityContext.fsGroup: 10000`.
extraVolumes:
  - name: google-chat-sa
    secret:
      secretName: google-chat-sa
extraVolumeMounts:
  - name: google-chat-sa
    mountPath: /var/run/secrets/google-chat
    readOnly: true

# Native file attachments need a separate, per-user OAuth setup
# (`/setup-files` in chat, upstream guide Step 10). Plain text messaging
# works without it, and this example does not configure it.