diff --git a/internal/services/nginx/nginx_configuration_data_source_test.go b/internal/services/nginx/nginx_configuration_data_source_test.go deleted file mode 100644 index bd711b395671..000000000000 --- a/internal/services/nginx/nginx_configuration_data_source_test.go +++ /dev/null @@ -1,39 +0,0 @@ -// Copyright (c) HashiCorp, Inc. -// SPDX-License-Identifier: MPL-2.0 - -package nginx_test - -import ( - "fmt" - "testing" - - "github.com/hashicorp/terraform-provider-azurerm/internal/acceptance" - "github.com/hashicorp/terraform-provider-azurerm/internal/acceptance/check" -) - -type NginxConfigurationDataSource struct{} - -func TestAccNginxConfigurationDataSource_basic(t *testing.T) { - data := acceptance.BuildTestData(t, "data.azurerm_nginx_configuration", "test") - r := NginxConfigurationDataSource{} - - data.DataSourceTest(t, []acceptance.TestStep{ - { - Config: r.basic(data), - Check: acceptance.ComposeTestCheckFunc( - check.That(data.ResourceName).Key("root_file").Exists(), - check.That(data.ResourceName).Key("config_file").Exists(), - ), - }, - }) -} - -func (d NginxConfigurationDataSource) basic(data acceptance.TestData) string { - return fmt.Sprintf(` -%s - -data "azurerm_nginx_configuration" "test" { - nginx_deployment_id = azurerm_nginx_deployment.test.id -} -`, ConfigurationResource{}.basic(data)) -} diff --git a/internal/services/nginx/nginx_configuration_resource.go b/internal/services/nginx/nginx_configuration_resource.go index 01b84d86bd95..42ce2cbe465d 100644 --- a/internal/services/nginx/nginx_configuration_resource.go +++ b/internal/services/nginx/nginx_configuration_resource.go @@ -93,7 +93,15 @@ func (c ConfigurationModel) ToSDKModel() nginxconfiguration.NginxConfiguration { type ConfigurationResource struct{} +// This resource has been deprecated and will be removed in the next major release. +// Default Nginx Configuration cannot be created anymore for service API breaking change created it automatically +// nginx configuration block is now embedded into nginx deployment resource +func (m *ConfigurationResource) DeprecatedInFavourOfResource() string { + return "azurerm_nginx_deployment" +} + var _ sdk.Resource = (*ConfigurationResource)(nil) +var _ sdk.ResourceWithDeprecationReplacedBy = &ConfigurationResource{} func (m ConfigurationResource) Arguments() map[string]*pluginsdk.Schema { return map[string]*pluginsdk.Schema{ diff --git a/internal/services/nginx/nginx_configuration_resource_test.go b/internal/services/nginx/nginx_configuration_resource_test.go deleted file mode 100644 index 2369b8308b53..000000000000 --- a/internal/services/nginx/nginx_configuration_resource_test.go +++ /dev/null @@ -1,257 +0,0 @@ -// Copyright (c) HashiCorp, Inc. -// SPDX-License-Identifier: MPL-2.0 - -package nginx_test - -import ( - "context" - "fmt" - "testing" - - "github.com/hashicorp/go-azure-sdk/resource-manager/nginx/2024-01-01-preview/nginxconfiguration" - "github.com/hashicorp/terraform-provider-azurerm/internal/acceptance" - "github.com/hashicorp/terraform-provider-azurerm/internal/acceptance/check" - "github.com/hashicorp/terraform-provider-azurerm/internal/clients" - "github.com/hashicorp/terraform-provider-azurerm/internal/services/nginx" - "github.com/hashicorp/terraform-provider-azurerm/internal/tf/pluginsdk" - "github.com/hashicorp/terraform-provider-azurerm/utils" -) - -type ConfigurationResource struct{} - -func (a ConfigurationResource) Exists(ctx context.Context, client *clients.Client, state *pluginsdk.InstanceState) (*bool, error) { - id, err := nginxconfiguration.ParseConfigurationID(state.ID) - if err != nil { - return nil, err - } - resp, err := client.Nginx.NginxConfiguration.ConfigurationsGet(ctx, *id) - if err != nil { - return nil, fmt.Errorf("retrieving Configuration %s: %+v", id, err) - } - return utils.Bool(resp.Model != nil), nil -} - -func TestAccConfiguration_basic(t *testing.T) { - data := acceptance.BuildTestData(t, nginx.ConfigurationResource{}.ResourceType(), "test") - r := ConfigurationResource{} - data.ResourceTest(t, r, []acceptance.TestStep{ - { - Config: r.basic(data), - Check: acceptance.ComposeTestCheckFunc( - check.That(data.ResourceName).ExistsInAzure(r), - ), - }, - data.ImportStep("protected_file"), - }) -} - -func TestAccConfiguration_update(t *testing.T) { - data := acceptance.BuildTestData(t, nginx.ConfigurationResource{}.ResourceType(), "test") - r := ConfigurationResource{} - data.ResourceTest(t, r, []acceptance.TestStep{ - { - Config: r.basic(data), - Check: acceptance.ComposeTestCheckFunc( - check.That(data.ResourceName).ExistsInAzure(r), - ), - }, - data.ImportStep("protected_file"), - { - Config: r.update(data), - Check: acceptance.ComposeTestCheckFunc( - check.That(data.ResourceName).ExistsInAzure(r), - ), - }, - data.ImportStep("protected_file"), - }) -} - -func TestAccConfiguration_requiresImport(t *testing.T) { - data := acceptance.BuildTestData(t, nginx.ConfigurationResource{}.ResourceType(), "test") - r := ConfigurationResource{} - data.ResourceTest(t, r, []acceptance.TestStep{ - { - Config: r.basic(data), - Check: acceptance.ComposeTestCheckFunc( - check.That(data.ResourceName).ExistsInAzure(r), - ), - }, - data.RequiresImportErrorStep(r.requiresImport), - }) -} - -func (a ConfigurationResource) basic(data acceptance.TestData) string { - return fmt.Sprintf(` - - -%s - -resource "azurerm_nginx_configuration" "test" { - nginx_deployment_id = azurerm_nginx_deployment.test.id - root_file = "/etc/nginx/nginx.conf" - - config_file { - content = local.config_content - virtual_path = "/etc/nginx/nginx.conf" - } - - protected_file { - content = local.protected_content - virtual_path = "/opt/.htpasswd" - } -} -`, a.template(data)) -} - -func (a ConfigurationResource) requiresImport(data acceptance.TestData) string { - return fmt.Sprintf(` - - -%s - -resource "azurerm_nginx_configuration" "import" { - nginx_deployment_id = azurerm_nginx_configuration.test.nginx_deployment_id - root_file = azurerm_nginx_configuration.test.root_file - config_file { - content = base64encode("http{}") - virtual_path = "/" - } -} -`, a.basic(data)) -} - -func (a ConfigurationResource) update(data acceptance.TestData) string { - return fmt.Sprintf(` - - -%s - -resource "azurerm_nginx_configuration" "test" { - nginx_deployment_id = azurerm_nginx_deployment.test.id - root_file = "/etc/nginx/nginx.conf" - - config_file { - content = local.config_content - virtual_path = "/etc/nginx/nginx.conf" - } - - config_file { - content = local.sub_config_content - virtual_path = "/etc/nginx/site/b.conf" - } - - protected_file { - content = local.protected_content - virtual_path = "/opt/.htpasswd" - } -} -`, a.template(data)) -} - -func (a ConfigurationResource) template(data acceptance.TestData) string { - return fmt.Sprintf(` -provider "azurerm" { - features {} -} - -resource "azurerm_resource_group" "test" { - name = "acctestRG-auto-%[1]d" - location = "%[2]s" -} - -locals { - config_content = base64encode(<<-EOT -http { - server { - listen 80; - location / { - auth_basic "Protected Area"; - auth_basic_user_file /opt/.htpasswd; - default_type text/html; - return 200 ' -
this one will be updated
-
at 10:38 am
- '; - } - include site/*.conf; - } -} -EOT - ) - - protected_content = base64encode(<<-EOT -user:$apr1$VeUA5kt.$IjjRk//8miRxDsZvD4daF1 -EOT - ) - - sub_config_content = base64encode(<<-EOT -location /bbb { - default_type text/html; - return 200 ' -
this one will be updated
-
at 10:38 am
- '; -} -EOT - ) -} - -resource "azurerm_public_ip" "test" { - name = "acctest%[1]d" - resource_group_name = azurerm_resource_group.test.name - location = azurerm_resource_group.test.location - allocation_method = "Static" - sku = "Standard" - - tags = { - environment = "Production" - } -} - -resource "azurerm_virtual_network" "test" { - name = "acctestvirtnet%[1]d" - address_space = ["10.0.0.0/16"] - location = azurerm_resource_group.test.location - resource_group_name = azurerm_resource_group.test.name -} - -resource "azurerm_subnet" "test" { - name = "accsubnet%[1]d" - resource_group_name = azurerm_resource_group.test.name - virtual_network_name = azurerm_virtual_network.test.name - address_prefixes = ["10.0.2.0/24"] - delegation { - name = "delegation" - - service_delegation { - name = "NGINX.NGINXPLUS/nginxDeployments" - actions = [ - "Microsoft.Network/virtualNetworks/subnets/join/action", - ] - } - } -} - -resource "azurerm_nginx_deployment" "test" { - name = "acctest-%[1]d" - resource_group_name = azurerm_resource_group.test.name - sku = "standard_Monthly" - location = azurerm_resource_group.test.location - - //message: "Conflict managed resource group name: tenant: -91a, subscription xxx, resource group example." - managed_resource_group = "accmr%[1]d" - diagnose_support_enabled = true - - frontend_public { - ip_address = [azurerm_public_ip.test.id] - } - - network_interface { - subnet_id = azurerm_subnet.test.id - } - tags = { - foo = "bar" - } -} -`, data.RandomInteger, data.Locations.Primary) -} diff --git a/internal/services/nginx/nginx_deployment_resource.go b/internal/services/nginx/nginx_deployment_resource.go index 19dfede0e880..c6d90cab4003 100644 --- a/internal/services/nginx/nginx_deployment_resource.go +++ b/internal/services/nginx/nginx_deployment_resource.go @@ -12,6 +12,7 @@ import ( "github.com/hashicorp/go-azure-helpers/lang/response" "github.com/hashicorp/go-azure-helpers/resourcemanager/commonschema" "github.com/hashicorp/go-azure-helpers/resourcemanager/identity" + "github.com/hashicorp/go-azure-sdk/resource-manager/nginx/2024-01-01-preview/nginxconfiguration" "github.com/hashicorp/go-azure-sdk/resource-manager/nginx/2024-01-01-preview/nginxdeployment" "github.com/hashicorp/terraform-provider-azurerm/internal/sdk" "github.com/hashicorp/terraform-provider-azurerm/internal/tf/pluginsdk" @@ -37,6 +38,18 @@ type NetworkInterface struct { SubnetId string `tfschema:"subnet_id"` } +type ConfigureFile struct { + Content string `tfschema:"content"` + VirtualPath string `tfschema:"virtual_path"` +} + +type Configuration struct { + ConfigureFile []ConfigureFile `tfschema:"config_file"` + ProtectedFile []ConfigureFile `tfschema:"protected_file"` + PackageData string `tfschema:"package_data"` + RootFile string `tfschema:"root_file"` +} + type AutoScaleProfile struct { Name string `tfschema:"name"` Min int64 `tfschema:"min_capacity"` @@ -61,6 +74,7 @@ type DeploymentModel struct { FrontendPrivate []FrontendPrivate `tfschema:"frontend_private"` NetworkInterface []NetworkInterface `tfschema:"network_interface"` UpgradeChannel string `tfschema:"automatic_upgrade_channel"` + Configuration []Configuration `tfschema:"configuration"` Tags map[string]string `tfschema:"tags"` } @@ -241,6 +255,73 @@ func (m DeploymentResource) Arguments() map[string]*pluginsdk.Schema { }, false), }, + "configuration": { + Type: pluginsdk.TypeList, + Optional: true, + Computed: true, + MaxItems: 1, + Elem: &pluginsdk.Resource{ + Schema: map[string]*pluginsdk.Schema{ + "config_file": { + Type: pluginsdk.TypeSet, + Optional: true, + AtLeastOneOf: []string{"configuration.0.config_file", "configuration.0.package_data"}, + Elem: &pluginsdk.Resource{ + Schema: map[string]*pluginsdk.Schema{ + "content": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsBase64, + }, + + "virtual_path": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + }, + }, + }, + + "protected_file": { + Type: pluginsdk.TypeSet, + Optional: true, + RequiredWith: []string{"configuration.0.config_file"}, + Elem: &pluginsdk.Resource{ + Schema: map[string]*pluginsdk.Schema{ + "content": { + Type: pluginsdk.TypeString, + Required: true, + Sensitive: true, + ValidateFunc: validation.StringIsBase64, + }, + + "virtual_path": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + }, + }, + }, + + "package_data": { + Type: pluginsdk.TypeString, + Optional: true, + ValidateFunc: validation.StringIsNotEmpty, + AtLeastOneOf: []string{"configuration.0.config_file", "configuration.0.package_data"}, + ConflictsWith: []string{"configuration.0.protected_file", "configuration.0.config_file"}, + }, + + "root_file": { + Type: pluginsdk.TypeString, + Required: true, + ValidateFunc: validation.StringIsNotEmpty, + }, + }, + }, + }, + "tags": commonschema.Tags(), } } @@ -392,6 +473,16 @@ func (m DeploymentResource) Create() sdk.ResourceFunc { return fmt.Errorf("creating %s: %v", id, err) } + if len(model.Configuration) > 0 { + // update configuration + configID := nginxconfiguration.NewConfigurationID(id.SubscriptionId, id.ResourceGroupName, id.NginxDeploymentName, defaultConfigurationName) + + configProp := expandConfiguration(model.Configuration[0]) + if err := meta.Client.Nginx.NginxConfiguration.ConfigurationsCreateOrUpdateThenPoll(ctx, configID, configProp); err != nil { + return fmt.Errorf("update default configuration of %q: %v", configID, err) + } + } + meta.SetID(id) return nil }, @@ -507,6 +598,44 @@ func (m DeploymentResource) Read() sdk.ResourceFunc { } } + // read configuration + configResp, err := meta.Client.Nginx.NginxConfiguration.ConfigurationsGet(ctx, nginxconfiguration.NewConfigurationID(id.SubscriptionId, id.ResourceGroupName, id.NginxDeploymentName, defaultConfigurationName)) + if err != nil && !response.WasNotFound(configResp.HttpResponse) { + return fmt.Errorf("retrieving default configuration of %q: %v", id, err) + } + if model := configResp.Model; model != nil { + if prop := model.Properties; prop != nil { + var files []ConfigureFile + if prop.Files != nil { + for _, file := range *prop.Files { + files = append(files, ConfigureFile{ + Content: pointer.From(file.Content), + VirtualPath: pointer.From(file.VirtualPath), + }) + } + } + + var protectedFiles []ConfigureFile + if prop.ProtectedFiles != nil { + for _, file := range *prop.ProtectedFiles { + protectedFiles = append(protectedFiles, ConfigureFile{ + Content: pointer.From(file.Content), + VirtualPath: pointer.From(file.VirtualPath), + }) + } + } + + output.Configuration = []Configuration{ + { + ConfigureFile: files, + ProtectedFile: protectedFiles, + PackageData: pointer.From(pointer.From(prop.Package).Data), + RootFile: pointer.From(prop.RootFile), + }, + } + } + } + return meta.Encode(&output) }, } @@ -596,6 +725,15 @@ func (m DeploymentResource) Update() sdk.ResourceFunc { return fmt.Errorf("updating %s: %v", id, err) } + if meta.ResourceData.HasChange("configuration") { + configID := nginxconfiguration.NewConfigurationID(id.SubscriptionId, id.ResourceGroupName, id.NginxDeploymentName, defaultConfigurationName) + + configProp := expandConfiguration(model.Configuration[0]) + if err := meta.Client.Nginx.NginxConfiguration.ConfigurationsCreateOrUpdateThenPoll(ctx, configID, configProp); err != nil { + return fmt.Errorf("update default configuration of %q: %v", configID, err) + } + } + return nil }, } @@ -624,3 +762,43 @@ func (m DeploymentResource) Delete() sdk.ResourceFunc { func (m DeploymentResource) IDValidationFunc() pluginsdk.SchemaValidateFunc { return nginxdeployment.ValidateNginxDeploymentID } + +func expandConfiguration(model Configuration) nginxconfiguration.NginxConfiguration { + result := nginxconfiguration.NginxConfiguration{ + Properties: &nginxconfiguration.NginxConfigurationProperties{}, + } + + if len(model.ConfigureFile) > 0 { + var files []nginxconfiguration.NginxConfigurationFile + for _, file := range model.ConfigureFile { + files = append(files, nginxconfiguration.NginxConfigurationFile{ + Content: pointer.To(file.Content), + VirtualPath: pointer.To(file.VirtualPath), + }) + } + result.Properties.Files = &files + } + + if len(model.ProtectedFile) > 0 { + var files []nginxconfiguration.NginxConfigurationFile + for _, file := range model.ProtectedFile { + files = append(files, nginxconfiguration.NginxConfigurationFile{ + Content: pointer.To(file.Content), + VirtualPath: pointer.To(file.VirtualPath), + }) + } + result.Properties.ProtectedFiles = &files + } + + if model.PackageData != "" { + result.Properties.Package = &nginxconfiguration.NginxConfigurationPackage{ + Data: pointer.To(model.PackageData), + } + } + + if model.RootFile != "" { + result.Properties.RootFile = pointer.To(model.RootFile) + } + + return result +} diff --git a/internal/services/nginx/nginx_deployment_resource_test.go b/internal/services/nginx/nginx_deployment_resource_test.go index 39ea538df98a..aa2a19e0aea3 100644 --- a/internal/services/nginx/nginx_deployment_resource_test.go +++ b/internal/services/nginx/nginx_deployment_resource_test.go @@ -82,6 +82,41 @@ func TestAccNginxDeployment_systemAssignedIdentity(t *testing.T) { }) } +func TestAccNginxDeployment_withConfiguration(t *testing.T) { + data := acceptance.BuildTestData(t, nginx.DeploymentResource{}.ResourceType(), "test") + r := DeploymentResource{} + data.ResourceTest(t, r, []acceptance.TestStep{ + { + Config: r.withConfiguration(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep(), + }) +} + +func TestAccNginxDeployment_updateWithConfiguration(t *testing.T) { + data := acceptance.BuildTestData(t, nginx.DeploymentResource{}.ResourceType(), "test") + r := DeploymentResource{} + data.ResourceTest(t, r, []acceptance.TestStep{ + { + Config: r.basic(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep(), + { + Config: r.withConfiguration(data), + Check: acceptance.ComposeTestCheckFunc( + check.That(data.ResourceName).ExistsInAzure(r), + ), + }, + data.ImportStep(), + }) +} + func TestAccNginxDeployment_userAssignedIdentity(t *testing.T) { data := acceptance.BuildTestData(t, nginx.DeploymentResource{}.ResourceType(), "test") r := DeploymentResource{} @@ -100,8 +135,6 @@ func (a DeploymentResource) basic(data acceptance.TestData) string { return fmt.Sprintf(` - - %s resource "azurerm_nginx_deployment" "test" { @@ -217,6 +250,97 @@ resource "azurerm_nginx_deployment" "test" { `, a.template(data), data.RandomInteger, data.Locations.Primary) } +func (a DeploymentResource) withConfiguration(data acceptance.TestData) string { + return fmt.Sprintf(` + + +%s + +locals { + config_content = base64encode(<<-EOT +http { + server { + listen 80; + location / { + auth_basic "Protected Area"; + auth_basic_user_file /opt/.htpasswd; + default_type text/html; + return 200 ' +
this one will be updated
+
at 10:38 am
+ '; + } + include site/*.conf; + } +} +EOT + ) + + protected_content = base64encode(<<-EOT +user:$apr1$VeUA5kt.$IjjRk//8miRxDsZvD4daF1 +EOT + ) + + sub_config_content = base64encode(<<-EOT +location /bbb { + default_type text/html; + return 200 ' +
this one will be updated
+
at 10:38 am
+ '; +} +EOT + ) +} + +resource "azurerm_nginx_deployment" "test" { + name = "acctest-%[2]d" + resource_group_name = azurerm_resource_group.test.name + sku = "standard_Monthly" + location = azurerm_resource_group.test.location + diagnose_support_enabled = true + + frontend_public { + ip_address = [azurerm_public_ip.test.id] + } + + network_interface { + subnet_id = azurerm_subnet.test.id + } + + capacity = 10 + + email = "test@test.com" + + configuration { + root_file = "/etc/nginx/nginx.conf" + + config_file { + content = local.config_content + virtual_path = "/etc/nginx/nginx.conf" + } + + config_file { + content = local.sub_config_content + virtual_path = "/etc/nginx/site/b.conf" + } + + protected_file { + content = local.protected_content + virtual_path = "/opt/.htpasswd" + } + } + + tags = { + foo = "bar" + } + + lifecycle { + ignore_changes = [configuration.0.protected_file] + } +} +`, a.template(data), data.RandomInteger, data.Locations.Primary) +} func (a DeploymentResource) update(data acceptance.TestData) string { return fmt.Sprintf(` diff --git a/website/docs/d/nginx_configuration.html.markdown b/website/docs/d/nginx_configuration.html.markdown deleted file mode 100644 index f944cca4fc82..000000000000 --- a/website/docs/d/nginx_configuration.html.markdown +++ /dev/null @@ -1,55 +0,0 @@ ---- -subcategory: "Nginx" -layout: "azurerm" -page_title: "Azure Resource Manager: Data Source: azurerm_nginx_configuration" -description: |- - Gets information about an existing Nginx Configuration. ---- - -# Data Source: azurerm_nginx_configuration - -Use this data source to access information about an existing Nginx Configuration. - -## Example Usage - -```hcl -data "azurerm_nginx_configuration" "example" { - nginx_deployment_id = azurerm_nginx_deployment.example.id -} - -output "id" { - value = data.azurerm_nginx_configuration.example.id -} -``` - -## Arguments Reference - -The following arguments are supported: - -* `nginx_deployment_id` - (Required) The ID of the Nginx Deployment. - -## Attributes Reference - -In addition to the Arguments listed above - the following Attributes are exported: - -* `id` - The ID of the Nginx Configuration. - -* `config_file` - A `config_file` block as defined below. - -* `package_data` - The package data for this configuration. - -* `root_file` - The root file path of this Nginx Configuration. - ---- - -A `config_file` block exports the following: - -* `content` - The base-64 encoded contents of this configuration file. - -* `virtual_path` - The path of this configuration file. - -## Timeouts - -The `timeouts` block allows you to specify [timeouts](https://www.terraform.io/language/resources/syntax#operation-timeouts) for certain actions: - -* `read` - (Defaults to 5 minutes) Used when retrieving the Nginx Configuration. diff --git a/website/docs/r/nginx_configuration.html.markdown b/website/docs/r/nginx_configuration.html.markdown deleted file mode 100644 index ddbc16ecb946..000000000000 --- a/website/docs/r/nginx_configuration.html.markdown +++ /dev/null @@ -1,168 +0,0 @@ ---- -subcategory: "Nginx" -layout: "azurerm" -page_title: "Azure Resource Manager: azurerm_nginx_configuration" -description: |- - Manages the configuration for a Nginx Deployment. ---- - -# azurerm_nginx_configuration - -Manages the configuration for a Nginx Deployment. - -## Example Usage - -```hcl -resource "azurerm_resource_group" "example" { - name = "example-rg" - location = "West Europe" -} - -resource "azurerm_public_ip" "example" { - name = "example" - resource_group_name = azurerm_resource_group.example.name - location = azurerm_resource_group.example.location - allocation_method = "Static" - sku = "Standard" - - tags = { - environment = "Production" - } -} - -resource "azurerm_virtual_network" "example" { - name = "example-vnet" - address_space = ["10.0.0.0/16"] - location = azurerm_resource_group.example.location - resource_group_name = azurerm_resource_group.example.name -} - -resource "azurerm_subnet" "example" { - name = "example-subnet" - resource_group_name = azurerm_resource_group.example.name - virtual_network_name = azurerm_virtual_network.example.name - address_prefixes = ["10.0.2.0/24"] - delegation { - name = "delegation" - - service_delegation { - name = "NGINX.NGINXPLUS/nginxDeployments" - actions = [ - "Microsoft.Network/virtualNetworks/subnets/join/action", - ] - } - } -} - -resource "azurerm_nginx_deployment" "example" { - name = "example-nginx" - resource_group_name = azurerm_resource_group.example.name - sku = "publicpreview_Monthly_gmz7xq9ge3py" - location = azurerm_resource_group.example.location - managed_resource_group = "example" - diagnose_support_enabled = true - - frontend_public { - ip_address = [azurerm_public_ip.example.id] - } - network_interface { - subnet_id = azurerm_subnet.example.id - } -} - -resource "azurerm_nginx_configuration" "example" { - nginx_deployment_id = azurerm_nginx_deployment.example.id - root_file = "/etc/nginx/nginx.conf" - - config_file { - content = base64encode(<<-EOT -http { - server { - listen 80; - location / { - default_type text/html; - return 200 ' -
this one will be updated
-
at 10:38 am
- '; - } - include site/*.conf; - } -} -EOT - ) - virtual_path = "/etc/nginx/nginx.conf" - } - - config_file { - content = base64encode(<<-EOT -location /bbb { - default_type text/html; - return 200 ' -
this one will be updated
-
at 10:38 am
- '; -} -EOT - ) - virtual_path = "/etc/nginx/site/b.conf" - } -} -``` - -## Arguments Reference - -The following arguments are supported: - -* `nginx_deployment_id` - (Required) The ID of the Nginx Deployment. Changing this forces a new Nginx Configuration to be created. - -* `root_file` - (Required) Specify the root file path of this Nginx Configuration. - ---- - --> **NOTE:** Either `package_data` or `config_file` must be specified - but not both. - -* `package_data` - (Optional) Specify the package data for this configuration. - -* `config_file` - (Optional) One or more `config_file` blocks as defined below. - -* `protected_file` - (Optional) One or more `protected_file` blocks with sensitive information as defined below. If specified `config_file` must also be specified. - ---- - -A `config_file` block supports the following: - -* `content` - (Required) Specifies the base-64 encoded contents of this config file. - -* `virtual_path` - (Required) Specify the path of this config file. - ---- - -A `protected_file` (Protected File) block supports the following: - -* `content` - (Required) Specifies the base-64 encoded contents of this config file (Sensitive). - -* `virtual_path` - (Required) Specify the path of this config file. - -## Attributes Reference - -In addition to the Arguments listed above - the following Attributes are exported: - -* `id` - The ID of this Nginx Configuration. - -## Timeouts - -The `timeouts` block allows you to specify [timeouts](https://www.terraform.io/language/resources/syntax#operation-timeouts) for certain actions: - -* `create` - (Defaults to 30 minutes) Used when creating the Nginx Configuration. -* `read` - (Defaults to 5 minutes) Used when retrieving the Nginx Configuration. -* `update` - (Defaults to 10 minutes) Used when updating the Nginx Configuration. -* `delete` - (Defaults to 10 minutes) Used when deleting the Nginx Configuration. - -## Import - -An Nginx Configuration can be imported using the `resource id`, e.g. - -```shell -terraform import azurerm_nginx_configuration.example /subscriptions/12345678-1234-9876-4563-123456789012/resourceGroups/group1/providers/Nginx.NginxPlus/nginxDeployments/dep1/configurations/default -``` diff --git a/website/docs/r/nginx_deployment.html.markdown b/website/docs/r/nginx_deployment.html.markdown index 2d758af3b3bf..33d7ce5d2bba 100644 --- a/website/docs/r/nginx_deployment.html.markdown +++ b/website/docs/r/nginx_deployment.html.markdown @@ -54,6 +54,40 @@ resource "azurerm_subnet" "example" { } } +locals { + config_content = base64encode(<<-EOT +http { + server { + listen 80; + location / { + auth_basic "Protected Area"; + auth_basic_user_file /opt/.htpasswd; + default_type text/html; + } + include site/*.conf; + } +} +EOT + ) + + protected_content = base64encode(<<-EOT +user:$apr1$VeUA5kt.$IjjRk//8miRxDsZvD4daF1 +EOT + ) + + sub_config_content = base64encode(<<-EOT +location /bbb { + default_type text/html; + return 200 ' +
this one will be updated
+
at 10:38 am
+ '; +} +EOT + ) +} + + resource "azurerm_nginx_deployment" "example" { name = "example-nginx" resource_group_name = azurerm_resource_group.example.name @@ -73,6 +107,29 @@ resource "azurerm_nginx_deployment" "example" { capacity = 20 email = "user@test.com" + configuration { + root_file = "/etc/nginx/nginx.conf" + + config_file { + content = local.config_content + virtual_path = "/etc/nginx/nginx.conf" + } + + config_file { + content = local.sub_config_content + virtual_path = "/etc/nginx/site/b.conf" + } + + protected_file { + content = local.protected_content + virtual_path = "/opt/.htpasswd" + } + } + + lifecycle { + ignore_changes = [configuration.0.protected_file] + } + } ``` @@ -114,6 +171,8 @@ The following arguments are supported: * `automatic_upgrade_channel` - (Optional) Specify the automatic upgrade channel for the NGINX deployment. Defaults to `stable`. The possible values are `stable` and `preview`. +* `configuration` - (Optional) Specify a custom `configuration` block as defined below. + * `tags` - (Optional) A mapping of tags which should be assigned to the Nginx Deployment. --- @@ -158,6 +217,37 @@ A `network_interface` block supports the following: --- +A `configuration` block supports the following: + +* `root_file` - (Required) Specify the root file path of this Nginx Configuration. + +--- + +-> **NOTE:** Either `package_data` or `config_file` must be specified - but not both. + +* `package_data` - (Optional) Specify the package data for this configuration. + +* `config_file` - (Optional) One or more `config_file` blocks as defined below. + +* `protected_file` - (Optional) One or more `protected_file` blocks with sensitive information as defined below. If specified `config_file` must also be specified. + +--- + +A `config_file` block supports the following: + +* `content` - (Required) Specifies the base-64 encoded contents of this config file. + +* `virtual_path` - (Required) Specify the path of this config file. + +--- + +A `protected_file` (Protected File) block supports the following: + +* `content` - (Required) Specifies the base-64 encoded contents of this config file (Sensitive). + +* `virtual_path` - (Required) Specify the path of this config file. +--- + An `auto_scale_profile` block supports the following: * `name` - (Required) Specify the name of the autoscaling profile.