From 96afa1f2cd2c7b900cd85093df3b4d65c54d4d35 Mon Sep 17 00:00:00 2001
From: Xiaxin <92154856+xiaxyi@users.noreply.github.com>
Date: Wed, 16 Nov 2022 14:54:13 +0800
Subject: [PATCH] Add example for azure function app using key vault reference
 (#114)
add examples for function app using key vault reference
---
 .../.terraform-docs.yml                       |  11 ++
 .../.tflint.hcl                               |  71 +++++++++++
 .../201-function-app-key-vault-ref/main.tf    | 112 ++++++++++++++++++
 .../providers.tf                              |  18 +++
 .../readme.html.markdown                      |  46 +++++++
 .../variables.tf                              |  10 ++
 6 files changed, 268 insertions(+)
 create mode 100644 quickstart/201-function-app-key-vault-ref/.terraform-docs.yml
 create mode 100644 quickstart/201-function-app-key-vault-ref/.tflint.hcl
 create mode 100644 quickstart/201-function-app-key-vault-ref/main.tf
 create mode 100644 quickstart/201-function-app-key-vault-ref/providers.tf
 create mode 100644 quickstart/201-function-app-key-vault-ref/readme.html.markdown
 create mode 100644 quickstart/201-function-app-key-vault-ref/variables.tf
diff --git a/quickstart/201-function-app-key-vault-ref/.terraform-docs.yml b/quickstart/201-function-app-key-vault-ref/.terraform-docs.yml
new file mode 100644
index 00000000..45efe475
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/.terraform-docs.yml
@@ -0,0 +1,11 @@
+formatter: "markdown table"
+
+content: |-
+  {{ .Resources }}
+  {{ .Inputs }}
+  {{ .Providers }}
+  {{ .Requirements }}
+
+output:
+  file: readme.html.markdown
+  mode: inject
\ No newline at end of file
diff --git a/quickstart/201-function-app-key-vault-ref/.tflint.hcl b/quickstart/201-function-app-key-vault-ref/.tflint.hcl
new file mode 100644
index 00000000..3e2ee6d6
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/.tflint.hcl
@@ -0,0 +1,71 @@
+/*
+THIS FILE IS GENERATED BY TFMOD-SCAFFOLD, PLEASE DO NOT MODIFY IT.
+IF YOU WANT TO USE A CUSTOMIZED CONFIGURATION, PLEASE CREATE YOUR OWN AND
+SET THIS FILE'S PATH TO $TFLINT_CONFIG ENVVIRONMENT VARIABLE.
+*/
+
+plugin "azurerm" {
+  enabled = true
+  version = "0.18.0"
+  source  = "github.com/terraform-linters/tflint-ruleset-azurerm"
+}
+
+rule "terraform_comment_syntax" {
+  enabled = true
+}
+
+rule "terraform_deprecated_index" {
+  enabled = true
+}
+
+rule "terraform_deprecated_interpolation" {
+  enabled = true
+}
+
+rule "terraform_documented_outputs" {
+  enabled = true
+}
+
+rule "terraform_documented_variables" {
+  enabled = true
+}
+
+rule "terraform_module_pinned_source" {
+  enabled = true
+}
+
+rule "terraform_module_version" {
+  enabled = true
+}
+
+rule "terraform_naming_convention" {
+  enabled = true
+}
+
+rule "terraform_required_providers" {
+  enabled = true
+}
+
+rule "terraform_required_version" {
+  enabled = true
+}
+
+rule "terraform_standard_module_structure" {
+  enabled = false
+}
+
+rule "terraform_typed_variables" {
+  enabled = true
+}
+
+rule "terraform_unused_declarations" {
+  enabled = true
+}
+
+rule "terraform_unused_required_providers" {
+  enabled = true
+}
+
+rule "terraform_workspace_remote" {
+  enabled = true
+}
\ No newline at end of file
diff --git a/quickstart/201-function-app-key-vault-ref/main.tf b/quickstart/201-function-app-key-vault-ref/main.tf
new file mode 100644
index 00000000..b2d13e93
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/main.tf
@@ -0,0 +1,112 @@
+data "azurerm_client_config" "current" {}
+
+resource "azurerm_resource_group" "default" {
+  name     = "${var.name_prefix}-rg"
+  location = var.location
+}
+
+resource "azurerm_user_assigned_identity" "default" {
+  name                = "${var.name_prefix}-uai"
+  resource_group_name = azurerm_resource_group.default.name
+  location            = azurerm_resource_group.default.location
+}
+
+resource "azurerm_storage_account" "default" {
+  name                     = "${var.name_prefix}sa"
+  resource_group_name      = azurerm_resource_group.default.name
+  location                 = azurerm_resource_group.default.location
+  account_tier             = "Standard"
+  account_replication_type = "LRS"
+}
+
+resource "azurerm_service_plan" "default" {
+  name                = "${var.name_prefix}-sp"
+  location            = azurerm_resource_group.default.location
+  resource_group_name = azurerm_resource_group.default.name
+  os_type             = "Windows"
+  sku_name            = "Y1"
+}
+
+
+resource "azurerm_key_vault" "default" {
+  name                       = "${var.name_prefix}-kv"
+  location                   = azurerm_resource_group.default.location
+  resource_group_name        = azurerm_resource_group.default.name
+  tenant_id                  = data.azurerm_client_config.current.tenant_id
+  sku_name                   = "standard"
+  soft_delete_retention_days = 7
+
+  access_policy {
+    tenant_id = data.azurerm_client_config.current.tenant_id
+    object_id = data.azurerm_client_config.current.object_id
+
+    key_permissions = [
+      "Get",
+    ]
+
+    secret_permissions = [
+      "Get",
+      "Delete",
+      "List",
+      "Purge",
+      "Recover",
+      "Set",
+    ]
+  }
+
+  access_policy {
+    tenant_id = data.azurerm_client_config.current.tenant_id
+    object_id = azurerm_user_assigned_identity.default.principal_id
+
+    secret_permissions = [
+      "Get",
+      "List",
+    ]
+  }
+
+  tags = {
+    environment = "tfTest"
+  }
+}
+
+resource "azurerm_key_vault_secret" "default" {
+  name         = "${var.name_prefix}-kvs"
+  value        = azurerm_storage_account.default.primary_connection_string
+  key_vault_id = azurerm_key_vault.default.id
+}
+
+/* when using key vault reference in functions app, please follow below instructions:
+1. when using event-driven scaling plans such as consumption and premium plan, WEBSITE_CONTENTSHARE key should be set in app_setting block. You don't need to explicitly specify it as Azure will generate a unique file share for you, unless:
+   1) You are using a secure storage account in a virtual network. In this case, you must set the WEBSITE_CONTENTSHARE value to a predefined share and set a unique share name for the main function app and the app for each deployment slot.
+   2) You can using key vault reference for setting WEBSITE_CONTENTAZUREFILECONNECTIONSTRING. This setting has additional validation check to ensure that the app can be properly started, check will fail as the secret itself cannot be resolved while processing the incoming request.
+   3) Please don't make WEBSITE_CONTENTSHARE a slot setting.
+To avoid the failure of the azure file check mentioned above, you can skip the validation by setting WEBSITE_SKIP_CONTENTSHARE_VALIDATION to "1". This will bypass all checks, and the content share will not be created for you. You should ensure it is created in advance.
+
+2. please make sure to set storage_key_vault_secret_id property to configure the app to use this identity for Key Vault reference operations.
+ */
+resource "azurerm_windows_function_app" "default" {
+  name                = "${var.name_prefix}-wfa"
+  resource_group_name = azurerm_resource_group.default.name
+  location            = azurerm_resource_group.default.location
+
+  service_plan_id = azurerm_service_plan.default.id
+
+  storage_key_vault_secret_id = azurerm_key_vault_secret.default.id
+
+  key_vault_reference_identity_id = azurerm_user_assigned_identity.default.id
+
+  app_settings = {
+    WEBSITE_SKIP_CONTENTSHARE_VALIDATION = 1
+  }
+
+  identity {
+    type         = "UserAssigned"
+    identity_ids = [azurerm_user_assigned_identity.default.id]
+  }
+
+  site_config {
+    application_stack {
+      node_version = "~14"
+    }
+  }
+}
\ No newline at end of file
diff --git a/quickstart/201-function-app-key-vault-ref/providers.tf b/quickstart/201-function-app-key-vault-ref/providers.tf
new file mode 100644
index 00000000..6e028d57
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/providers.tf
@@ -0,0 +1,18 @@
+terraform {
+  required_version = ">=1.0"
+
+  required_providers {
+    azurerm = {
+      source  = "hashicorp/azurerm"
+      version = "~>3.8"
+    }
+  }
+}
+provider "azurerm" {
+  features {
+    key_vault {
+      purge_soft_delete_on_destroy    = true
+      recover_soft_deleted_key_vaults = true
+    }
+  }
+}
\ No newline at end of file
diff --git a/quickstart/201-function-app-key-vault-ref/readme.html.markdown b/quickstart/201-function-app-key-vault-ref/readme.html.markdown
new file mode 100644
index 00000000..72b9e259
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/readme.html.markdown
@@ -0,0 +1,46 @@
+# Azure Windows/ Linux Function App using key vault reference
+
+This template deploys an Azure Function App running using key vault reference
+
+
+
+
+
+
+
+
+
+
+## Resources
+
+| Name                                                                                                                                             | Type        |
+|--------------------------------------------------------------------------------------------------------------------------------------------------|-------------|
+| [azurerm_key_vault.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/key_vault)                           | resource    |
+| [azurerm_key_vault_secret.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/key_vault_secret)             | resource    |
+| [azurerm_resource_group.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/resource_group)                 | resource    |
+| [azurerm_service_plan.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/service_plan)                     | resource    |
+| [azurerm_storage_account.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/storage_account)               | resource    |
+| [azurerm_user_assigned_identity.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/user_assigned_identity) | resource    |
+| [azurerm_windows_function_app.default](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/resources/windows_function_app)     | resource    |
+| [azurerm_client_config.current](https://registry.terraform.io/providers/hashicorp/azurerm/latest/docs/data-sources/client_config)                | data source |
+## Inputs
+
+| Name                                                                  | Description                           | Type     | Default       | Required |
+|-----------------------------------------------------------------------|---------------------------------------|----------|---------------|:--------:|
+|  [location](#input\_location)            | Location to deploy the resource group | `string` | `"West US 2"` |    no    |
+|  [name\_prefix](#input\_name\_prefix) | Prefix of the resource name           | `string` | n/a           |   yes    |
+## Providers
+
+| Name                                                          | Version |
+|---------------------------------------------------------------|---------|
+|  [azurerm](#provider\_azurerm) | ~>3.8   |
+## Requirements
+
+| Name                                                                      | Version |
+|---------------------------------------------------------------------------|---------|
+|  [terraform](#requirement\_terraform) | >=1.0   |
+|  [azurerm](#requirement\_azurerm)       | ~>3.8   |
+
+## Example
+
+To see how to run this example, see [Create an Azure Function App using Terraform](https://docs.microsoft.com/azure/developer/terraform/create-azure-windows-linux-function-app-using-key-vault-reference).
diff --git a/quickstart/201-function-app-key-vault-ref/variables.tf b/quickstart/201-function-app-key-vault-ref/variables.tf
new file mode 100644
index 00000000..e4c01012
--- /dev/null
+++ b/quickstart/201-function-app-key-vault-ref/variables.tf
@@ -0,0 +1,10 @@
+variable "name_prefix" {
+  type        = string
+  description = "Prefix of the resource name"
+}
+
+variable "location" {
+  type        = string
+  description = "Location to deploy the resource group"
+  default     = "West US 2"
+}