cloud run functions initializes correct

This commit is contained in:
johnpccd 2025-05-24 23:52:53 +02:00
parent 0f19eca29b
commit 77bf5125fb
11 changed files with 1097 additions and 351 deletions

3
.gitignore vendored
View File

@ -55,3 +55,6 @@ coverage.xml
.terraform .terraform
firestore-credentials.json firestore-credentials.json
# Deployment
function-source.zip

View File

@ -0,0 +1,66 @@
# Cloud Function for Image Processing
This directory contains the source code for the Cloud Function that processes image embeddings.
## Deployment
**Note: This Cloud Function is now deployed via Terraform, not the previous bash script.**
The Cloud Function is automatically deployed when you run:
```bash
cd deployment/terraform
terraform apply
```
## What the Cloud Function Does
1. **Triggered by Pub/Sub**: Listens to the `image-processing-topic` for new image processing tasks
2. **Downloads Images**: Retrieves images from Google Cloud Storage
3. **Generates Embeddings**: Uses Google Cloud Vision API to create image embeddings
4. **Stores Vectors**: Saves embeddings to the Qdrant vector database
5. **Updates Status**: Updates Firestore with processing status and embedding metadata
## Environment Variables
The following environment variables are automatically configured by Terraform:
- `QDRANT_HOST`: IP address of the vector database VM
- `QDRANT_PORT`: Port for Qdrant (default: 6333)
- `QDRANT_API_KEY`: API key for Qdrant authentication
- `QDRANT_COLLECTION`: Collection name for storing vectors (default: image_vectors)
## Function Configuration
- **Runtime**: Python 3.11
- **Memory**: 512MB
- **Timeout**: 540 seconds (9 minutes)
- **Max Instances**: 10
- **Min Instances**: 0 (scales to zero when not in use)
- **Retry Policy**: Automatic retries on failure
## Dependencies
See `requirements.txt` for the complete list of Python dependencies.
## Monitoring
The function automatically logs to Google Cloud Logging. You can monitor:
- Function executions
- Error rates
- Processing times
- Pub/Sub message handling
## Manual Testing
To manually trigger the function, publish a message to the Pub/Sub topic:
```json
{
"image_id": "test-image-123",
"storage_path": "your-bucket/path/to/image.jpg",
"team_id": "team-456",
"retry_count": 0
}
```

View File

@ -1,74 +0,0 @@
#!/bin/bash
# Cloud Function deployment script for image processing
set -e
# Configuration
PROJECT_ID=${GOOGLE_CLOUD_PROJECT:-"your-project-id"}
FUNCTION_NAME="process-image-embedding"
REGION=${REGION:-"us-central1"}
PUBSUB_TOPIC=${PUBSUB_TOPIC:-"image-processing-topic"}
MEMORY=${MEMORY:-"512MB"}
TIMEOUT=${TIMEOUT:-"540s"}
# Environment variables for the function
QDRANT_HOST=${QDRANT_HOST:-""}
QDRANT_PORT=${QDRANT_PORT:-"6333"}
QDRANT_API_KEY=${QDRANT_API_KEY:-""}
QDRANT_COLLECTION=${QDRANT_COLLECTION:-"image_vectors"}
echo "Deploying Cloud Function: $FUNCTION_NAME"
echo "Project: $PROJECT_ID"
echo "Region: $REGION"
echo "Pub/Sub Topic: $PUBSUB_TOPIC"
# Check if required environment variables are set
if [ -z "$QDRANT_HOST" ]; then
echo "Warning: QDRANT_HOST not set. Function will not store embeddings."
echo "Please set QDRANT_HOST to your vector database VM's external IP address."
fi
# Deploy the function
gcloud functions deploy $FUNCTION_NAME \
--gen2 \
--runtime=python311 \
--region=$REGION \
--source=. \
--entry-point=process_image_embedding \
--trigger-topic=$PUBSUB_TOPIC \
--memory=$MEMORY \
--timeout=$TIMEOUT \
--set-env-vars="QDRANT_HOST=$QDRANT_HOST,QDRANT_PORT=$QDRANT_PORT,QDRANT_API_KEY=$QDRANT_API_KEY,QDRANT_COLLECTION=$QDRANT_COLLECTION" \
--retry \
--max-instances=10 \
--min-instances=0
echo "Cloud Function deployed successfully!"
echo "Function name: $FUNCTION_NAME"
echo "Trigger: Pub/Sub topic '$PUBSUB_TOPIC'"
echo "Region: $REGION"
echo "Qdrant Host: $QDRANT_HOST"
# Set up retry policy for the Pub/Sub subscription
SUBSCRIPTION_NAME="${PUBSUB_TOPIC}-subscription"
echo "Configuring retry policy for subscription: $SUBSCRIPTION_NAME"
# Check if subscription exists, create if not
if ! gcloud pubsub subscriptions describe $SUBSCRIPTION_NAME --project=$PROJECT_ID >/dev/null 2>&1; then
echo "Creating Pub/Sub subscription: $SUBSCRIPTION_NAME"
gcloud pubsub subscriptions create $SUBSCRIPTION_NAME \
--topic=$PUBSUB_TOPIC \
--project=$PROJECT_ID
fi
# Update subscription with retry policy (max 3 retries)
gcloud pubsub subscriptions update $SUBSCRIPTION_NAME \
--max-retry-delay=600s \
--min-retry-delay=10s \
--max-delivery-attempts=3 \
--project=$PROJECT_ID
echo "Retry policy configured: max 3 delivery attempts"
echo "Deployment complete!"

View File

