diff --git a/examples/basic/main.tf b/examples/basic/main.tf index 9c068289..70fadd72 100644 --- a/examples/basic/main.tf +++ b/examples/basic/main.tf @@ -31,16 +31,18 @@ resource "time_sleep" "wait" { create_duration = "15s" } -resource "elasticsearch_index" "test" { - depends_on = [time_sleep.wait] - name = "terraform-test" - number_of_shards = 1 - number_of_replicas = 1 - force_destroy = true -} +# Commenting below code to this issue https://github.com/terraform-ibm-modules/terraform-ibm-icd-elasticsearch/issues/317 -resource "elasticsearch_cluster_settings" "global" { - depends_on = [time_sleep.wait] - cluster_max_shards_per_node = 10 - action_auto_create_index = "my-index-000001,index10,-index1*,+ind*" -} +# resource "elasticsearch_index" "test" { +# depends_on = [time_sleep.wait] +# name = "terraform-test" +# number_of_shards = 1 +# number_of_replicas = 1 +# force_destroy = true +# } + +# resource "elasticsearch_cluster_settings" "global" { +# depends_on = [time_sleep.wait] +# cluster_max_shards_per_node = 10 +# action_auto_create_index = "my-index-000001,index10,-index1*,+ind*" +# } diff --git a/solutions/standard/README.md b/solutions/standard/README.md index 6394c7fb..a40a9b5b 100644 --- a/solutions/standard/README.md +++ b/solutions/standard/README.md @@ -6,6 +6,7 @@ This architecture creates an instance of IBM Cloud Databases for Elasticsearch a - A KMS root key, if one is not passed in. - An IBM Cloud Databases for Elasticsearch instance with KMS encryption. - Autoscaling rules for the database instance, if provided. +- Kibana dashboard for Elasticsearch. ![fscloud-elastic-search](../../reference-architecture/deployable-architecture-elasticsearch.svg) diff --git a/solutions/standard/main.tf b/solutions/standard/main.tf index 37e93c35..4a254144 100644 --- a/solutions/standard/main.tf +++ b/solutions/standard/main.tf @@ -232,3 +232,87 @@ data "ibm_database_connection" "existing_connection" { user_id = data.ibm_database.existing_db_instance[0].adminuser user_type = "database" } + +######################################################################################################################## +# Code Engine Kibana Dashboard instance +######################################################################################################################## + +locals { + + code_engine_project_id = var.existing_code_engine_project_id != null ? var.existing_code_engine_project_id : null + code_engine_project_name = local.code_engine_project_id != null ? null : var.prefix != null ? "${var.prefix}-code-engine-kibana-project" : "ce-kibana-project" + code_engine_app_name = var.prefix != null ? "${var.prefix}-kibana-app" : "ce-kibana-app" + + es_host = local.use_existing_db_instance ? data.ibm_database_connection.existing_connection[0].https[0].hosts[0].hostname : module.elasticsearch[0].hostname + es_port = local.use_existing_db_instance ? data.ibm_database_connection.existing_connection[0].https[0].hosts[0].port : module.elasticsearch[0].port + es_cert = local.use_existing_db_instance ? data.ibm_database_connection.existing_connection[0].https[0].certificate[0].certificate_base64 : module.elasticsearch[0].certificate_base64 + es_username = local.use_existing_db_instance ? data.ibm_database.existing_db_instance[0].adminuser : "admin" + es_password = local.admin_pass + es_data = var.enable_kibana_dashboard ? jsondecode(data.http.es_metadata[0].response_body) : null + es_full_version = var.enable_kibana_dashboard ? (var.elasticsearch_full_version != null ? var.elasticsearch_full_version : local.es_data.version.number) : null + +} + +data "http" "es_metadata" { + count = var.enable_kibana_dashboard ? 1 : 0 + url = "https://${local.es_username}:${local.es_password}@${local.es_host}:${local.es_port}" + ca_cert_pem = base64decode(local.es_cert) +} + +module "code_engine_kibana" { + count = var.enable_kibana_dashboard ? 1 : 0 + source = "terraform-ibm-modules/code-engine/ibm" + version = "2.0.4" + resource_group_id = module.resource_group.resource_group_id + project_name = local.code_engine_project_name + existing_project_id = local.code_engine_project_id + secrets = { + "es-secret" = { + format = "generic" + data = { + "ELASTICSEARCH_PASSWORD" = local.es_password + } + } + } + + apps = { + (local.code_engine_app_name) = { + image_reference = "docker.elastic.co/kibana/kibana:${local.es_full_version}" + image_port = 5601 + run_env_variables = [{ + type = "literal" + name = "ELASTICSEARCH_HOSTS" + value = "[\"https://${local.es_host}:${local.es_port}\"]" + }, + { + type = "literal" + name = "ELASTICSEARCH_USERNAME" + value = local.es_username + }, + { + type = "secret_key_reference" + name = "ELASTICSEARCH_PASSWORD" + key = "ELASTICSEARCH_PASSWORD" + reference = "es-secret" + }, + { + type = "literal" + name = "ELASTICSEARCH_SSL_ENABLED" + value = "true" + }, + { + type = "literal" + name = "SERVER_HOST" + value = "0.0.0.0" + }, + { + type = "literal" + name = "ELASTICSEARCH_SSL_VERIFICATIONMODE" + value = "none" + } + ] + scale_min_instances = 1 + scale_max_instances = 3 + } + } +} diff --git a/solutions/standard/outputs.tf b/solutions/standard/outputs.tf index 807b0e1e..62f1d12a 100644 --- a/solutions/standard/outputs.tf +++ b/solutions/standard/outputs.tf @@ -59,3 +59,8 @@ output "admin_pass" { value = local.admin_pass sensitive = true } + +output "kibana_app_endpoint" { + description = "Code Engine Kibana endpoint URL" + value = var.enable_kibana_dashboard ? module.code_engine_kibana[0].app[local.code_engine_app_name].endpoint : null +} diff --git a/solutions/standard/variables.tf b/solutions/standard/variables.tf index 03d293e5..5bdc24ff 100644 --- a/solutions/standard/variables.tf +++ b/solutions/standard/variables.tf @@ -315,3 +315,25 @@ variable "admin_pass_sm_secret_name" { description = "The name of a new elasticsearch administrator secret. If a prefix input variable is specified, the prefix is added to the name in the `-` format." default = "elasticsearch-admin-password" } + +############################################################## +# Kibana Configuration +############################################################## + +variable "existing_code_engine_project_id" { + description = "Existing code engine project ID to deploy Kibana. If no value is passed, a new code engine project will be created." + type = string + default = null +} + +variable "enable_kibana_dashboard" { + type = bool + description = "Set it true to deploy Kibana in code engine. NOTE: Kibana image is coming direcly from the official registry (https://www.docker.elastic.co/) and not certified by the IBM." + default = false +} + +variable "elasticsearch_full_version" { + description = "(Optional) Full version of the Elasticsearch instance in the format `x.x.x` to deploy Kibana dashboard. If no value is passed, data lookup will fetch the full version using the Elasticsearch API, see https://github.com/elastic/kibana?tab=readme-ov-file#version-compatibility-with-elasticsearch" + type = string + default = null +} diff --git a/solutions/standard/version.tf b/solutions/standard/version.tf index 100dc7e5..9703547d 100644 --- a/solutions/standard/version.tf +++ b/solutions/standard/version.tf @@ -15,5 +15,9 @@ terraform { source = "hashicorp/random" version = "3.6.3" } + http = { + source = "hashicorp/http" + version = "3.4.5" + } } } diff --git a/tests/pr_test.go b/tests/pr_test.go index 3fa5f8bc..63fa38c6 100644 --- a/tests/pr_test.go +++ b/tests/pr_test.go @@ -192,6 +192,7 @@ func TestRunStandardSolutionSchematics(t *testing.T) { {Name: "service_credential_secrets", Value: serviceCredentialSecrets, DataType: "list(object)"}, {Name: "admin_pass_sm_secret_group", Value: options.Prefix, DataType: "string"}, {Name: "admin_pass_sm_secret_name", Value: options.Prefix, DataType: "string"}, + {Name: "enable_kibana_dashboard", Value: true, DataType: "bool"}, } err := options.RunSchematicTest() assert.Nil(t, err, "This should not have errored")