From f1c41a074d10bfd94f3e9b052acb6d3585812bdc Mon Sep 17 00:00:00 2001 From: johnpccd Date: Fri, 23 May 2025 22:54:02 +0200 Subject: [PATCH] cp --- .gitignore | 4 + deployment/README.md | 64 +++ deployment/cloudbuild.yaml | 54 +++ deployment/deploy.sh | 142 ++++++ deployment/terraform/.terraform.lock.hcl | 21 + deployment/terraform/README.md | 95 ++++ deployment/terraform/main.tf | 94 ++++ deployment/terraform/outputs.tf | 19 + deployment/terraform/terraform.tfstate | 9 + deployment/terraform/terraform.tfstate.backup | 416 ++++++++++++++++++ deployment/terraform/terraform.tfvars.example | 5 + deployment/terraform/variables.tf | 27 ++ 12 files changed, 950 insertions(+) create mode 100644 deployment/README.md create mode 100644 deployment/cloudbuild.yaml create mode 100644 deployment/deploy.sh create mode 100644 deployment/terraform/.terraform.lock.hcl create mode 100644 deployment/terraform/README.md create mode 100644 deployment/terraform/main.tf create mode 100644 deployment/terraform/outputs.tf create mode 100644 deployment/terraform/terraform.tfstate create mode 100644 deployment/terraform/terraform.tfstate.backup create mode 100644 deployment/terraform/terraform.tfvars.example create mode 100644 deployment/terraform/variables.tf diff --git a/.gitignore b/.gitignore index 09ecf58..1631e6e 100644 --- a/.gitignore +++ b/.gitignore @@ -49,3 +49,7 @@ htmlcov/ .coverage.* coverage.xml *.cover + +# Terraform +*.tfvars +.terraform diff --git a/deployment/README.md b/deployment/README.md new file mode 100644 index 0000000..3dde3a0 --- /dev/null +++ b/deployment/README.md @@ -0,0 +1,64 @@ +# Deployment Options for Sereact + +This directory contains multiple options for deploying the Sereact application: + +## Terraform Infrastructure (`/terraform`) + +The Terraform configuration automates the provisioning of all required Google Cloud resources: + +- Google Cloud Run service +- Google Container Registry (GCR) +- Cloud Firestore +- Cloud Storage buckets + +See [terraform/README.md](terraform/README.md) for detailed instructions. + +## Cloud Run Deployment (`/cloud-run`) + +The `service.yaml` file defines the Cloud Run service configuration which can be deployed using: + +```bash +gcloud run services replace deployment/cloud-run/service.yaml --region=us-central1 +``` + +## Deployment Script (`deploy.sh`) + +For convenience, a deployment script is provided to handle the entire deployment workflow: + +```bash +# Provision infrastructure with Terraform +./deployment/deploy.sh --provision + +# Build and push Docker image +./deployment/deploy.sh --build + +# Deploy to Cloud Run +./deployment/deploy.sh --deploy + +# Do everything (provision, build, deploy) +./deployment/deploy.sh --all +``` + +## CI/CD Pipelines + +For CI/CD integration, consider using: + +1. **GitHub Actions**: Sample workflow included in terraform/README.md +2. **Cloud Build**: Configure a `cloudbuild.yaml` in your repository +3. **Jenkins**: Use the `deploy.sh` script in your pipeline + +## Managing Secrets + +Sensitive data should be managed using Google Secret Manager: + +```bash +# Create a secret +gcloud secrets create sereact-db-uri --replication-policy="automatic" + +# Add a secret version +echo -n "your-mongodb-uri" | gcloud secrets versions add sereact-db-uri --data-file=- + +# Update Cloud Run service to use the secret +gcloud run services update sereact \ + --update-secrets=DATABASE_URI=sereact-db-uri:latest +``` \ No newline at end of file diff --git a/deployment/cloudbuild.yaml b/deployment/cloudbuild.yaml new file mode 100644 index 0000000..d957ac0 --- /dev/null +++ b/deployment/cloudbuild.yaml @@ -0,0 +1,54 @@ +steps: +# Build the container image +- name: 'gcr.io/cloud-builders/docker' + args: ['build', '-t', 'gcr.io/$PROJECT_ID/sereact:$COMMIT_SHA', '.'] + +# Push the container image to Container Registry +- name: 'gcr.io/cloud-builders/docker' + args: ['push', 'gcr.io/$PROJECT_ID/sereact:$COMMIT_SHA'] + +# Tag the image as latest +- name: 'gcr.io/cloud-builders/docker' + args: ['tag', 'gcr.io/$PROJECT_ID/sereact:$COMMIT_SHA', 'gcr.io/$PROJECT_ID/sereact:latest'] + +# Push the latest tag +- name: 'gcr.io/cloud-builders/docker' + args: ['push', 'gcr.io/$PROJECT_ID/sereact:latest'] + +# Deploy to Cloud Run +- name: 'gcr.io/google.com/cloudsdktool/cloud-sdk' + entrypoint: gcloud + args: + - 'run' + - 'deploy' + - 'sereact' + - '--image=gcr.io/$PROJECT_ID/sereact:$COMMIT_SHA' + - '--region=us-central1' + - '--platform=managed' + - '--allow-unauthenticated' + - '--set-env-vars=GCS_BUCKET_NAME=${_GCS_BUCKET_NAME},DATABASE_NAME=${_DATABASE_NAME},VECTOR_DB_ENVIRONMENT=${_VECTOR_DB_ENVIRONMENT},VECTOR_DB_INDEX_NAME=${_VECTOR_DB_INDEX_NAME},LOG_LEVEL=INFO' + - '--set-secrets=DATABASE_URI=sereact-db-uri:latest,API_KEY_SECRET=sereact-api-key-secret:latest,VECTOR_DB_API_KEY=sereact-vector-db-key:latest' + +# Optional: Run tests after deployment +# - name: 'gcr.io/google.com/cloudsdktool/cloud-sdk' +# entrypoint: /bin/bash +# args: +# - '-c' +# - | +# SERVICE_URL=$(gcloud run services describe sereact --region=us-central1 --format='value(status.url)') +# curl -s -o /dev/null -w "%{http_code}" $${SERVICE_URL}/health | grep 200 + +# Store images in Container Registry +images: + - 'gcr.io/$PROJECT_ID/sereact:$COMMIT_SHA' + - 'gcr.io/$PROJECT_ID/sereact:latest' + +# Substitution variables to be set in the Cloud Build trigger +substitutions: + _GCS_BUCKET_NAME: 'your-app-storage-bucket' + _DATABASE_NAME: 'imagedb' + _VECTOR_DB_ENVIRONMENT: 'your-pinecone-env' + _VECTOR_DB_INDEX_NAME: 'image-embeddings' + +# Increase timeout to 30 minutes +timeout: '1800s' \ No newline at end of file diff --git a/deployment/deploy.sh b/deployment/deploy.sh new file mode 100644 index 0000000..5ded0cc --- /dev/null +++ b/deployment/deploy.sh @@ -0,0 +1,142 @@ +#!/bin/bash +set -e + +# Configuration +PROJECT_ID=$(gcloud config get-value project) +IMAGE_NAME="sereact" +REGION="us-central1" +SERVICE_NAME="sereact" + +# Help function +function show_help { + echo "Usage: $0 [options]" + echo "Options:" + echo " --provision Run Terraform to provision cloud resources" + echo " --build Build and push Docker image" + echo " --deploy Deploy to Cloud Run" + echo " --all Do all of the above" + echo " --help Show this help message" + exit 0 +} + +# Check if any arguments were provided +if [ $# -eq 0 ]; then + show_help +fi + +# Process arguments +PROVISION=false +BUILD=false +DEPLOY=false + +while [[ $# -gt 0 ]]; do + case "$1" in + --provision) + PROVISION=true + shift + ;; + --build) + BUILD=true + shift + ;; + --deploy) + DEPLOY=true + shift + ;; + --all) + PROVISION=true + BUILD=true + DEPLOY=true + shift + ;; + --help) + show_help + ;; + *) + echo "Unknown option: $1" + show_help + ;; + esac +done + +# Ensure gcloud is configured +if [ -z "$PROJECT_ID" ]; then + echo "ERROR: No Google Cloud project is set. Run 'gcloud config set project YOUR_PROJECT_ID'" + exit 1 +fi + +echo "Using Google Cloud project: $PROJECT_ID" +echo "===================================" + +# Provision resources with Terraform +if [ "$PROVISION" = true ]; then + echo "Provisioning cloud resources with Terraform..." + cd "$(dirname "$0")/terraform" + + # Check if terraform.tfvars exists, if not copy from example + if [ ! -f terraform.tfvars ]; then + echo "Creating terraform.tfvars from example..." + cp terraform.tfvars.example terraform.tfvars + # Replace project ID in tfvars file + sed -i "s/your-gcp-project-id/$PROJECT_ID/g" terraform.tfvars + echo "Please review and edit terraform.tfvars with your desired values" + exit 0 + fi + + terraform init + terraform apply + + cd - > /dev/null + echo "Provisioning completed." +fi + +# Build and push Docker image +if [ "$BUILD" = true ]; then + echo "Building and pushing Docker image..." + + # Enable Docker to authenticate to GCR + gcloud auth configure-docker gcr.io + + # Build the image with timestamp tag + TAG=$(date +%Y%m%d-%H%M%S) + FULL_IMAGE_NAME="gcr.io/$PROJECT_ID/$IMAGE_NAME:$TAG" + LATEST_IMAGE_NAME="gcr.io/$PROJECT_ID/$IMAGE_NAME:latest" + + echo "Building image: $FULL_IMAGE_NAME" + docker build -t "$FULL_IMAGE_NAME" -t "$LATEST_IMAGE_NAME" . + + echo "Pushing images to Container Registry..." + docker push "$FULL_IMAGE_NAME" + docker push "$LATEST_IMAGE_NAME" + + echo "Image built and pushed successfully." +fi + +# Deploy to Cloud Run +if [ "$DEPLOY" = true ]; then + echo "Deploying to Cloud Run..." + + # Deploy using the latest image + LATEST_IMAGE_NAME="gcr.io/$PROJECT_ID/$IMAGE_NAME:latest" + + # Check if we have an existing service.yaml to use + if [ -f "$(dirname "$0")/cloud-run/service.yaml" ]; then + echo "Deploying using service.yaml configuration..." + gcloud run services replace "$(dirname "$0")/cloud-run/service.yaml" --region="$REGION" + else + echo "Deploying directly..." + gcloud run deploy "$SERVICE_NAME" \ + --image="$LATEST_IMAGE_NAME" \ + --platform="managed" \ + --region="$REGION" \ + --allow-unauthenticated + fi + + # Get service URL + SERVICE_URL=$(gcloud run services describe "$SERVICE_NAME" --region="$REGION" --format='value(status.url)') + + echo "Deployment completed successfully." + echo "Service URL: $SERVICE_URL" +fi + +echo "All operations completed." \ No newline at end of file diff --git a/deployment/terraform/.terraform.lock.hcl b/deployment/terraform/.terraform.lock.hcl new file mode 100644 index 0000000..c26d39f --- /dev/null +++ b/deployment/terraform/.terraform.lock.hcl @@ -0,0 +1,21 @@ +# This file is maintained automatically by "terraform init". +# Manual edits may be lost in future updates. + +provider "registry.terraform.io/hashicorp/google" { + version = "6.36.1" + hashes = [ + "h1:rj3g00i0dH4VxXYO5xXJg188i6OXWbFUT6WmLbO5orY=", + "zh:161d054bda352a286a997f80f3d59366d072377abc6777bfe8abacc2e10ac2bf", + "zh:314c38d8050036176031f691b533184c3578036085483fed877b3b139f887047", + "zh:503c9807312feb9766f0da207d5ac149aa6f5a669144c60da38a33d072ebe2c2", + "zh:897abe484c44c625b301e828a4967c9f781fbf33b5bb50afe226410ebbfd0137", + "zh:97bcdc879b48f5f8bee98316234a1eed3c2e440e356631066d07b5d85ccfe288", + "zh:b273e940da85c5d673cbb3cafe36fb70dd8536e2d8812e617191196c312dac3b", + "zh:ba294699ca7082d394498ce62ecb55501c6a141fd1c43db00a6abdaebc92fa2e", + "zh:c50be96b5c8df5124f18ccdef473eed0bc3a2452e674c19f58fbf7ee14195af4", + "zh:d5a8fda3abda57d912be020e22bab3568facc729756e5339af9a3e56ca277cbc", + "zh:dddbfed09dff01fe538830714a13e71d7581cf2ccfba15acc0a6bb7266147bed", + "zh:e65e8c2e97d1e23c9380516b1d37e111cc700b538d8fca6b9e28ebb89e305ee0", + "zh:f569b65999264a9416862bca5cd2a6177d94ccb0424f3a4ef424428912b9cb3c", + ] +} diff --git a/deployment/terraform/README.md b/deployment/terraform/README.md new file mode 100644 index 0000000..ab91fc6 --- /dev/null +++ b/deployment/terraform/README.md @@ -0,0 +1,95 @@ +# Terraform Configuration for Sereact + +This directory contains Terraform configurations to provision the required Google Cloud resources for Sereact: + +- Google Cloud Run service +- Google Container Registry (GCR) +- Firestore database +- Cloud Storage bucket + +## Prerequisites + +1. Install [Terraform](https://www.terraform.io/downloads) (v1.0.0+) +2. Install [Google Cloud SDK](https://cloud.google.com/sdk/docs/install) +3. Authenticate with Google Cloud: + ```bash + gcloud auth login + gcloud auth application-default login + ``` +4. Create or select a Google Cloud project: + ```bash + gcloud projects create PROJECT_ID --name="Sereact Project" # optional + gcloud config set project PROJECT_ID + ``` + +## Setup and Usage + +1. Copy the example variables file and edit it with your values: + ```bash + cp terraform.tfvars.example terraform.tfvars + # Edit terraform.tfvars with your project-specific values + ``` + +2. Initialize Terraform: + ```bash + terraform init + ``` + +3. Preview the changes: + ```bash + terraform plan + ``` + +4. Apply the configuration: + ```bash + terraform apply + ``` + +5. After provisioning, you'll see outputs including: + - Cloud Run service URL + - Storage bucket name + - Firestore database ID + - Container Registry URL + +## Managing Secrets + +Secrets for environment variables (DATABASE_URI, API_KEY_SECRET, etc.) should be managed separately using Google Secret Manager: + +```bash +# Create secrets +gcloud secrets create sereact-db-uri --replication-policy="automatic" +gcloud secrets create sereact-api-key-secret --replication-policy="automatic" +gcloud secrets create sereact-vector-db-key --replication-policy="automatic" + +# Add secret versions +echo -n "your-secret-value" | gcloud secrets versions add sereact-db-uri --data-file=- +echo -n "your-secret-value" | gcloud secrets versions add sereact-api-key-secret --data-file=- +echo -n "your-secret-value" | gcloud secrets versions add sereact-vector-db-key --data-file=- + +# Update Cloud Run service to use secrets +gcloud run services update sereact \ + --update-secrets=DATABASE_URI=sereact-db-uri:latest,API_KEY_SECRET=sereact-api-key-secret:latest,VECTOR_DB_API_KEY=sereact-vector-db-key:latest +``` + +## CI/CD Integration + +To integrate this with CI/CD, store the `terraform.tfvars` securely in your CI/CD system and run Terraform as part of your deployment pipeline: + +```yaml +# Example GitHub Actions step +- name: Terraform Apply + run: | + cd deployment/terraform + terraform init + terraform apply -auto-approve + env: + GOOGLE_APPLICATION_CREDENTIALS: ${{ secrets.GCP_SA_KEY }} +``` + +## Destroying Resources + +To destroy all provisioned resources: + +```bash +terraform destroy +``` \ No newline at end of file diff --git a/deployment/terraform/main.tf b/deployment/terraform/main.tf new file mode 100644 index 0000000..1ec8dc9 --- /dev/null +++ b/deployment/terraform/main.tf @@ -0,0 +1,94 @@ +provider "google" { + project = var.project_id + region = var.region + zone = var.zone +} + +# Enable required APIs +resource "google_project_service" "services" { + for_each = toset([ + "cloudresourcemanager.googleapis.com", + "containerregistry.googleapis.com", + "run.googleapis.com", + "firestore.googleapis.com", + "storage.googleapis.com" + ]) + + project = var.project_id + service = each.key + + disable_on_destroy = false +} + +# Cloud Storage bucket +resource "google_storage_bucket" "app_bucket" { + name = var.storage_bucket_name + location = var.region + uniform_bucket_level_access = true + + depends_on = [google_project_service.services] +} + +# Firestore Database +resource "google_firestore_database" "database" { + name = var.firestore_db_name + location_id = var.region + type = "FIRESTORE_NATIVE" + + depends_on = [google_project_service.services] +} + +# Container Registry - no explicit resource needed, just enable the API +# You'll push images to gcr.io/${var.project_id}/sereact + +# Cloud Run service +resource "google_cloud_run_service" "sereact" { + name = "sereact" + location = var.region + + template { + spec { + containers { + # Using a public placeholder image that exists to avoid deployment failure + # You'll need to update this later with your actual image + image = "gcr.io/google-samples/hello-app:1.0" + + ports { + container_port = 8080 + } + + resources { + limits = { + cpu = "1" + memory = "512Mi" + } + } + + env { + name = "DATABASE_NAME" + value = var.firestore_db_name + } + + env { + name = "GCS_BUCKET_NAME" + value = var.storage_bucket_name + } + + env { + name = "LOG_LEVEL" + value = "INFO" + } + } + } + } + + depends_on = [google_project_service.services] +} + +# Make the Cloud Run service publicly accessible +resource "google_cloud_run_service_iam_member" "public_access" { + service = google_cloud_run_service.sereact.name + location = google_cloud_run_service.sereact.location + role = "roles/run.invoker" + member = "allUsers" +} \ No newline at end of file diff --git a/deployment/terraform/outputs.tf b/deployment/terraform/outputs.tf new file mode 100644 index 0000000..ef8f87e --- /dev/null +++ b/deployment/terraform/outputs.tf @@ -0,0 +1,19 @@ +output "cloud_run_url" { + value = google_cloud_run_service.sereact.status[0].url + description = "The URL of the deployed Cloud Run service" +} + +output "storage_bucket_name" { + value = google_storage_bucket.app_bucket.name + description = "The name of the provisioned Cloud Storage bucket" +} + +output "firestore_database_id" { + value = google_firestore_database.database.id + description = "The ID of the provisioned Firestore database" +} + +output "container_registry_url" { + value = "gcr.io/${var.project_id}/sereact" + description = "The URL of the Container Registry repository" +} \ No newline at end of file diff --git a/deployment/terraform/terraform.tfstate b/deployment/terraform/terraform.tfstate new file mode 100644 index 0000000..84b0c9e --- /dev/null +++ b/deployment/terraform/terraform.tfstate @@ -0,0 +1,9 @@ +{ + "version": 4, + "terraform_version": "1.10.1", + "serial": 28, + "lineage": "a183cd95-f987-8698-c6dd-84e933c394a5", + "outputs": {}, + "resources": [], + "check_results": null +} diff --git a/deployment/terraform/terraform.tfstate.backup b/deployment/terraform/terraform.tfstate.backup new file mode 100644 index 0000000..9652ce7 --- /dev/null +++ b/deployment/terraform/terraform.tfstate.backup @@ -0,0 +1,416 @@ +{ + "version": 4, + "terraform_version": "1.10.1", + "serial": 18, + "lineage": "a183cd95-f987-8698-c6dd-84e933c394a5", + "outputs": { + "cloud_run_url": { + "value": "https://sereact-p64zpdtkta-uc.a.run.app", + "type": "string" + }, + "container_registry_url": { + "value": "gcr.io/gen-lang-client-0424120530/sereact", + "type": "string" + }, + "firestore_database_id": { + "value": "projects/gen-lang-client-0424120530/databases/imagedb", + "type": "string" + }, + "storage_bucket_name": { + "value": "sereact-storage-bucket", + "type": "string" + } + }, + "resources": [ + { + "mode": "managed", + "type": "google_cloud_run_service", + "name": "sereact", + "provider": "provider[\"registry.terraform.io/hashicorp/google\"]", + "instances": [ + { + "schema_version": 2, + "attributes": { + "autogenerate_revision_name": false, + "id": "locations/us-central1/namespaces/gen-lang-client-0424120530/services/sereact", + "location": "us-central1", + "metadata": [ + { + "annotations": {}, + "effective_annotations": { + "run.googleapis.com/ingress": "all", + "run.googleapis.com/ingress-status": "all", + "run.googleapis.com/operation-id": "0982194f-b3e8-45b8-a33f-7ed5fd529307", + "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/lastModifier": "johnpccd3@gmail.com" + }, + "effective_labels": { + "cloud.googleapis.com/location": "us-central1" + }, + "generation": 1, + "labels": {}, + "namespace": "gen-lang-client-0424120530", + "resource_version": "AAY108GXDwM", + "self_link": "/apis/serving.knative.dev/v1/namespaces/761163285547/services/sereact", + "terraform_labels": {}, + "uid": "5b695749-5095-4fb5-86bd-4d86f77dc7da" + } + ], + "name": "sereact", + "project": "gen-lang-client-0424120530", + "status": [ + { + "conditions": [ + { + "message": "", + "reason": "", + "status": "True", + "type": "Ready" + }, + { + "message": "", + "reason": "", + "status": "True", + "type": "ConfigurationsReady" + }, + { + "message": "", + "reason": "", + "status": "True", + "type": "RoutesReady" + } + ], + "latest_created_revision_name": "sereact-00001-bt2", + "latest_ready_revision_name": "sereact-00001-bt2", + "observed_generation": 1, + "traffic": [ + { + "latest_revision": true, + "percent": 100, + "revision_name": "sereact-00001-bt2", + "tag": "", + "url": "" + } + ], + "url": "https://sereact-p64zpdtkta-uc.a.run.app" + } + ], + "template": [ + { + "metadata": [ + { + "annotations": { + "autoscaling.knative.dev/maxScale": "3" + }, + "generation": 0, + "labels": { + "run.googleapis.com/startupProbeType": "Default" + }, + "name": "", + "namespace": "", + "resource_version": "", + "self_link": "", + "uid": "" + } + ], + "spec": [ + { + "container_concurrency": 80, + "containers": [ + { + "args": null, + "command": null, + "env": [ + { + "name": "DATABASE_NAME", + "value": "imagedb", + "value_from": [] + }, + { + "name": "GCS_BUCKET_NAME", + "value": "sereact-storage-bucket", + "value_from": [] + }, + { + "name": "LOG_LEVEL", + "value": "INFO", + "value_from": [] + } + ], + "env_from": [], + "image": "gcr.io/google-samples/hello-app:1.0", + "liveness_probe": [], + "name": "", + "ports": [ + { + "container_port": 8080, + "name": "http1", + "protocol": "" + } + ], + "resources": [ + { + "limits": { + "cpu": "1", + "memory": "512Mi" + }, + "requests": null + } + ], + "startup_probe": [ + { + "failure_threshold": 1, + "grpc": [], + "http_get": [], + "initial_delay_seconds": 0, + "period_seconds": 240, + "tcp_socket": [ + { + "port": 8080 + } + ], + "timeout_seconds": 240 + } + ], + "volume_mounts": [], + "working_dir": "" + } + ], + "node_selector": null, + "service_account_name": "761163285547-compute@developer.gserviceaccount.com", + "serving_state": "", + "timeout_seconds": 300, + "volumes": [] + } + ] + } + ], + "timeouts": null, + "traffic": [ + { + "latest_revision": true, + "percent": 100, + "revision_name": "", + "tag": "", + "url": "" + } + ] + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInVwZGF0ZSI6MTIwMDAwMDAwMDAwMH0sInNjaGVtYV92ZXJzaW9uIjoiMiJ9", + "dependencies": [ + "google_project_service.services" + ] + } + ] + }, + { + "mode": "managed", + "type": "google_cloud_run_service_iam_member", + "name": "public_access", + "provider": "provider[\"registry.terraform.io/hashicorp/google\"]", + "instances": [ + { + "schema_version": 0, + "attributes": { + "condition": [], + "etag": "BwY108GyUf0=", + "id": "v1/projects/gen-lang-client-0424120530/locations/us-central1/services/sereact/roles/run.invoker/allUsers", + "location": "us-central1", + "member": "allUsers", + "project": "gen-lang-client-0424120530", + "role": "roles/run.invoker", + "service": "v1/projects/gen-lang-client-0424120530/locations/us-central1/services/sereact" + }, + "sensitive_attributes": [], + "private": "bnVsbA==", + "dependencies": [ + "google_cloud_run_service.sereact", + "google_project_service.services" + ] + } + ] + }, + { + "mode": "managed", + "type": "google_firestore_database", + "name": "database", + "provider": "provider[\"registry.terraform.io/hashicorp/google\"]", + "instances": [ + { + "schema_version": 0, + "attributes": { + "app_engine_integration_mode": "DISABLED", + "cmek_config": [], + "concurrency_mode": "PESSIMISTIC", + "create_time": "", + "database_edition": "STANDARD", + "delete_protection_state": "DELETE_PROTECTION_DISABLED", + "deletion_policy": "ABANDON", + "earliest_version_time": "2025-05-23T20:47:31.801717Z", + "etag": "IIelp4e8uo0DMPX0nai7uo0D", + "id": "projects/gen-lang-client-0424120530/databases/imagedb", + "key_prefix": "", + "location_id": "us-central1", + "name": "imagedb", + "point_in_time_recovery_enablement": "POINT_IN_TIME_RECOVERY_DISABLED", + "project": "gen-lang-client-0424120530", + "timeouts": null, + "type": "FIRESTORE_NATIVE", + "uid": "177e30f2-9b67-428c-9979-22e625b929c4", + "update_time": "", + "version_retention_period": "3600s" + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInVwZGF0ZSI6MTIwMDAwMDAwMDAwMH19", + "dependencies": [ + "google_project_service.services" + ] + } + ] + }, + { + "mode": "managed", + "type": "google_project_service", + "name": "services", + "provider": "provider[\"registry.terraform.io/hashicorp/google\"]", + "instances": [ + { + "index_key": "cloudresourcemanager.googleapis.com", + "schema_version": 0, + "attributes": { + "disable_dependent_services": null, + "disable_on_destroy": false, + "id": "gen-lang-client-0424120530/cloudresourcemanager.googleapis.com", + "project": "gen-lang-client-0424120530", + "service": "cloudresourcemanager.googleapis.com", + "timeouts": null + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" + }, + { + "index_key": "containerregistry.googleapis.com", + "schema_version": 0, + "attributes": { + "disable_dependent_services": null, + "disable_on_destroy": false, + "id": "gen-lang-client-0424120530/containerregistry.googleapis.com", + "project": "gen-lang-client-0424120530", + "service": "containerregistry.googleapis.com", + "timeouts": null + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" + }, + { + "index_key": "firestore.googleapis.com", + "schema_version": 0, + "attributes": { + "disable_dependent_services": null, + "disable_on_destroy": false, + "id": "gen-lang-client-0424120530/firestore.googleapis.com", + "project": "gen-lang-client-0424120530", + "service": "firestore.googleapis.com", + "timeouts": null + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" + }, + { + "index_key": "run.googleapis.com", + "schema_version": 0, + "attributes": { + "disable_dependent_services": null, + "disable_on_destroy": false, + "id": "gen-lang-client-0424120530/run.googleapis.com", + "project": "gen-lang-client-0424120530", + "service": "run.googleapis.com", + "timeouts": null + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" + }, + { + "index_key": "storage.googleapis.com", + "schema_version": 0, + "attributes": { + "disable_dependent_services": null, + "disable_on_destroy": false, + "id": "gen-lang-client-0424120530/storage.googleapis.com", + "project": "gen-lang-client-0424120530", + "service": "storage.googleapis.com", + "timeouts": null + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjoxMjAwMDAwMDAwMDAwLCJkZWxldGUiOjEyMDAwMDAwMDAwMDAsInJlYWQiOjYwMDAwMDAwMDAwMCwidXBkYXRlIjoxMjAwMDAwMDAwMDAwfX0=" + } + ] + }, + { + "mode": "managed", + "type": "google_storage_bucket", + "name": "app_bucket", + "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": "sereact-storage-bucket", + "labels": {}, + "lifecycle_rule": [], + "location": "US-CENTRAL1", + "logging": [], + "name": "sereact-storage-bucket", + "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/sereact-storage-bucket", + "soft_delete_policy": [ + { + "effective_time": "2025-05-23T20:47:26.788Z", + "retention_duration_seconds": 604800 + } + ], + "storage_class": "STANDARD", + "terraform_labels": { + "goog-terraform-provisioned": "true" + }, + "time_created": "2025-05-23T20:47:26.788Z", + "timeouts": null, + "uniform_bucket_level_access": true, + "updated": "2025-05-23T20:47:26.788Z", + "url": "gs://sereact-storage-bucket", + "versioning": [], + "website": [] + }, + "sensitive_attributes": [], + "private": "eyJlMmJmYjczMC1lY2FhLTExZTYtOGY4OC0zNDM2M2JjN2M0YzAiOnsiY3JlYXRlIjo2MDAwMDAwMDAwMDAsInJlYWQiOjI0MDAwMDAwMDAwMCwidXBkYXRlIjoyNDAwMDAwMDAwMDB9LCJzY2hlbWFfdmVyc2lvbiI6IjMifQ==", + "dependencies": [ + "google_project_service.services" + ] + } + ] + } + ], + "check_results": null +} diff --git a/deployment/terraform/terraform.tfvars.example b/deployment/terraform/terraform.tfvars.example new file mode 100644 index 0000000..dfbd2d1 --- /dev/null +++ b/deployment/terraform/terraform.tfvars.example @@ -0,0 +1,5 @@ +project_id = "your-gcp-project-id" +region = "us-central1" +zone = "us-central1-a" +storage_bucket_name = "your-app-storage-bucket" +firestore_db_name = "imagedb" \ No newline at end of file diff --git a/deployment/terraform/variables.tf b/deployment/terraform/variables.tf new file mode 100644 index 0000000..0e23fb9 --- /dev/null +++ b/deployment/terraform/variables.tf @@ -0,0 +1,27 @@ +variable "project_id" { + description = "The Google Cloud project ID" + type = string +} + +variable "region" { + description = "The Google Cloud region" + type = string + default = "us-central1" +} + +variable "zone" { + description = "The Google Cloud zone" + type = string + default = "us-central1-a" +} + +variable "storage_bucket_name" { + description = "The name of the Cloud Storage bucket" + type = string +} + +variable "firestore_db_name" { + description = "The name of the Firestore database" + type = string + default = "imagedb" +} \ No newline at end of file