diff --git a/azurerm/internal/services/iothub/data_source_iothub_dps_shared_access_policy.go b/azurerm/internal/services/iothub/data_source_iothub_dps_shared_access_policy.go new file mode 100644 index 000000000000..63dc608266c0 --- /dev/null +++ b/azurerm/internal/services/iothub/data_source_iothub_dps_shared_access_policy.go @@ -0,0 +1,119 @@ +package iothub + +import ( + "fmt" + "regexp" + "time" + + "github.com/hashicorp/terraform-plugin-sdk/helper/schema" + "github.com/hashicorp/terraform-plugin-sdk/helper/validation" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/helpers/azure" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/helpers/validate" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/internal/clients" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/internal/timeouts" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/utils" +) + +func dataSourceIotHubDPSSharedAccessPolicy() *schema.Resource { + return &schema.Resource{ + Read: dataSourceIotHubDPSSharedAccessPolicyRead, + + Timeouts: &schema.ResourceTimeout{ + Read: schema.DefaultTimeout(5 * time.Minute), + }, + + Schema: map[string]*schema.Schema{ + "name": { + Type: schema.TypeString, + Required: true, + ValidateFunc: validation.StringMatch(regexp.MustCompile(`[a-zA-Z0-9!._-]{1,64}`), ""+ + "The shared access policy key name must not be empty, and must not exceed 64 characters in length. The shared access policy key name can only contain alphanumeric characters, exclamation marks, periods, underscores and hyphens."), + }, + + "resource_group_name": azure.SchemaResourceGroupNameForDataSource(), + + "iothub_dps_name": { + Type: schema.TypeString, + Required: true, + ValidateFunc: validate.IoTHubName, + }, + + "primary_key": { + Type: schema.TypeString, + Sensitive: true, + Computed: true, + }, + + "primary_connection_string": { + Type: schema.TypeString, + Sensitive: true, + Computed: true, + }, + + "secondary_key": { + Type: schema.TypeString, + Sensitive: true, + Computed: true, + }, + + "secondary_connection_string": { + Type: schema.TypeString, + Sensitive: true, + Computed: true, + }, + }, + } +} + +func dataSourceIotHubDPSSharedAccessPolicyRead(d *schema.ResourceData, meta interface{}) error { + client := meta.(*clients.Client).IoTHub.DPSResourceClient + ctx, cancel := timeouts.ForRead(meta.(*clients.Client).StopContext, d) + defer cancel() + + keyName := d.Get("name").(string) + resourceGroup := d.Get("resource_group_name").(string) + iothubDpsName := d.Get("iothub_dps_name").(string) + + iothubDps, err := client.Get(ctx, iothubDpsName, resourceGroup) + if err != nil { + if utils.ResponseWasNotFound(iothubDps.Response) { + return fmt.Errorf("Error: IotHub DPS %q (Resource Group %q) was not found", iothubDpsName, resourceGroup) + } + + return fmt.Errorf("Error retrieving IotHub DPS %q (Resource Group %q): %+v", iothubDpsName, resourceGroup, err) + } + + accessPolicy, err := client.ListKeysForKeyName(ctx, iothubDpsName, keyName, resourceGroup) + if err != nil { + if utils.ResponseWasNotFound(accessPolicy.Response) { + return fmt.Errorf("Error: Shared Access Policy %q (IotHub DPS %q / Resource Group %q) was not found", keyName, iothubDpsName, resourceGroup) + } + + return fmt.Errorf("Error loading Shared Access Policy %q (IotHub DPS %q / Resource Group %q): %+v", keyName, iothubDpsName, resourceGroup, err) + } + + d.Set("name", keyName) + d.Set("resource_group_name", resourceGroup) + + resourceID := fmt.Sprintf("%s/keys/%s", *iothubDps.ID, keyName) + d.SetId(resourceID) + + d.Set("primary_key", accessPolicy.PrimaryKey) + d.Set("secondary_key", accessPolicy.SecondaryKey) + + primaryConnectionString := "" + secondaryConnectionString := "" + if iothubDps.Properties != nil && iothubDps.Properties.DeviceProvisioningHostName != nil { + hostname := iothubDps.Properties.DeviceProvisioningHostName + if primary := accessPolicy.PrimaryKey; primary != nil { + primaryConnectionString = getSAPConnectionString(*hostname, keyName, *primary) + } + if secondary := accessPolicy.SecondaryKey; secondary != nil { + secondaryConnectionString = getSAPConnectionString(*hostname, keyName, *secondary) + } + } + d.Set("primary_connection_string", primaryConnectionString) + d.Set("secondary_connection_string", secondaryConnectionString) + + return nil +} diff --git a/azurerm/internal/services/iothub/registration.go b/azurerm/internal/services/iothub/registration.go index e931067bded7..5bdcfdd49312 100644 --- a/azurerm/internal/services/iothub/registration.go +++ b/azurerm/internal/services/iothub/registration.go @@ -14,8 +14,9 @@ func (r Registration) Name() string { // SupportedDataSources returns the supported Data Sources supported by this Service func (r Registration) SupportedDataSources() map[string]*schema.Resource { return map[string]*schema.Resource{ - "azurerm_iothub_dps": dataSourceArmIotHubDPS(), - "azurerm_iothub_shared_access_policy": dataSourceArmIotHubSharedAccessPolicy(), + "azurerm_iothub_dps": dataSourceArmIotHubDPS(), + "azurerm_iothub_dps_shared_access_policy": dataSourceIotHubDPSSharedAccessPolicy(), + "azurerm_iothub_shared_access_policy": dataSourceArmIotHubSharedAccessPolicy(), } } diff --git a/azurerm/internal/services/iothub/resource_arm_iothub_dps_shared_access_policy.go b/azurerm/internal/services/iothub/resource_arm_iothub_dps_shared_access_policy.go index 324e3421e3a0..03e2b794b7fe 100644 --- a/azurerm/internal/services/iothub/resource_arm_iothub_dps_shared_access_policy.go +++ b/azurerm/internal/services/iothub/resource_arm_iothub_dps_shared_access_policy.go @@ -234,21 +234,19 @@ func resourceArmIotHubDPSSharedAccessPolicyRead(d *schema.ResourceData, meta int d.Set("primary_key", accessPolicy.PrimaryKey) d.Set("secondary_key", accessPolicy.SecondaryKey) - if props := iothubDps.Properties; props != nil { - if host := props.ServiceOperationsHostName; host != nil { - if pKey := accessPolicy.PrimaryKey; pKey != nil { - if err := d.Set("primary_connection_string", getSAPConnectionString(*host, keyName, *pKey)); err != nil { - return fmt.Errorf("error setting `primary_connection_string`: %v", err) - } - } - - if sKey := accessPolicy.SecondaryKey; sKey != nil { - if err := d.Set("secondary_connection_string", getSAPConnectionString(*host, keyName, *sKey)); err != nil { - return fmt.Errorf("error setting `secondary_connection_string`: %v", err) - } - } + primaryConnectionString := "" + secondaryConnectionString := "" + if iothubDps.Properties != nil && iothubDps.Properties.DeviceProvisioningHostName != nil { + hostname := iothubDps.Properties.DeviceProvisioningHostName + if primary := accessPolicy.PrimaryKey; primary != nil { + primaryConnectionString = getSAPConnectionString(*hostname, keyName, *primary) + } + if secondary := accessPolicy.SecondaryKey; secondary != nil { + secondaryConnectionString = getSAPConnectionString(*hostname, keyName, *secondary) } } + d.Set("primary_connection_string", primaryConnectionString) + d.Set("secondary_connection_string", secondaryConnectionString) rights := flattenDpsAccessRights(accessPolicy.Rights) d.Set("enrollment_read", rights.enrollmentRead) diff --git a/azurerm/internal/services/iothub/tests/data_source_iothub_dps_shared_access_policy_test.go b/azurerm/internal/services/iothub/tests/data_source_iothub_dps_shared_access_policy_test.go new file mode 100644 index 000000000000..5cf2c07d3013 --- /dev/null +++ b/azurerm/internal/services/iothub/tests/data_source_iothub_dps_shared_access_policy_test.go @@ -0,0 +1,61 @@ +package tests + +import ( + "fmt" + "testing" + + "github.com/hashicorp/terraform-plugin-sdk/helper/resource" + "github.com/terraform-providers/terraform-provider-azurerm/azurerm/internal/acceptance" +) + +func TestAccDataSourceAzureRMIotHubDpsSharedAccessPolicy_basic(t *testing.T) { + data := acceptance.BuildTestData(t, "data.azurerm_iothub_dps_shared_access_policy", "test") + + resource.ParallelTest(t, resource.TestCase{ + PreCheck: func() { acceptance.PreCheck(t) }, + Providers: acceptance.SupportedProviders, + CheckDestroy: testCheckAzureRMIotHubDpsSharedAccessPolicyDestroy, + Steps: []resource.TestStep{ + { + Config: testAccDataSourceAzureRMIotHubDpsSharedAccessPolicy_basic(data), + Check: resource.ComposeTestCheckFunc( + testCheckAzureRMIotHubDpsSharedAccessPolicyExists(data.ResourceName), + resource.TestCheckResourceAttrSet(data.ResourceName, "primary_key"), + resource.TestCheckResourceAttrSet(data.ResourceName, "primary_connection_string"), + resource.TestCheckResourceAttrSet(data.ResourceName, "secondary_key"), + resource.TestCheckResourceAttrSet(data.ResourceName, "secondary_connection_string"), + ), + }, + }, + }) +} + +func testAccDataSourceAzureRMIotHubDpsSharedAccessPolicy_basic(data acceptance.TestData) string { + return fmt.Sprintf(` +resource "azurerm_resource_group" "test" { + name = "acctestRG-%d" + location = "%s" +} +resource "azurerm_iothub_dps" "test" { + name = "acctestIoTDPS-%d" + resource_group_name = "${azurerm_resource_group.test.name}" + location = "${azurerm_resource_group.test.location}" + + sku { + name = "S1" + capacity = "1" + } +} +resource "azurerm_iothub_dps_shared_access_policy" "test" { + resource_group_name = "${azurerm_resource_group.test.name}" + iothub_dps_name = "${azurerm_iothub_dps.test.name}" + name = "acctest" + service_config = true +} +data "azurerm_iothub_dps_shared_access_policy" "test" { + name = "${azurerm_iothub_dps_shared_access_policy.test.name}" + iothub_dps_name = "${azurerm_iothub_dps.test.name}" + resource_group_name = "${azurerm_resource_group.test.name}" +} +`, data.RandomInteger, data.Locations.Primary, data.RandomInteger) +} diff --git a/website/azurerm.erb b/website/azurerm.erb index 95e77be0e89a..97fe50b576d6 100644 --- a/website/azurerm.erb +++ b/website/azurerm.erb @@ -234,6 +234,10 @@ azurerm_iothub_dps +