@@ -141,6 +141,12 @@ resource "google_service_account" "optimizer" {
141141 project = var. project_id
142142}
143143
144+ resource "google_service_account" "visualizer" {
145+ account_id = " visualizer"
146+ display_name = " Visualizer Service Account"
147+ project = var. project_id
148+ }
149+
144150# IAM for pubsub
145151
146152# to pub orders/telemetry topics
@@ -185,6 +191,16 @@ resource "google_pubsub_topic_iam_member" "optimizer_publisher" {
185191 depends_on = [module . decisions_topic ]
186192}
187193
194+ # visualizer needs to subscribe to telemetry-sub
195+ resource "google_pubsub_subscription_iam_member" "visualizer_subscriber" {
196+ project = var. project_id
197+ subscription = " telemetry-sub"
198+ role = " roles/pubsub.subscriber"
199+ member = " serviceAccount:${ google_service_account . visualizer . email } "
200+
201+ depends_on = [module . telemetry_topic ]
202+ }
203+
188204# pubsub SA need to be set as pub on DLQ to pub failed ones
189205resource "google_pubsub_topic_iam_member" "pubsub_dlq_publisher" {
190206 project = var. project_id
@@ -289,7 +305,202 @@ resource "google_project_iam_member" "seed_firestore_datastore" {
289305 member = " serviceAccount:${ google_service_account . seed_firestore . email } "
290306}
291307
292- # cloud Run Job: simulator
308+ # Cloud Run Service: ingestion API
309+ resource "google_cloud_run_v2_service" "ingestion" {
310+ name = " ingestion"
311+ location = var. region
312+ project = var. project_id
313+ labels = local. common_labels
314+
315+ template {
316+ service_account = google_service_account. ingestion_api . email
317+
318+ scaling {
319+ min_instance_count = 0
320+ max_instance_count = 2
321+ }
322+
323+ containers {
324+ image = " ${ local . image_base } /ingestion:latest"
325+
326+ env {
327+ name = " ENVIRONMENT"
328+ value = var. environment
329+ }
330+ env {
331+ name = " PROJECT_ID"
332+ value = var. project_id
333+ }
334+
335+ resources {
336+ limits = {
337+ cpu = " 1"
338+ memory = " 512Mi"
339+ }
340+ }
341+ }
342+ }
343+
344+ depends_on = [google_project_service . cloud_run ]
345+
346+ lifecycle {
347+ ignore_changes = [
348+ template [0 ]. containers [0 ]. image ,
349+ template [0 ]. containers [0 ]. env ,
350+ ]
351+ }
352+ }
353+
354+ # Cloud Run Service: state-manager
355+ resource "google_cloud_run_v2_service" "state_manager" {
356+ name = " state-manager"
357+ location = var. region
358+ project = var. project_id
359+ labels = local. common_labels
360+
361+ template {
362+ service_account = google_service_account. state_manager . email
363+
364+ scaling {
365+ min_instance_count = 1
366+ max_instance_count = 3
367+ }
368+
369+ containers {
370+ image = " ${ local . image_base } /state-manager:latest"
371+
372+ env {
373+ name = " ENVIRONMENT"
374+ value = var. environment
375+ }
376+ env {
377+ name = " PROJECT_ID"
378+ value = var. project_id
379+ }
380+ env {
381+ name = " SPRING_PROFILES_ACTIVE"
382+ value = var. environment
383+ }
384+
385+ resources {
386+ limits = {
387+ cpu = " 2"
388+ memory = " 1Gi"
389+ }
390+ }
391+ }
392+ }
393+
394+ depends_on = [google_project_service . cloud_run ]
395+
396+ lifecycle {
397+ ignore_changes = [
398+ template [0 ]. containers [0 ]. image ,
399+ template [0 ]. containers [0 ]. env ,
400+ ]
401+ }
402+ }
403+
404+ # Cloud Run Service: visualizer
405+ resource "google_cloud_run_v2_service" "visualizer" {
406+ name = " visualizer"
407+ location = var. region
408+ project = var. project_id
409+ labels = local. common_labels
410+
411+ template {
412+ service_account = google_service_account. visualizer . email
413+
414+ scaling {
415+ min_instance_count = 0
416+ max_instance_count = 2
417+ }
418+
419+ containers {
420+ image = " ${ local . image_base } /visualizer:latest"
421+
422+ env {
423+ name = " PROJECT_ID"
424+ value = var. project_id
425+ }
426+ env {
427+ name = " NODE_ENV"
428+ value = " production"
429+ }
430+ env {
431+ name = " PUBSUB_SUBSCRIPTION"
432+ value = " telemetry-sub"
433+ }
434+
435+ resources {
436+ limits = {
437+ cpu = " 1"
438+ memory = " 512Mi"
439+ }
440+ }
441+ }
442+ }
443+
444+ depends_on = [google_project_service . cloud_run ]
445+
446+ lifecycle {
447+ ignore_changes = [
448+ template [0 ]. containers [0 ]. image ,
449+ template [0 ]. containers [0 ]. env ,
450+ ]
451+ }
452+ }
453+
454+ # Cloud Run Job: path-optimizer
455+ resource "google_cloud_run_v2_job" "path_optimizer" {
456+ name = " path-optimizer"
457+ location = var. region
458+ project = var. project_id
459+ labels = local. common_labels
460+
461+ template {
462+ template {
463+ service_account = google_service_account. optimizer . email
464+ timeout = " 300s"
465+ max_retries = 1
466+
467+ containers {
468+ image = " ${ local . image_base } /path-optimizer:latest"
469+
470+ env {
471+ name = " ENVIRONMENT"
472+ value = var. environment
473+ }
474+ env {
475+ name = " PROJECT_ID"
476+ value = var. project_id
477+ }
478+ env {
479+ name = " STATE_MANAGER_URL"
480+ value = google_cloud_run_v2_service. state_manager . uri
481+ }
482+
483+ resources {
484+ limits = {
485+ cpu = " 2"
486+ memory = " 2Gi"
487+ }
488+ }
489+ }
490+ }
491+ }
492+
493+ depends_on = [google_project_service . cloud_run ]
494+
495+ lifecycle {
496+ ignore_changes = [
497+ template [0 ]. template [0 ]. containers [0 ]. image ,
498+ template [0 ]. template [0 ]. containers [0 ]. env ,
499+ ]
500+ }
501+ }
502+
503+ # Cloud Run Job: simulator
293504resource "google_cloud_run_v2_job" "simulator" {
294505 name = " simulator"
295506 location = var. region
@@ -315,7 +526,7 @@ resource "google_cloud_run_v2_job" "simulator" {
315526 }
316527 env {
317528 name = " INGESTION_API_URL"
318- value = " https:// ingestion-placeholder.run.app "
529+ value = google_cloud_run_v2_service . ingestion . uri
319530 }
320531
321532 resources {
0 commit comments