-
Notifications
You must be signed in to change notification settings - Fork 4.7k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
New Resource:
azurerm_azuread_application
(#1269)
* Add an AD Application provider. Split from PR #961. * Rename resource to azurerm_azuread_application and update function names to match. * Address code review comments. * Remove Password/Key Credentials to turn them into resources. * Refactoring: - updating the acceptance tests to prefix the name with `acctest` so it's easily identifyable - wrapping the error messages to display more useful information - ensuring we disable apps or other tenants before deleting them - making available_to_other_tenants / oauth2_allow_implicit_flow not computed - updating the docs ``` $ acctests azurerm TestAccAzureRMActiveDirectoryApplication_ === RUN TestAccAzureRMActiveDirectoryApplication_importBasic --- PASS: TestAccAzureRMActiveDirectoryApplication_importBasic (38.38s) === RUN TestAccAzureRMActiveDirectoryApplication_importComplete --- PASS: TestAccAzureRMActiveDirectoryApplication_importComplete (25.42s) === RUN TestAccAzureRMActiveDirectoryApplication_basic --- PASS: TestAccAzureRMActiveDirectoryApplication_basic (20.18s) === RUN TestAccAzureRMActiveDirectoryApplication_availableToOtherTenants --- PASS: TestAccAzureRMActiveDirectoryApplication_availableToOtherTenants (21.60s) === RUN TestAccAzureRMActiveDirectoryApplication_complete --- PASS: TestAccAzureRMActiveDirectoryApplication_complete (20.19s) === RUN TestAccAzureRMActiveDirectoryApplication_update --- PASS: TestAccAzureRMActiveDirectoryApplication_update (39.92s) PASS ok github.com/terraform-providers/terraform-provider-azurerm/azurerm 165.735s ```
- Loading branch information
1 parent
4c760cb
commit 30f0dfa
Showing
7 changed files
with
577 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
package azurerm | ||
|
||
import ( | ||
"testing" | ||
|
||
"github.com/google/uuid" | ||
"github.com/hashicorp/terraform/helper/resource" | ||
) | ||
|
||
func TestAccAzureRMActiveDirectoryApplication_importBasic(t *testing.T) { | ||
resourceName := "azurerm_azuread_application.test" | ||
|
||
id := uuid.New().String() | ||
config := testAccAzureRMActiveDirectoryApplication_basic(id) | ||
|
||
resource.Test(t, resource.TestCase{ | ||
PreCheck: func() { testAccPreCheck(t) }, | ||
Providers: testAccProviders, | ||
CheckDestroy: testCheckAzureRMActiveDirectoryApplicationDestroy, | ||
Steps: []resource.TestStep{ | ||
{ | ||
Config: config, | ||
}, | ||
{ | ||
ResourceName: resourceName, | ||
ImportState: true, | ||
ImportStateVerify: true, | ||
}, | ||
}, | ||
}) | ||
} | ||
|
||
func TestAccAzureRMActiveDirectoryApplication_importComplete(t *testing.T) { | ||
resourceName := "azurerm_azuread_application.test" | ||
|
||
id := uuid.New().String() | ||
config := testAccAzureRMActiveDirectoryApplication_complete(id) | ||
|
||
resource.Test(t, resource.TestCase{ | ||
PreCheck: func() { testAccPreCheck(t) }, | ||
Providers: testAccProviders, | ||
CheckDestroy: testCheckAzureRMActiveDirectoryApplicationDestroy, | ||
Steps: []resource.TestStep{ | ||
{ | ||
Config: config, | ||
}, | ||
{ | ||
ResourceName: resourceName, | ||
ImportState: true, | ||
ImportStateVerify: true, | ||
}, | ||
}, | ||
}) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,255 @@ | ||
package azurerm | ||
|
||
import ( | ||
"fmt" | ||
"log" | ||
|
||
"github.com/Azure/azure-sdk-for-go/services/graphrbac/1.6/graphrbac" | ||
"github.com/hashicorp/terraform/helper/schema" | ||
"github.com/terraform-providers/terraform-provider-azurerm/azurerm/utils" | ||
) | ||
|
||
func resourceArmActiveDirectoryApplication() *schema.Resource { | ||
return &schema.Resource{ | ||
Create: resourceArmActiveDirectoryApplicationCreate, | ||
Read: resourceArmActiveDirectoryApplicationRead, | ||
Update: resourceArmActiveDirectoryApplicationUpdate, | ||
Delete: resourceArmActiveDirectoryApplicationDelete, | ||
Importer: &schema.ResourceImporter{ | ||
State: schema.ImportStatePassthrough, | ||
}, | ||
|
||
Schema: map[string]*schema.Schema{ | ||
"name": { | ||
Type: schema.TypeString, | ||
Required: true, | ||
}, | ||
|
||
"homepage": { | ||
Type: schema.TypeString, | ||
Optional: true, | ||
Computed: true, | ||
}, | ||
|
||
"identifier_uris": { | ||
Type: schema.TypeList, | ||
Optional: true, | ||
Computed: true, | ||
MinItems: 1, | ||
Elem: &schema.Schema{ | ||
Type: schema.TypeString, | ||
}, | ||
}, | ||
|
||
"reply_urls": { | ||
Type: schema.TypeList, | ||
Optional: true, | ||
Computed: true, | ||
Elem: &schema.Schema{ | ||
Type: schema.TypeString, | ||
}, | ||
}, | ||
|
||
"available_to_other_tenants": { | ||
Type: schema.TypeBool, | ||
Optional: true, | ||
}, | ||
|
||
"oauth2_allow_implicit_flow": { | ||
Type: schema.TypeBool, | ||
Optional: true, | ||
}, | ||
|
||
"application_id": { | ||
Type: schema.TypeString, | ||
Computed: true, | ||
}, | ||
}, | ||
} | ||
} | ||
|
||
func resourceArmActiveDirectoryApplicationCreate(d *schema.ResourceData, meta interface{}) error { | ||
client := meta.(*ArmClient).applicationsClient | ||
ctx := meta.(*ArmClient).StopContext | ||
|
||
name := d.Get("name").(string) | ||
availableToOtherTenants := d.Get("available_to_other_tenants").(bool) | ||
|
||
properties := graphrbac.ApplicationCreateParameters{ | ||
DisplayName: &name, | ||
Homepage: expandAzureRmActiveDirectoryApplicationHomepage(d, name), | ||
IdentifierUris: expandAzureRmActiveDirectoryApplicationIdentifierUris(d), | ||
ReplyUrls: expandAzureRmActiveDirectoryApplicationReplyUrls(d), | ||
AvailableToOtherTenants: utils.Bool(availableToOtherTenants), | ||
} | ||
|
||
if v, ok := d.GetOk("oauth2_allow_implicit_flow"); ok { | ||
properties.Oauth2AllowImplicitFlow = utils.Bool(v.(bool)) | ||
} | ||
|
||
app, err := client.Create(ctx, properties) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
d.SetId(*app.ObjectID) | ||
|
||
return resourceArmActiveDirectoryApplicationRead(d, meta) | ||
} | ||
|
||
func resourceArmActiveDirectoryApplicationUpdate(d *schema.ResourceData, meta interface{}) error { | ||
client := meta.(*ArmClient).applicationsClient | ||
ctx := meta.(*ArmClient).StopContext | ||
|
||
name := d.Get("name").(string) | ||
|
||
var properties graphrbac.ApplicationUpdateParameters | ||
|
||
if d.HasChange("name") { | ||
properties.DisplayName = &name | ||
} | ||
|
||
if d.HasChange("homepage") { | ||
properties.Homepage = expandAzureRmActiveDirectoryApplicationHomepage(d, name) | ||
} | ||
|
||
if d.HasChange("identifier_uris") { | ||
properties.IdentifierUris = expandAzureRmActiveDirectoryApplicationIdentifierUris(d) | ||
} | ||
|
||
if d.HasChange("reply_urls") { | ||
properties.ReplyUrls = expandAzureRmActiveDirectoryApplicationReplyUrls(d) | ||
} | ||
|
||
if d.HasChange("available_to_other_tenants") { | ||
availableToOtherTenants := d.Get("available_to_other_tenants").(bool) | ||
properties.AvailableToOtherTenants = utils.Bool(availableToOtherTenants) | ||
} | ||
|
||
if d.HasChange("oauth2_allow_implicit_flow") { | ||
oauth := d.Get("oauth2_allow_implicit_flow").(bool) | ||
properties.Oauth2AllowImplicitFlow = utils.Bool(oauth) | ||
} | ||
|
||
_, err := client.Patch(ctx, d.Id(), properties) | ||
if err != nil { | ||
return fmt.Errorf("Error patching Azure AD Application with ID %q: %+v", d.Id(), err) | ||
} | ||
|
||
return resourceArmActiveDirectoryApplicationRead(d, meta) | ||
} | ||
|
||
func resourceArmActiveDirectoryApplicationRead(d *schema.ResourceData, meta interface{}) error { | ||
client := meta.(*ArmClient).applicationsClient | ||
ctx := meta.(*ArmClient).StopContext | ||
|
||
resp, err := client.Get(ctx, d.Id()) | ||
if err != nil { | ||
if utils.ResponseWasNotFound(resp.Response) { | ||
log.Printf("[DEBUG] Azure AD Application with ID %q was not found - removing from state", d.Id()) | ||
d.SetId("") | ||
return nil | ||
} | ||
|
||
return fmt.Errorf("Error retrieving Azure AD Application with ID %q: %+v", d.Id(), err) | ||
} | ||
|
||
d.Set("name", resp.DisplayName) | ||
d.Set("application_id", resp.AppID) | ||
d.Set("homepage", resp.Homepage) | ||
d.Set("available_to_other_tenants", resp.AvailableToOtherTenants) | ||
d.Set("oauth2_allow_implicit_flow", resp.Oauth2AllowImplicitFlow) | ||
|
||
identifierUris := flattenAzureADApplicationIdentifierUris(resp.IdentifierUris) | ||
if err := d.Set("identifier_uris", identifierUris); err != nil { | ||
return fmt.Errorf("Error setting`identifier_uris`: %+v", err) | ||
} | ||
|
||
replyUrls := flattenAzureADApplicationReplyUrls(resp.ReplyUrls) | ||
if err := d.Set("reply_urls", replyUrls); err != nil { | ||
return fmt.Errorf("Error setting`reply_urls`: %+v", err) | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func resourceArmActiveDirectoryApplicationDelete(d *schema.ResourceData, meta interface{}) error { | ||
client := meta.(*ArmClient).applicationsClient | ||
ctx := meta.(*ArmClient).StopContext | ||
|
||
// in order to delete an application which is available to other tenants, we first have to disable this setting | ||
availableToOtherTenants := d.Get("available_to_other_tenants").(bool) | ||
if availableToOtherTenants { | ||
log.Printf("[DEBUG] Azure AD Application is available to other tenants - disabling that feature before deleting.") | ||
properties := graphrbac.ApplicationUpdateParameters{ | ||
AvailableToOtherTenants: utils.Bool(false), | ||
} | ||
_, err := client.Patch(ctx, d.Id(), properties) | ||
if err != nil { | ||
return fmt.Errorf("Error patching Azure AD Application with ID %q: %+v", d.Id(), err) | ||
} | ||
} | ||
|
||
resp, err := client.Delete(ctx, d.Id()) | ||
if err != nil { | ||
if !utils.ResponseWasNotFound(resp) { | ||
return fmt.Errorf("Error Deleting Azure AD Application with ID %q: %+v", d.Id(), err) | ||
} | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func expandAzureRmActiveDirectoryApplicationHomepage(d *schema.ResourceData, name string) *string { | ||
if v, ok := d.GetOk("homepage"); ok { | ||
return utils.String(v.(string)) | ||
} | ||
|
||
return utils.String(fmt.Sprintf("http://%s", name)) | ||
} | ||
|
||
func expandAzureRmActiveDirectoryApplicationIdentifierUris(d *schema.ResourceData) *[]string { | ||
identifierUris := d.Get("identifier_uris").([]interface{}) | ||
identifiers := make([]string, 0) | ||
|
||
for _, id := range identifierUris { | ||
identifiers = append(identifiers, id.(string)) | ||
} | ||
|
||
return &identifiers | ||
} | ||
|
||
func expandAzureRmActiveDirectoryApplicationReplyUrls(d *schema.ResourceData) *[]string { | ||
replyUrls := d.Get("reply_urls").([]interface{}) | ||
urls := make([]string, 0) | ||
|
||
for _, url := range replyUrls { | ||
urls = append(urls, url.(string)) | ||
} | ||
|
||
return &urls | ||
} | ||
|
||
func flattenAzureADApplicationIdentifierUris(input *[]string) []string { | ||
output := make([]string, 0) | ||
|
||
if input != nil { | ||
for _, v := range *input { | ||
output = append(output, v) | ||
} | ||
} | ||
|
||
return output | ||
} | ||
|
||
func flattenAzureADApplicationReplyUrls(input *[]string) []string { | ||
output := make([]string, 0) | ||
|
||
if input != nil { | ||
for _, v := range *input { | ||
output = append(output, v) | ||
} | ||
} | ||
|
||
return output | ||
} |
Oops, something went wrong.