-
Notifications
You must be signed in to change notification settings - Fork 18
/
sshizzle.tf
179 lines (156 loc) · 6.53 KB
/
sshizzle.tf
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
locals {
// Generate name in advance to avoid cyclic dependency
keyvault_name = "${var.prefix}-kv-sshizzle"
}
// Create a resource group
resource "azurerm_resource_group" "rg-sshizzle" {
name = "rg-sshizzle"
location = var.location
}
// Create the Key Vault
resource "azurerm_key_vault" "kv-sshizzle" {
name = local.keyvault_name
location = azurerm_resource_group.rg-sshizzle.location
resource_group_name = azurerm_resource_group.rg-sshizzle.name
tenant_id = data.azurerm_client_config.current.tenant_id
sku_name = "standard"
soft_delete_enabled = false
purge_protection_enabled = false
// Allow network access to possible Azure Functions IP space and Terraform client IP
network_acls {
default_action = "Deny"
bypass = "AzureServices"
ip_rules = concat(
[chomp(data.http.client_ip.body)],
split(",", azurerm_function_app.func-sshizzle.possible_outbound_ip_addresses),
)
}
// Allow the Function App MSI access to fetch and sign with keys
access_policy {
tenant_id = data.azurerm_client_config.current.tenant_id
object_id = azurerm_function_app.func-sshizzle.identity[0].principal_id
key_permissions = ["get", "sign"]
}
// Catch all permissions for the current user (assuming Azure CLI auth, this should be you!)
// Used for testing - probably shouldn't do this in production
access_policy {
tenant_id = data.azurerm_client_config.current.tenant_id
object_id = data.azurerm_client_config.current.object_id
key_permissions = ["get", "list", "update", "create", "import", "delete", "recover", "backup", "restore"]
}
}
// Create the CA key - an Azure generated RSA key
resource "azurerm_key_vault_key" "key-sshizzle" {
name = "sshizzle"
key_vault_id = azurerm_key_vault.kv-sshizzle.id
key_type = "RSA"
key_size = "${var.ca_key_size}"
key_opts = ["sign", "verify"]
}
// Create a storage account to back the App Service Plan
resource "azurerm_storage_account" "sasshizzle" {
name = "${var.prefix}sasshizzle"
resource_group_name = azurerm_resource_group.rg-sshizzle.name
location = azurerm_resource_group.rg-sshizzle.location
account_tier = "Standard"
account_replication_type = "LRS"
}
// Create an App Service plan to enable billing for the Azure Function
resource "azurerm_app_service_plan" "plan-sshizzle" {
name = "plan-sshizzle"
location = azurerm_resource_group.rg-sshizzle.location
resource_group_name = azurerm_resource_group.rg-sshizzle.name
kind = "FunctionApp"
sku {
tier = "Dynamic"
size = "Y1"
}
}
// Generate a random identifier for the Azure Function to avoid collisions
resource "random_id" "function-id" {
byte_length = 4
}
// Create an app registration for the agent
resource "azuread_application" "app-sshizzle-agent" {
name = "app-sshizzle-agent"
available_to_other_tenants = false
type = "native"
owners = [data.azurerm_client_config.current.object_id]
reply_urls = ["http://localhost:8080/callback"]
// Give application access to the Graph API and allow users to Sign In
required_resource_access {
resource_app_id = "00000003-0000-0000-c000-000000000000"
resource_access {
id = "e1fe6dd8-ba31-4d61-89e7-88639da4683d"
type = "Scope"
}
}
}
// Create an app registration for the CA
resource "azuread_application" "app-sshizzle-ca" {
name = "app-sshizzle-ca"
owners = [data.azurerm_client_config.current.object_id]
homepage = "https://func-sshizzle-${lower(random_id.function-id.b64_url)}.azurewebsites.net"
identifier_uris = ["https://func-sshizzle-${lower(random_id.function-id.b64_url)}.azurewebsites.net"]
reply_urls = ["https://func-sshizzle-${lower(random_id.function-id.b64_url)}.azurewebsites.net/.auth/login/aad/callback"]
type = "webapp/api"
available_to_other_tenants = false
required_resource_access {
resource_app_id = "00000002-0000-0000-c000-000000000000"
resource_access {
id = "311a71cc-e848-46a1-bdf8-97ff7156d8e6"
type = "Scope"
}
}
}
// Generate a random password for the CA service principal
resource "random_password" "ca-password" {
length = 32
special = true
override_special = "_%@"
}
// Create the application password
resource "azuread_application_password" "apppw-sshizzle-ca" {
application_object_id = azuread_application.app-sshizzle-ca.id
value = random_password.ca-password.result
end_date_relative = "8760h"
}
// Create a service principal for the CA
resource "azuread_service_principal" "sp-sshizzle-ca" {
application_id = azuread_application.app-sshizzle-ca.application_id
app_role_assignment_required = false
// This Tag is needed to make it an "Enterprise Application"
tags = ["WindowsAzureActiveDirectoryIntegratedApp"]
}
// Create the Azure Function
resource "azurerm_function_app" "func-sshizzle" {
name = "func-sshizzle-${lower(random_id.function-id.b64_url)}"
location = azurerm_resource_group.rg-sshizzle.location
resource_group_name = azurerm_resource_group.rg-sshizzle.name
app_service_plan_id = azurerm_app_service_plan.plan-sshizzle.id
storage_account_name = azurerm_storage_account.sasshizzle.name
storage_account_access_key = azurerm_storage_account.sasshizzle.primary_access_key
version = "~3"
https_only = true
client_affinity_enabled = true
enable_builtin_logging = true
// Force users to sign in with Azure AD before they can invoke the function
auth_settings {
enabled = true
default_provider = "AzureActiveDirectory"
issuer = "https://sts.windows.net/${data.azurerm_client_config.current.tenant_id}/"
token_store_enabled = true
unauthenticated_client_action = "RedirectToLoginPage"
active_directory {
client_id = azuread_application.app-sshizzle-ca.application_id
client_secret = azuread_application_password.apppw-sshizzle-ca.id
allowed_audiences = ["https://func-sshizzle-${lower(random_id.function-id.b64_url)}.azurewebsites.net"]
}
}
app_settings = {
KV_NAME = local.keyvault_name
}
identity {
type = "SystemAssigned"
}
}