@ -1,6 +1,25 @@
# This file is maintained automatically by "terraform init". # This file is maintained automatically by "terraform init".
# Manual edits may be lost in future updates. # Manual edits may be lost in future updates.
provider "registry.terraform.io/hashicorp/archive" {
version = "2.7.1"
hashes = [
"h1:RzToQiFwVaxcV0QmgbyaKgNOhqc6oLKiFyZTrQSGcog=",
"zh:19881bb356a4a656a865f48aee70c0b8a03c35951b7799b6113883f67f196e8e",
"zh:2fcfbf6318dd514863268b09bbe19bfc958339c636bcbcc3664b45f2b8bf5cc6",
"zh:3323ab9a504ce0a115c28e64d0739369fe85151291a2ce480d51ccbb0c381ac5",
"zh:362674746fb3da3ab9bd4e70c75a3cdd9801a6cf258991102e2c46669cf68e19",
"zh:7140a46d748fdd12212161445c46bbbf30a3f4586c6ac97dd497f0c2565fe949",
"zh:78d5eefdd9e494defcb3c68d282b8f96630502cac21d1ea161f53cfe9bb483b3",
"zh:875e6ce78b10f73b1efc849bfcc7af3a28c83a52f878f503bb22776f71d79521",
"zh:b872c6ed24e38428d817ebfb214da69ea7eefc2c38e5a774db2ccd58e54d3a22",
"zh:cd6a44f731c1633ae5d37662af86e7b01ae4c96eb8b04144255824c3f350392d",
"zh:e0600f5e8da12710b0c52d6df0ba147a5486427c1a2cc78f31eea37a47ee1b07",
"zh:f21b2e2563bbb1e44e73557bcd6cdbc1ceb369d471049c40eb56cb84b6317a60",
"zh:f752829eba1cc04a479cf7ae7271526b402e206d5bcf1fcce9f535de5ff9e4e6",
]
}
provider "registry.terraform.io/hashicorp/google" { provider "registry.terraform.io/hashicorp/google" {
version = "6.36.1" version = "6.36.1"
hashes = [ hashes = [

View File

@ -3,9 +3,12 @@
This directory contains Terraform configurations to provision the required Google Cloud resources for Sereact: This directory contains Terraform configurations to provision the required Google Cloud resources for Sereact:
- Google Cloud Run service - Google Cloud Run service
- Google Cloud Function for image processing
- Google Container Registry (GCR) - Google Container Registry (GCR)
- Firestore database - Firestore database
- Cloud Storage bucket - Cloud Storage bucket
- Pub/Sub topics and subscriptions
- Qdrant vector database VM
## Prerequisites ## Prerequisites
@ -22,8 +25,53 @@ This directory contains Terraform configurations to provision the required Googl
gcloud config set project PROJECT_ID gcloud config set project PROJECT_ID
``` ```
## Architecture Overview
The infrastructure includes:
- **Cloud Run Service**: Main application service
- **Cloud Function**: Image processing and embedding generation
- **Qdrant VM**: Vector database running on Compute Engine
- **Firestore**: Document database
- **Cloud Storage**: File storage
- **Pub/Sub**: Message queue for asynchronous image processing
- **Automatic IP Configuration**: Qdrant VM IP is automatically passed to Cloud Run and Cloud Function
## Cloud Function Integration
The Cloud Function is now fully integrated into Terraform and handles:
1. **Image Processing**: Triggered by Pub/Sub messages
2. **Embedding Generation**: Uses Google Cloud Vision API
3. **Vector Storage**: Stores embeddings in Qdrant
4. **Status Updates**: Updates Firestore with processing results
### Automatic Configuration
The Cloud Function is automatically configured with:
- **Qdrant Connection**: VM IP address passed as environment variable
- **IAM Permissions**: Firestore, Storage, and Vision API access
- **Retry Policy**: Automatic retries on failure
- **Scaling**: 0-10 instances based on demand
## Setup and Usage ## Setup and Usage
### Option 1: Automated Deployment (Recommended)
Use the provided script that handles API enablement and proper deployment order:
```bash
cd deployment/terraform
./deploy-with-apis.sh
```
This script will:
1. Enable all required APIs
2. Wait for API propagation
3. Deploy infrastructure in the correct order
4. Handle Cloud Functions v2 dependencies
### Option 2: Manual Deployment
1. Copy the example variables file and edit it with your values: 1. Copy the example variables file and edit it with your values:
```bash ```bash
cp terraform.tfvars.example terraform.tfvars cp terraform.tfvars.example terraform.tfvars
@ -35,16 +83,33 @@ This directory contains Terraform configurations to provision the required Googl
terraform init terraform init
``` ```
3. Preview the changes: 3. Enable APIs first (required for Cloud Functions v2):
```bash ```bash
terraform plan terraform apply -target=google_project_service.services
``` ```
4. Apply the configuration: 4. Wait for APIs to propagate (2-3 minutes), then deploy everything:
```bash ```bash
terraform apply terraform apply
``` ```
## Required APIs
The following APIs are automatically enabled by Terraform:
- `cloudresourcemanager.googleapis.com` - Resource management
- `containerregistry.googleapis.com` - Container Registry
- `run.googleapis.com` - Cloud Run
- `firestore.googleapis.com` - Firestore database
- `storage.googleapis.com` - Cloud Storage
- `compute.googleapis.com` - Compute Engine (for Qdrant VM)
- `cloudfunctions.googleapis.com` - Cloud Functions
- `cloudbuild.googleapis.com` - Cloud Build (for function deployment)
- `eventarc.googleapis.com` - Eventarc (required for Cloud Functions v2)
- `pubsub.googleapis.com` - Pub/Sub messaging
**Note**: If you get an Eventarc API error, use the automated deployment script or wait 2-3 minutes after enabling APIs before deploying the Cloud Function.
5. After provisioning, you'll see outputs including: 5. After provisioning, you'll see outputs including:
- Cloud Run service URL - Cloud Run service URL
- Storage bucket name - Storage bucket name

View File

@ -0,0 +1,113 @@
# Create a Cloud Storage bucket for Cloud Function source code
resource "google_storage_bucket" "function_source" {
name = "${var.project_id}-cloud-function-source"
location = var.region
uniform_bucket_level_access = true
depends_on = [google_project_service.services]
}
# Create a ZIP archive of the Cloud Function source code
data "archive_file" "function_source" {
type = "zip"
output_path = "${path.module}/function-source.zip"
source_dir = "${path.module}/../cloud-function"
}
# Upload the ZIP file to Cloud Storage
resource "google_storage_bucket_object" "function_source" {
name = "function-source-${data.archive_file.function_source.output_md5}.zip"
bucket = google_storage_bucket.function_source.name
source = data.archive_file.function_source.output_path
}
# Create the Cloud Function
resource "google_cloudfunctions2_function" "image_processor" {
name = "process-image-embedding"
location = var.region
description = "Process image embeddings and store in vector database"
build_config {
runtime = "python311"
entry_point = "process_image_embedding"
source {
storage_source {
bucket = google_storage_bucket.function_source.name
object = google_storage_bucket_object.function_source.name
}
}
}
service_config {
max_instance_count = 10
min_instance_count = 0
available_memory = "512M"
timeout_seconds = 540
environment_variables = {
QDRANT_HOST = google_compute_instance.vector_db_vm.network_interface[0].access_config[0].nat_ip
QDRANT_PORT = "6333"
QDRANT_API_KEY = var.qdrant_api_key
QDRANT_COLLECTION = "image_vectors"
}
service_account_email = local.cloud_function_service_account
}
event_trigger {
trigger_region = var.region
event_type = "google.cloud.pubsub.topic.v1.messagePublished"
pubsub_topic = google_pubsub_topic.image_processing.id
retry_policy = "RETRY_POLICY_RETRY"
}
depends_on = [
google_project_service.services,
google_compute_instance.vector_db_vm,
google_pubsub_topic.image_processing
]
}
# Grant the Cloud Function service account necessary permissions
resource "google_project_iam_member" "function_firestore" {
project = var.project_id
role = "roles/datastore.user"
member = "serviceAccount:${local.cloud_function_service_account}"
}
resource "google_project_iam_member" "function_storage" {
project = var.project_id
role = "roles/storage.objectViewer"
member = "serviceAccount:${local.cloud_function_service_account}"
}
resource "google_project_iam_member" "function_vision" {
project = var.project_id
role = "roles/ml.developer"
member = "serviceAccount:${local.cloud_function_service_account}"
}
# Additional permissions required for Cloud Functions v2 with Eventarc
resource "google_project_iam_member" "function_eventarc_receiver" {
project = var.project_id
role = "roles/eventarc.eventReceiver"
member = "serviceAccount:${local.cloud_function_service_account}"
}
resource "google_project_iam_member" "function_pubsub_subscriber" {
project = var.project_id
role = "roles/pubsub.subscriber"
member = "serviceAccount:${local.cloud_function_service_account}"
}
# Output the Cloud Function details
output "cloud_function_name" {
description = "Name of the deployed Cloud Function"
value = google_cloudfunctions2_function.image_processor.name
}
output "cloud_function_url" {
description = "URL of the deployed Cloud Function"
value = google_cloudfunctions2_function.image_processor.service_config[0].uri
}

View File

@ -0,0 +1,64 @@
#!/bin/bash
# Deployment script that ensures APIs are enabled before deploying Cloud Functions
set -e
echo "🚀 Starting Terraform deployment with API enablement..."
# Get project ID from terraform.tfvars or environment
PROJECT_ID=${GOOGLE_CLOUD_PROJECT:-$(grep 'project_id' terraform.tfvars | cut -d'"' -f2)}
if [ -z "$PROJECT_ID" ]; then
echo "❌ Error: PROJECT_ID not found. Set GOOGLE_CLOUD_PROJECT or ensure terraform.tfvars has project_id"
exit 1
fi
echo "📋 Project ID: $PROJECT_ID"
# Step 1: Enable APIs first
echo "🔧 Step 1: Enabling required APIs..."
terraform apply -target=google_project_service.services -auto-approve
# Step 2: Wait for APIs to propagate
echo "⏳ Step 2: Waiting for APIs to propagate (30 seconds)..."
sleep 30
# Step 3: Verify critical APIs are enabled
echo "✅ Step 3: Verifying API enablement..."
REQUIRED_APIS=(
"cloudfunctions.googleapis.com"
"eventarc.googleapis.com"
"pubsub.googleapis.com"
"cloudbuild.googleapis.com"
)
for api in "${REQUIRED_APIS[@]}"; do
echo " Checking $api..."
if gcloud services list --enabled --project="$PROJECT_ID" --filter="name:$api" --format="value(name)" | grep -q "$api"; then
echo "$api is enabled"
else
echo "$api is not enabled yet, waiting longer..."
sleep 15
fi
done
# Step 4: Deploy infrastructure
echo "🏗️ Step 4: Deploying infrastructure..."
terraform apply -target=google_storage_bucket.app_bucket -target=google_firestore_database.database -target=google_compute_instance.vector_db_vm -auto-approve
# Step 5: Deploy Pub/Sub resources
echo "📨 Step 5: Deploying Pub/Sub resources..."
terraform apply -target=google_pubsub_topic.image_processing -target=google_pubsub_topic.image_processing_dlq -auto-approve
# Step 6: Deploy Cloud Function
echo "⚡ Step 6: Deploying Cloud Function..."
terraform apply -target=google_cloudfunctions2_function.image_processor -auto-approve
# Step 7: Deploy remaining resources
echo "🎯 Step 7: Deploying remaining resources..."
terraform apply -auto-approve
echo "🎉 Deployment completed successfully!"
echo ""
echo "📊 Deployment Summary:"
terraform output deployment_summary 2>/dev/null || echo " Run 'terraform output' to see all outputs"

View File

@ -17,7 +17,11 @@ resource "google_project_service" "services" {
"run.googleapis.com", "run.googleapis.com",
"firestore.googleapis.com", "firestore.googleapis.com",
"storage.googleapis.com", "storage.googleapis.com",
"compute.googleapis.com" "compute.googleapis.com",
"cloudfunctions.googleapis.com",
"cloudbuild.googleapis.com",
"eventarc.googleapis.com",
"pubsub.googleapis.com"
]) ])
project = var.project_id project = var.project_id

View File

@ -15,37 +15,6 @@ resource "google_pubsub_topic" "image_processing" {
} }
} }
# Pub/Sub subscription with retry policy
resource "google_pubsub_subscription" "image_processing" {
name = "${var.pubsub_topic_name}-subscription"
topic = google_pubsub_topic.image_processing.name
# Retry policy configuration
retry_policy {
minimum_backoff = "10s"
maximum_backoff = "600s"
}
# Dead letter policy after 5 failed attempts
dead_letter_policy {
dead_letter_topic = google_pubsub_topic.image_processing_dlq.id
max_delivery_attempts = 5
}
# Message retention
message_retention_duration = "604800s" # 7 days
retain_acked_messages = false
# Acknowledgment deadline
ack_deadline_seconds = 600 # 10 minutes
labels = {
environment = var.environment
service = "sereact"
component = "image-processing"
}
}
# Dead letter queue for failed messages # Dead letter queue for failed messages
resource "google_pubsub_topic" "image_processing_dlq" { resource "google_pubsub_topic" "image_processing_dlq" {
name = "${var.pubsub_topic_name}-dlq" name = "${var.pubsub_topic_name}-dlq"
@ -73,7 +42,7 @@ resource "google_pubsub_subscription" "image_processing_dlq" {
} }
} }
# IAM binding for Cloud Function to publish to topic # IAM binding for Cloud Run to publish to topic
resource "google_pubsub_topic_iam_binding" "image_processing_publisher" { resource "google_pubsub_topic_iam_binding" "image_processing_publisher" {
topic = google_pubsub_topic.image_processing.name topic = google_pubsub_topic.image_processing.name
role = "roles/pubsub.publisher" role = "roles/pubsub.publisher"
@ -83,27 +52,12 @@ resource "google_pubsub_topic_iam_binding" "image_processing_publisher" {
] ]
} }
# IAM binding for Cloud Function to subscribe
resource "google_pubsub_subscription_iam_binding" "image_processing_subscriber" {
subscription = google_pubsub_subscription.image_processing.name
role = "roles/pubsub.subscriber"
members = [
"serviceAccount:${local.cloud_function_service_account}",
]
}
# Output the topic and subscription names # Output the topic and subscription names
output "pubsub_topic_name" { output "pubsub_topic_name" {
description = "Name of the Pub/Sub topic for image processing" description = "Name of the Pub/Sub topic for image processing"
value = google_pubsub_topic.image_processing.name value = google_pubsub_topic.image_processing.name
} }
output "pubsub_subscription_name" {
description = "Name of the Pub/Sub subscription for image processing"
value = google_pubsub_subscription.image_processing.name
}
output "pubsub_dlq_topic_name" { output "pubsub_dlq_topic_name" {
description = "Name of the dead letter queue topic" description = "Name of the dead letter queue topic"
value = google_pubsub_topic.image_processing_dlq.name value = google_pubsub_topic.image_processing_dlq.name

View File

@ -1,9 +1,17 @@
{ {
"version": 4, "version": 4,
"terraform_version": "1.10.1", "terraform_version": "1.10.1",
"serial": 369, "serial": 388,
"lineage": "a183cd95-f987-8698-c6dd-84e933c394a5", "lineage": "a183cd95-f987-8698-c6dd-84e933c394a5",
"outputs": { "outputs": {
"cloud_function_name": {
"value": "process-image-embedding",
"type": "string"
},
"cloud_function_url": {
"value": "https://process-image-embedding-p64zpdtkta-uc.a.run.app",
"type": "string"
},
"cloud_run_qdrant_host": { "cloud_run_qdrant_host": {
"value": "34.71.6.1", "value": "34.71.6.1",
"type": "string" "type": "string"
@ -49,10 +57,6 @@
"value": "image-processing-topic-dlq", "value": "image-processing-topic-dlq",
"type": "string" "type": "string"
}, },
"pubsub_subscription_name": {
"value": "image-processing-topic-subscription",
"type": "string"
},
"pubsub_topic_name": { "pubsub_topic_name": {
"value": "image-processing-topic", "value": "image-processing-topic",
"type": "string" "type": "string"
@ -83,6 +87,38 @@
} }
}, },
"resources": [ "resources": [
{
"mode": "data",
"type": "archive_file",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/archive\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"exclude_symlink_directories": null,
"excludes": null,
"id": "ebb70c54eaebd24049805bcc1425349f70bc582d",
"output_base64sha256": "+Q18L9q1o61gbnGJlSvTmwG9cRv1Qwzf8GI95No2Rb4=",
"output_base64sha512": "tK0wkH07eL77+ytrOI8lcHATsN/nP0f/CYq0uzrrlhaRbJ+wsO1/6y0tmeX1hF6xqxW5ZDYTrhrSnayA+2afwQ==",
"output_file_mode": null,
"output_md5": "95eb8ea5146b66f5b26bb830e3f0eab6",
"output_path": "./function-source.zip",
"output_sha": "ebb70c54eaebd24049805bcc1425349f70bc582d",
"output_sha256": "f90d7c2fdab5a3ad606e7189952bd39b01bd711bf5430cdff0623de4da3645be",
"output_sha512": "b4ad30907d3b78befbfb2b6b388f25707013b0dfe73f47ff098ab4bb3aeb9616916c9fb0b0ed7feb2d2d99e5f5845eb1ab15b9643613ae1ad29dac80fb669fc1",
"output_size": 4781,
"source": [],
"source_content": null,
"source_content_filename": null,
"source_dir": "./../cloud-function",
"source_file": null,
"type": "zip"
},
"sensitive_attributes": []
}
]
},
{ {
"mode": "data", "mode": "data",
"type": "google_project", "type": "google_project",
@ -134,9 +170,11 @@
"run.googleapis.com/ingress": "all" "run.googleapis.com/ingress": "all"
}, },
"effective_annotations": { "effective_annotations": {
"run.googleapis.com/client-name": "gcloud",
"run.googleapis.com/client-version": "431.0.0",
"run.googleapis.com/ingress": "all", "run.googleapis.com/ingress": "all",
"run.googleapis.com/ingress-status": "all", "run.googleapis.com/ingress-status": "all",
"run.googleapis.com/operation-id": "3653c984-38f6-42b8-b3c1-9a6814773095", "run.googleapis.com/operation-id": "e4d7484f-39e4-4dde-8105-28d285eb927b",
"run.googleapis.com/urls": "[\"https://sereact-761163285547.us-central1.run.app\",\"https://sereact-p64zpdtkta-uc.a.run.app\"]", "run.googleapis.com/urls": "[\"https://sereact-761163285547.us-central1.run.app\",\"https://sereact-p64zpdtkta-uc.a.run.app\"]",
"serving.knative.dev/creator": "johnpccd3@gmail.com", "serving.knative.dev/creator": "johnpccd3@gmail.com",
"serving.knative.dev/lastModifier": "johnpccd3@gmail.com" "serving.knative.dev/lastModifier": "johnpccd3@gmail.com"
@ -145,10 +183,10 @@
"cloud.googleapis.com/location": "us-central1", "cloud.googleapis.com/location": "us-central1",
"goog-terraform-provisioned": "true" "goog-terraform-provisioned": "true"
}, },
"generation": 1, "generation": 2,
"labels": {}, "labels": {},
"namespace": "gen-lang-client-0424120530", "namespace": "gen-lang-client-0424120530",
"resource_version": "AAY16EtYS9U", "resource_version": "AAY16Gy+yWQ",
"self_link": "/apis/serving.knative.dev/v1/namespaces/761163285547/services/sereact", "self_link": "/apis/serving.knative.dev/v1/namespaces/761163285547/services/sereact",
"terraform_labels": { "terraform_labels": {
"goog-terraform-provisioned": "true" "goog-terraform-provisioned": "true"
@ -180,14 +218,14 @@
"type": "RoutesReady" "type": "RoutesReady"
} }
], ],
"latest_created_revision_name": "sereact-00001-hw9", "latest_created_revision_name": "sereact-00002-cew",
"latest_ready_revision_name": "sereact-00001-hw9", "latest_ready_revision_name": "sereact-00002-cew",
"observed_generation": 1, "observed_generation": 2,
"traffic": [ "traffic": [
{ {
"latest_revision": true, "latest_revision": true,
"percent": 100, "percent": 100,
"revision_name": "sereact-00001-hw9", "revision_name": "sereact-00002-cew",
"tag": "", "tag": "",
"url": "" "url": ""
} }
@ -200,13 +238,15 @@
"metadata": [ "metadata": [
{ {
"annotations": { "annotations": {
"autoscaling.knative.dev/maxScale": "10" "autoscaling.knative.dev/maxScale": "10",
"run.googleapis.com/client-name": "gcloud",
"run.googleapis.com/client-version": "431.0.0"
}, },
"generation": 0, "generation": 0,
"labels": { "labels": {
"run.googleapis.com/startupProbeType": "Default" "run.googleapis.com/startupProbeType": "Default"
}, },
"name": "", "name": "sereact-00002-cew",
"namespace": "", "namespace": "",
"resource_version": "", "resource_version": "",
"self_link": "", "self_link": "",
@ -417,6 +457,141 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_cloudfunctions2_function",
"name": "image_processor",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"build_config": [
{
"automatic_update_policy": [
{}
],
"build": "projects/761163285547/locations/us-central1/builds/d3341e98-07e4-49de-8dc7-3d53e4d2570a",
"docker_repository": "projects/gen-lang-client-0424120530/locations/us-central1/repositories/gcf-artifacts",
"entry_point": "process_image_embedding",
"environment_variables": {},
"on_deploy_update_policy": [],
"runtime": "python311",
"service_account": "projects/gen-lang-client-0424120530/serviceAccounts/761163285547-compute@developer.gserviceaccount.com",
"source": [
{
"repo_source": [],
"storage_source": [
{
"bucket": "gen-lang-client-0424120530-cloud-function-source",
"generation": 1748123369545880,
"object": "function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip"
}
]
}
],
"worker_pool": ""
}
],
"description": "Process image embeddings and store in vector database",
"effective_labels": {
"goog-terraform-provisioned": "true"
},
"environment": "GEN_2",
"event_trigger": [
{
"event_filters": [],
"event_type": "google.cloud.pubsub.topic.v1.messagePublished",
"pubsub_topic": "projects/gen-lang-client-0424120530/topics/image-processing-topic",
"retry_policy": "RETRY_POLICY_RETRY",
"service_account_email": "761163285547-compute@developer.gserviceaccount.com",
"trigger": "projects/gen-lang-client-0424120530/locations/us-central1/triggers/process-image-embedding-422683",
"trigger_region": "us-central1"
}
],
"id": "projects/gen-lang-client-0424120530/locations/us-central1/functions/process-image-embedding",
"kms_key_name": "",
"labels": null,
"location": "us-central1",
"name": "process-image-embedding",
"project": "gen-lang-client-0424120530",
"service_config": [
{
"all_traffic_on_latest_revision": true,
"available_cpu": "0.3333",
"available_memory": "512M",
"binary_authorization_policy": "",
"environment_variables": {
"LOG_EXECUTION_ID": "true",
"QDRANT_API_KEY": "",
"QDRANT_COLLECTION": "image_vectors",
"QDRANT_HOST": "34.71.6.1",
"QDRANT_PORT": "6333"
},
"gcf_uri": "",
"ingress_settings": "ALLOW_ALL",
"max_instance_count": 10,
"max_instance_request_concurrency": 1,
"min_instance_count": 0,
"secret_environment_variables": [],
"secret_volumes": [],
"service": "projects/gen-lang-client-0424120530/locations/us-central1/services/process-image-embedding",
"service_account_email": "761163285547-compute@developer.gserviceaccount.com",
"timeout_seconds": 540,
"uri": "https://process-image-embedding-p64zpdtkta-uc.a.run.app",
"vpc_connector": "",
"vpc_connector_egress_settings": ""
}
],
"state": "ACTIVE",
"terraform_labels": {
"goog-terraform-provisioned": "true"
},
"timeouts": null,
"update_time": "2025-05-24T21:52:26.933576416Z",
"url": "https://us-central1-gen-lang-client-0424120530.cloudfunctions.net/process-image-embedding"
},
"sensitive_attributes": [
[
{
"type": "get_attr",
"value": "service_config"
},
{
"type": "index",
"value": {
"value": 0,
"type": "number"
}
},
{
"type": "get_attr",
"value": "environment_variables"
},
{
"type": "index",
"value": {
"value": "QDRANT_API_KEY",
"type": "string"
}
}
]
],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjozNjAwMDAwMDAwMDAwLCJkZWxldGUiOjM2MDAwMDAwMDAwMDAsInVwZGF0ZSI6MzYwMDAwMDAwMDAwMH19",
"dependencies": [
"data.archive_file.function_source",
"data.google_project.current",
"google_compute_address.vector_db_static_ip",
"google_compute_instance.vector_db_vm",
"google_project_service.services",
"google_pubsub_topic.image_processing",
"google_service_account.vector_db_sa",
"google_storage_bucket.function_source",
"google_storage_bucket_object.function_source"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_compute_firewall", "type": "google_compute_firewall",
@ -690,7 +865,7 @@
"delete_protection_state": "DELETE_PROTECTION_DISABLED", "delete_protection_state": "DELETE_PROTECTION_DISABLED",
"deletion_policy": "ABANDON", "deletion_policy": "ABANDON",
"earliest_version_time": "2025-05-24T21:09:24.677010Z", "earliest_version_time": "2025-05-24T21:09:24.677010Z",
"etag": "IJCLh6eGvY0DMKrW4vCEvY0D", "etag": "IOXfuveKvY0DMKrW4vCEvY0D",
"id": "projects/gen-lang-client-0424120530/databases/sereact-imagedb", "id": "projects/gen-lang-client-0424120530/databases/sereact-imagedb",
"key_prefix": "", "key_prefix": "",
"location_id": "us-central1", "location_id": "us-central1",
@ -711,12 +886,160 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_eventarc_receiver",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16K9kGDo=",
"id": "gen-lang-client-0424120530/roles/eventarc.eventReceiver/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/eventarc.eventReceiver"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_firestore",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16Kj5NHI=",
"id": "gen-lang-client-0424120530/roles/datastore.user/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/datastore.user"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_pubsub_subscriber",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16K9kGDo=",
"id": "gen-lang-client-0424120530/roles/pubsub.subscriber/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/pubsub.subscriber"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_storage",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16Kj5NHI=",
"id": "gen-lang-client-0424120530/roles/storage.objectViewer/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/storage.objectViewer"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_vision",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16Kj5NHI=",
"id": "gen-lang-client-0424120530/roles/ml.developer/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/ml.developer"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_project_service", "type": "google_project_service",
"name": "services", "name": "services",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]", "provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [ "instances": [
{
"index_key": "cloudbuild.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/cloudbuild.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "cloudbuild.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{
"index_key": "cloudfunctions.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/cloudfunctions.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "cloudfunctions.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{ {
"index_key": "cloudresourcemanager.googleapis.com", "index_key": "cloudresourcemanager.googleapis.com",
"schema_version": 0, "schema_version": 0,
@ -759,6 +1082,20 @@
"sensitive_attributes": [], "sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
}, },
{
"index_key": "eventarc.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/eventarc.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "eventarc.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{ {
"index_key": "firestore.googleapis.com", "index_key": "firestore.googleapis.com",
"schema_version": 0, "schema_version": 0,
@ -773,6 +1110,20 @@
"sensitive_attributes": [], "sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
}, },
{
"index_key": "pubsub.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/pubsub.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "pubsub.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{ {
"index_key": "run.googleapis.com", "index_key": "run.googleapis.com",
"schema_version": 0, "schema_version": 0,
@ -803,73 +1154,6 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_pubsub_subscription",
"name": "image_processing",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"ack_deadline_seconds": 600,
"bigquery_config": [],
"cloud_storage_config": [],
"dead_letter_policy": [
{
"dead_letter_topic": "projects/gen-lang-client-0424120530/topics/image-processing-topic-dlq",
"max_delivery_attempts": 5
}
],
"effective_labels": {
"component": "image-processing",
"environment": "dev",
"goog-terraform-provisioned": "true",
"service": "sereact"
},
"enable_exactly_once_delivery": false,
"enable_message_ordering": false,
"expiration_policy": [
{
"ttl": "2678400s"
}
],
"filter": "",
"id": "projects/gen-lang-client-0424120530/subscriptions/image-processing-topic-subscription",
"labels": {
"component": "image-processing",
"environment": "dev",
"service": "sereact"
},
"message_retention_duration": "604800s",
"name": "image-processing-topic-subscription",
"project": "gen-lang-client-0424120530",
"push_config": [],
"retain_acked_messages": false,
"retry_policy": [
{
"maximum_backoff": "600s",
"minimum_backoff": "10s"
}
],
"terraform_labels": {
"component": "image-processing",
"environment": "dev",
"goog-terraform-provisioned": "true",
"service": "sereact"
},
"timeouts": null,
"topic": "projects/gen-lang-client-0424120530/topics/image-processing-topic"
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInVwZGF0ZSI6MTIwMDAwMDAwMDAwMH19",
"dependencies": [
"google_pubsub_topic.image_processing",
"google_pubsub_topic.image_processing_dlq"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_pubsub_subscription", "type": "google_pubsub_subscription",
@ -926,36 +1210,6 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_pubsub_subscription_iam_binding",
"name": "image_processing_subscriber",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16CF7/Zw=",
"id": "projects/gen-lang-client-0424120530/subscriptions/image-processing-topic-subscription/roles/pubsub.subscriber",
"members": [
"serviceAccount:761163285547-compute@developer.gserviceaccount.com"
],
"project": null,
"role": "roles/pubsub.subscriber",
"subscription": "image-processing-topic-subscription"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current",
"google_pubsub_subscription.image_processing",
"google_pubsub_topic.image_processing",
"google_pubsub_topic.image_processing_dlq"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_pubsub_topic", "type": "google_pubsub_topic",
@ -1155,6 +1409,122 @@
] ]
} }
] ]
},
{
"mode": "managed",
"type": "google_storage_bucket",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 3,
"attributes": {
"autoclass": [],
"cors": [],
"custom_placement_config": [],
"default_event_based_hold": false,
"effective_labels": {
"goog-terraform-provisioned": "true"
},
"enable_object_retention": false,
"encryption": [],
"force_destroy": false,
"hierarchical_namespace": [
{
"enabled": false
}
],
"id": "gen-lang-client-0424120530-cloud-function-source",
"labels": {},
"lifecycle_rule": [],
"location": "US-CENTRAL1",
"logging": [],
"name": "gen-lang-client-0424120530-cloud-function-source",
"project": "gen-lang-client-0424120530",
"project_number": 761163285547,
"public_access_prevention": "inherited",
"requester_pays": false,
"retention_policy": [],
"rpo": null,
"self_link": "https://www.googleapis.com/storage/v1/b/gen-lang-client-0424120530-cloud-function-source",
"soft_delete_policy": [
{
"effective_time": "2025-05-24T21:47:35.399Z",
"retention_duration_seconds": 604800
}
],
"storage_class": "STANDARD",
"terraform_labels": {
"goog-terraform-provisioned": "true"
},
"time_created": "2025-05-24T21:47:35.399Z",
"timeouts": null,
"uniform_bucket_level_access": true,
"updated": "2025-05-24T21:47:35.399Z",
"url": "gs://gen-lang-client-0424120530-cloud-function-source",
"versioning": [],
"website": []
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjo2MDAwMDAwMDAwMDAsInJlYWQiOjI0MDAwMDAwMDAwMCwidXBkYXRlIjoyNDAwMDAwMDAwMDB9LCJzY2hlbWFfdmVyc2lvbiI6IjMifQ==",
"dependencies": [
"google_project_service.services"
]
}
]
},
{
"mode": "managed",
"type": "google_storage_bucket_object",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"bucket": "gen-lang-client-0424120530-cloud-function-source",
"cache_control": "",
"content": null,
"content_disposition": "",
"content_encoding": "",
"content_language": "",
"content_type": "application/zip",
"crc32c": "tbmr3A==",
"customer_encryption": [],
"detect_md5hash": "leuOpRRrZvWya7gw4/Dqtg==",
"event_based_hold": false,
"generation": 1748123256911890,
"id": "gen-lang-client-0424120530-cloud-function-source-function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"kms_key_name": "",
"md5hash": "leuOpRRrZvWya7gw4/Dqtg==",
"md5hexhash": "95eb8ea5146b66f5b26bb830e3f0eab6",
"media_link": "https://storage.googleapis.com/download/storage/v1/b/gen-lang-client-0424120530-cloud-function-source/o/function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip?generation=1748123256911890\u0026alt=media",
"metadata": {},
"name": "function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"output_name": "function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"retention": [],
"self_link": "https://www.googleapis.com/storage/v1/b/gen-lang-client-0424120530-cloud-function-source/o/function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"source": "./function-source.zip",
"storage_class": "STANDARD",
"temporary_hold": false,
"timeouts": null
},
"sensitive_attributes": [
[
{
"type": "get_attr",
"value": "content"
}
]
],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoyNDAwMDAwMDAwMDAsImRlbGV0ZSI6MjQwMDAwMDAwMDAwLCJ1cGRhdGUiOjI0MDAwMDAwMDAwMH19",
"dependencies": [
"data.archive_file.function_source",
"google_project_service.services",
"google_storage_bucket.function_source"
]
}
]
} }
], ],
"check_results": null "check_results": null

View File

@ -1,9 +1,13 @@
{ {
"version": 4, "version": 4,
"terraform_version": "1.10.1", "terraform_version": "1.10.1",
"serial": 368, "serial": 381,
"lineage": "a183cd95-f987-8698-c6dd-84e933c394a5", "lineage": "a183cd95-f987-8698-c6dd-84e933c394a5",
"outputs": { "outputs": {
"cloud_function_name": {
"value": "process-image-embedding",
"type": "string"
},
"cloud_run_qdrant_host": { "cloud_run_qdrant_host": {
"value": "34.71.6.1", "value": "34.71.6.1",
"type": "string" "type": "string"
@ -49,10 +53,6 @@
"value": "image-processing-topic-dlq", "value": "image-processing-topic-dlq",
"type": "string" "type": "string"
}, },
"pubsub_subscription_name": {
"value": "image-processing-topic-subscription",
"type": "string"
},
"pubsub_topic_name": { "pubsub_topic_name": {
"value": "image-processing-topic", "value": "image-processing-topic",
"type": "string" "type": "string"
@ -83,6 +83,38 @@
} }
}, },
"resources": [ "resources": [
{
"mode": "data",
"type": "archive_file",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/archive\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"exclude_symlink_directories": null,
"excludes": null,
"id": "ebb70c54eaebd24049805bcc1425349f70bc582d",
"output_base64sha256": "+Q18L9q1o61gbnGJlSvTmwG9cRv1Qwzf8GI95No2Rb4=",
"output_base64sha512": "tK0wkH07eL77+ytrOI8lcHATsN/nP0f/CYq0uzrrlhaRbJ+wsO1/6y0tmeX1hF6xqxW5ZDYTrhrSnayA+2afwQ==",
"output_file_mode": null,
"output_md5": "95eb8ea5146b66f5b26bb830e3f0eab6",
"output_path": "./function-source.zip",
"output_sha": "ebb70c54eaebd24049805bcc1425349f70bc582d",
"output_sha256": "f90d7c2fdab5a3ad606e7189952bd39b01bd711bf5430cdff0623de4da3645be",
"output_sha512": "b4ad30907d3b78befbfb2b6b388f25707013b0dfe73f47ff098ab4bb3aeb9616916c9fb0b0ed7feb2d2d99e5f5845eb1ab15b9643613ae1ad29dac80fb669fc1",
"output_size": 4781,
"source": [],
"source_content": null,
"source_content_filename": null,
"source_dir": "./../cloud-function",
"source_file": null,
"type": "zip"
},
"sensitive_attributes": []
}
]
},
{ {
"mode": "data", "mode": "data",
"type": "google_project", "type": "google_project",
@ -134,9 +166,11 @@
"run.googleapis.com/ingress": "all" "run.googleapis.com/ingress": "all"
}, },
"effective_annotations": { "effective_annotations": {
"run.googleapis.com/client-name": "gcloud",
"run.googleapis.com/client-version": "431.0.0",
"run.googleapis.com/ingress": "all", "run.googleapis.com/ingress": "all",
"run.googleapis.com/ingress-status": "all", "run.googleapis.com/ingress-status": "all",
"run.googleapis.com/operation-id": "3653c984-38f6-42b8-b3c1-9a6814773095", "run.googleapis.com/operation-id": "e4d7484f-39e4-4dde-8105-28d285eb927b",
"run.googleapis.com/urls": "[\"https://sereact-761163285547.us-central1.run.app\",\"https://sereact-p64zpdtkta-uc.a.run.app\"]", "run.googleapis.com/urls": "[\"https://sereact-761163285547.us-central1.run.app\",\"https://sereact-p64zpdtkta-uc.a.run.app\"]",
"serving.knative.dev/creator": "johnpccd3@gmail.com", "serving.knative.dev/creator": "johnpccd3@gmail.com",
"serving.knative.dev/lastModifier": "johnpccd3@gmail.com" "serving.knative.dev/lastModifier": "johnpccd3@gmail.com"
@ -145,10 +179,10 @@
"cloud.googleapis.com/location": "us-central1", "cloud.googleapis.com/location": "us-central1",
"goog-terraform-provisioned": "true" "goog-terraform-provisioned": "true"
}, },
"generation": 1, "generation": 2,
"labels": {}, "labels": {},
"namespace": "gen-lang-client-0424120530", "namespace": "gen-lang-client-0424120530",
"resource_version": "AAY16EtYS9U", "resource_version": "AAY16Gy+yWQ",
"self_link": "/apis/serving.knative.dev/v1/namespaces/761163285547/services/sereact", "self_link": "/apis/serving.knative.dev/v1/namespaces/761163285547/services/sereact",
"terraform_labels": { "terraform_labels": {
"goog-terraform-provisioned": "true" "goog-terraform-provisioned": "true"
@ -180,14 +214,14 @@
"type": "RoutesReady" "type": "RoutesReady"
} }
], ],
"latest_created_revision_name": "sereact-00001-hw9", "latest_created_revision_name": "sereact-00002-cew",
"latest_ready_revision_name": "sereact-00001-hw9", "latest_ready_revision_name": "sereact-00002-cew",
"observed_generation": 1, "observed_generation": 2,
"traffic": [ "traffic": [
{ {
"latest_revision": true, "latest_revision": true,
"percent": 100, "percent": 100,
"revision_name": "sereact-00001-hw9", "revision_name": "sereact-00002-cew",
"tag": "", "tag": "",
"url": "" "url": ""
} }
@ -200,13 +234,15 @@
"metadata": [ "metadata": [
{ {
"annotations": { "annotations": {
"autoscaling.knative.dev/maxScale": "10" "autoscaling.knative.dev/maxScale": "10",
"run.googleapis.com/client-name": "gcloud",
"run.googleapis.com/client-version": "431.0.0"
}, },
"generation": 0, "generation": 0,
"labels": { "labels": {
"run.googleapis.com/startupProbeType": "Default" "run.googleapis.com/startupProbeType": "Default"
}, },
"name": "", "name": "sereact-00002-cew",
"namespace": "", "namespace": "",
"resource_version": "", "resource_version": "",
"self_link": "", "self_link": "",
@ -417,6 +453,13 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_compute_address",
"name": "vector_db_static_ip",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": []
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_compute_firewall", "type": "google_compute_firewall",
@ -637,7 +680,7 @@
}, },
{ {
"type": "get_attr", "type": "get_attr",
"value": "disk_encryption_key_rsa" "value": "disk_encryption_key_raw"
} }
], ],
[ [
@ -654,7 +697,7 @@
}, },
{ {
"type": "get_attr", "type": "get_attr",
"value": "disk_encryption_key_raw" "value": "disk_encryption_key_rsa"
} }
], ],
[ [
@ -690,7 +733,7 @@
"delete_protection_state": "DELETE_PROTECTION_DISABLED", "delete_protection_state": "DELETE_PROTECTION_DISABLED",
"deletion_policy": "ABANDON", "deletion_policy": "ABANDON",
"earliest_version_time": "2025-05-24T21:09:24.677010Z", "earliest_version_time": "2025-05-24T21:09:24.677010Z",
"etag": "IIa6rZSGvY0DMKrW4vCEvY0D", "etag": "IPvK9cCKvY0DMKrW4vCEvY0D",
"id": "projects/gen-lang-client-0424120530/databases/sereact-imagedb", "id": "projects/gen-lang-client-0424120530/databases/sereact-imagedb",
"key_prefix": "", "key_prefix": "",
"location_id": "us-central1", "location_id": "us-central1",
@ -711,12 +754,112 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_firestore",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16KjLzjY=",
"id": "gen-lang-client-0424120530/roles/datastore.user/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/datastore.user"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_storage",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16KjLzjY=",
"id": "gen-lang-client-0424120530/roles/storage.objectViewer/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/storage.objectViewer"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{
"mode": "managed",
"type": "google_project_iam_member",
"name": "function_vision",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16KjLzjY=",
"id": "gen-lang-client-0424120530/roles/ml.developer/serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"member": "serviceAccount:761163285547-compute@developer.gserviceaccount.com",
"project": "gen-lang-client-0424120530",
"role": "roles/ml.developer"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_project_service", "type": "google_project_service",
"name": "services", "name": "services",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]", "provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [ "instances": [
{
"index_key": "cloudbuild.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/cloudbuild.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "cloudbuild.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{
"index_key": "cloudfunctions.googleapis.com",
"schema_version": 0,
"attributes": {
"disable_dependent_services": null,
"disable_on_destroy": false,
"id": "gen-lang-client-0424120530/cloudfunctions.googleapis.com",
"project": "gen-lang-client-0424120530",
"service": "cloudfunctions.googleapis.com",
"timeouts": null
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0="
},
{ {
"index_key": "cloudresourcemanager.googleapis.com", "index_key": "cloudresourcemanager.googleapis.com",
"schema_version": 0, "schema_version": 0,
@ -803,73 +946,6 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_pubsub_subscription",
"name": "image_processing",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"ack_deadline_seconds": 600,
"bigquery_config": [],
"cloud_storage_config": [],
"dead_letter_policy": [
{
"dead_letter_topic": "projects/gen-lang-client-0424120530/topics/image-processing-topic-dlq",
"max_delivery_attempts": 5
}
],
"effective_labels": {
"component": "image-processing",
"environment": "dev",
"goog-terraform-provisioned": "true",
"service": "sereact"
},
"enable_exactly_once_delivery": false,
"enable_message_ordering": false,
"expiration_policy": [
{
"ttl": "2678400s"
}
],
"filter": "",
"id": "projects/gen-lang-client-0424120530/subscriptions/image-processing-topic-subscription",
"labels": {
"component": "image-processing",
"environment": "dev",
"service": "sereact"
},
"message_retention_duration": "604800s",
"name": "image-processing-topic-subscription",
"project": "gen-lang-client-0424120530",
"push_config": [],
"retain_acked_messages": false,
"retry_policy": [
{
"maximum_backoff": "600s",
"minimum_backoff": "10s"
}
],
"terraform_labels": {
"component": "image-processing",
"environment": "dev",
"goog-terraform-provisioned": "true",
"service": "sereact"
},
"timeouts": null,
"topic": "projects/gen-lang-client-0424120530/topics/image-processing-topic"
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInVwZGF0ZSI6MTIwMDAwMDAwMDAwMH19",
"dependencies": [
"google_pubsub_topic.image_processing",
"google_pubsub_topic.image_processing_dlq"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_pubsub_subscription", "type": "google_pubsub_subscription",
@ -926,36 +1002,6 @@
} }
] ]
}, },
{
"mode": "managed",
"type": "google_pubsub_subscription_iam_binding",
"name": "image_processing_subscriber",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"condition": [],
"etag": "BwY16CF7/Zw=",
"id": "projects/gen-lang-client-0424120530/subscriptions/image-processing-topic-subscription/roles/pubsub.subscriber",
"members": [
"serviceAccount:761163285547-compute@developer.gserviceaccount.com"
],
"project": null,
"role": "roles/pubsub.subscriber",
"subscription": "image-processing-topic-subscription"
},
"sensitive_attributes": [],
"private": "bnVsbA==",
"dependencies": [
"data.google_project.current",
"google_pubsub_subscription.image_processing",
"google_pubsub_topic.image_processing",
"google_pubsub_topic.image_processing_dlq"
]
}
]
},
{ {
"mode": "managed", "mode": "managed",
"type": "google_pubsub_topic", "type": "google_pubsub_topic",
@ -1155,6 +1201,122 @@
] ]
} }
] ]
},
{
"mode": "managed",
"type": "google_storage_bucket",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 3,
"attributes": {
"autoclass": [],
"cors": [],
"custom_placement_config": [],
"default_event_based_hold": false,
"effective_labels": {
"goog-terraform-provisioned": "true"
},
"enable_object_retention": false,
"encryption": [],
"force_destroy": false,
"hierarchical_namespace": [
{
"enabled": false
}
],
"id": "gen-lang-client-0424120530-cloud-function-source",
"labels": null,
"lifecycle_rule": [],
"location": "US-CENTRAL1",
"logging": [],
"name": "gen-lang-client-0424120530-cloud-function-source",
"project": "gen-lang-client-0424120530",
"project_number": 761163285547,
"public_access_prevention": "inherited",
"requester_pays": false,
"retention_policy": [],
"rpo": null,
"self_link": "https://www.googleapis.com/storage/v1/b/gen-lang-client-0424120530-cloud-function-source",
"soft_delete_policy": [
{
"effective_time": "2025-05-24T21:47:35.399Z",
"retention_duration_seconds": 604800
}
],
"storage_class": "STANDARD",
"terraform_labels": {
"goog-terraform-provisioned": "true"
},
"time_created": "2025-05-24T21:47:35.399Z",
"timeouts": null,
"uniform_bucket_level_access": true,
"updated": "2025-05-24T21:47:35.399Z",
"url": "gs://gen-lang-client-0424120530-cloud-function-source",
"versioning": [],
"website": []
},
"sensitive_attributes": [],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjo2MDAwMDAwMDAwMDAsInJlYWQiOjI0MDAwMDAwMDAwMCwidXBkYXRlIjoyNDAwMDAwMDAwMDB9LCJzY2hlbWFfdmVyc2lvbiI6IjMifQ==",
"dependencies": [
"google_project_service.services"
]
}
]
},
{
"mode": "managed",
"type": "google_storage_bucket_object",
"name": "function_source",
"provider": "provider[\"registry.terraform.io/hashicorp/google\"]",
"instances": [
{
"schema_version": 0,
"attributes": {
"bucket": "gen-lang-client-0424120530-cloud-function-source",
"cache_control": "",
"content": null,
"content_disposition": "",
"content_encoding": "",
"content_language": "",
"content_type": "application/zip",
"crc32c": "tbmr3A==",
"customer_encryption": [],
"detect_md5hash": "leuOpRRrZvWya7gw4/Dqtg==",
"event_based_hold": false,
"generation": 1748123256911890,
"id": "gen-lang-client-0424120530-cloud-function-source-function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"kms_key_name": "",
"md5hash": "leuOpRRrZvWya7gw4/Dqtg==",
"md5hexhash": "95eb8ea5146b66f5b26bb830e3f0eab6",
"media_link": "https://storage.googleapis.com/download/storage/v1/b/gen-lang-client-0424120530-cloud-function-source/o/function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip?generation=1748123256911890\u0026alt=media",
"metadata": null,
"name": "function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"output_name": "function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"retention": [],
"self_link": "https://www.googleapis.com/storage/v1/b/gen-lang-client-0424120530-cloud-function-source/o/function-source-95eb8ea5146b66f5b26bb830e3f0eab6.zip",
"source": "./function-source.zip",
"storage_class": "STANDARD",
"temporary_hold": false,
"timeouts": null
},
"sensitive_attributes": [
[
{
"type": "get_attr",
"value": "content"
}
]
],
"private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoyNDAwMDAwMDAwMDAsImRlbGV0ZSI6MjQwMDAwMDAwMDAwLCJ1cGRhdGUiOjI0MDAwMDAwMDAwMH19",
"dependencies": [
"data.archive_file.function_source",
"google_project_service.services",
"google_storage_bucket.function_source"
]
}
]
} }
], ],
"check_results": null "check_results": null