From c7a9b4b9df05722768a0c0da989a30de12c4cf21 Mon Sep 17 00:00:00 2001 From: Heather Lanigan Date: Wed, 23 Oct 2024 10:29:22 +0200 Subject: [PATCH 1/3] docs: add info on which schema attributes will cause delete create Add to the schema attribute descriptions which changes will cause terraform to destroy and recreate a resource. --- docs/resources/application.md | 12 +++---- docs/resources/credential.md | 10 +++--- docs/resources/machine.md | 14 ++++---- docs/resources/model.md | 2 +- docs/resources/offer.md | 8 ++--- docs/resources/secret.md | 2 +- docs/resources/user.md | 6 ++-- internal/provider/resource_application.go | 31 ++++++++++------- internal/provider/resource_credential.go | 13 +++---- internal/provider/resource_machine.go | 41 ++++++++++++++--------- internal/provider/resource_model.go | 3 +- internal/provider/resource_offer.go | 22 +++++++----- internal/provider/resource_secret.go | 5 +-- internal/provider/resource_user.go | 9 ++--- 14 files changed, 100 insertions(+), 78 deletions(-) diff --git a/docs/resources/application.md b/docs/resources/application.md index 32f8c33a..8e91204f 100644 --- a/docs/resources/application.md +++ b/docs/resources/application.md @@ -48,17 +48,17 @@ resource "juju_application" "this" { ### Required -- `model` (String) The name of the model where the application is to be deployed. +- `model` (String) The name of the model where the application is to be deployed. Changing this value will cause the application to be destroyed and recreated by terraform. ### Optional -- `charm` (Block List) The name of the charm to be installed from Charmhub. (see [below for nested schema](#nestedblock--charm)) +- `charm` (Block List) The charm installed from Charmhub. (see [below for nested schema](#nestedblock--charm)) - `config` (Map of String) Application specific configuration. Must evaluate to a string, integer or boolean. -- `constraints` (String) Constraints imposed on this application. +- `constraints` (String) Constraints imposed on this application. Changing this value will cause the application to be destroyed and recreated by terraform. - `endpoint_bindings` (Attributes Set) Configure endpoint bindings (see [below for nested schema](#nestedatt--endpoint_bindings)) - `expose` (Block List) Makes an application publicly available over the network (see [below for nested schema](#nestedblock--expose)) -- `name` (String) A custom name for the application deployment. If empty, uses the charm's name. -- `placement` (String) Specify the target location for the application's units +- `name` (String) A custom name for the application deployment. If empty, uses the charm's name.Changing this value will cause the application to be destroyed and recreated by terraform. +- `placement` (String) Specify the target location for the application's units. Changing this value will cause the application to be destroyed and recreated by terraform. - `resources` (Map of String) Charm resources. Must evaluate to a string. A resource could be a resource revision number from CharmHub or a custom OCI image resource. Specify a resource other than the default for a charm. Note that not all charms have resources. @@ -82,7 +82,7 @@ Notes: Required: -- `name` (String) The name of the charm +- `name` (String) The name of the charm to be deployed. Changing this value will cause the application to be destroyed and recreated by terraform. Optional: diff --git a/docs/resources/credential.md b/docs/resources/credential.md index f13022d9..2b3cc5f4 100644 --- a/docs/resources/credential.md +++ b/docs/resources/credential.md @@ -35,15 +35,15 @@ resource "juju_credential" "this" { ### Required -- `auth_type` (String) Credential authorization type -- `name` (String) The name to be assigned to the credential +- `auth_type` (String) Credential authorization type. +- `name` (String) The name to be assigned to the credential. Changing this value will cause the credential to be destroyed and recreated by terraform. ### Optional - `attributes` (Map of String, Sensitive) Credential attributes accordingly to the cloud -- `client_credential` (Boolean) Add credentials to the client -- `cloud` (Block List) JuJu Cloud where the credentials will be used to access (see [below for nested schema](#nestedblock--cloud)) -- `controller_credential` (Boolean) Add credentials to the controller +- `client_credential` (Boolean) Add credentials to the client. +- `cloud` (Block List) Juju Cloud where the credentials will be used to access. (see [below for nested schema](#nestedblock--cloud)) +- `controller_credential` (Boolean) Add credentials to the controller. ### Read-Only diff --git a/docs/resources/machine.md b/docs/resources/machine.md index 700a8fb8..a0639654 100644 --- a/docs/resources/machine.md +++ b/docs/resources/machine.md @@ -26,19 +26,19 @@ resource "juju_machine" "this_machine" { ### Required -- `model` (String) The Juju model in which to add a new machine. +- `model` (String) The Juju model in which to add a new machine. Changing this value will cause the machine to be destroyed and recreated by terraform. ### Optional -- `base` (String) The operating system to install on the new machine(s). E.g. ubuntu@22.04. -- `constraints` (String) Machine constraints that overwrite those available from 'juju get-model-constraints' and provider's defaults. -- `disks` (String) Storage constraints for disks to attach to the machine(s). +- `base` (String) The operating system to install on the new machine(s). E.g. ubuntu@22.04. Changing this value will cause the machine to be destroyed and recreated by terraform. +- `constraints` (String) Machine constraints that overwrite those available from 'juju get-model-constraints' and provider's defaults. Changing this value will cause the application to be destroyed and recreated by terraform. +- `disks` (String) Storage constraints for disks to attach to the machine(s). Changing this value will cause the machine to be destroyed and recreated by terraform. - `name` (String) A name for the machine resource in Terraform. -- `placement` (String) Additional information about how to allocate the machine in the cloud. +- `placement` (String) Additional information about how to allocate the machine in the cloud. Changing this value will cause the application to be destroyed and recreated by terraform. - `private_key_file` (String) The file path to read the private key from. - `public_key_file` (String) The file path to read the public key from. -- `series` (String, Deprecated) The operating system series to install on the new machine(s). -- `ssh_address` (String) The user@host directive for manual provisioning an existing machine via ssh. Requires public_key_file & private_key_file arguments. +- `series` (String, Deprecated) The operating system series to install on the new machine(s). Changing this value will cause the machine to be destroyed and recreated by terraform. +- `ssh_address` (String) The user@host directive for manual provisioning an existing machine via ssh. Requires public_key_file & private_key_file arguments. Changing this value will cause the machine to be destroyed and recreated by terraform. ### Read-Only diff --git a/docs/resources/model.md b/docs/resources/model.md index e7f593f3..04da910c 100644 --- a/docs/resources/model.md +++ b/docs/resources/model.md @@ -38,7 +38,7 @@ resource "juju_model" "this" { ### Optional -- `cloud` (Block List) JuJu Cloud where the model will operate (see [below for nested schema](#nestedblock--cloud)) +- `cloud` (Block List) Juju Cloud where the model will operate. Changing this value will cause the model to be destroyed and recreated by terraform. (see [below for nested schema](#nestedblock--cloud)) - `config` (Map of String) Override default model configuration - `constraints` (String) Constraints imposed to this model - `credential` (String) Credential used to add the model diff --git a/docs/resources/offer.md b/docs/resources/offer.md index 55af65cf..a145fefd 100644 --- a/docs/resources/offer.md +++ b/docs/resources/offer.md @@ -39,13 +39,13 @@ resource "juju_integration" "this" { ### Required -- `application_name` (String) The name of the application. -- `endpoint` (String) The endpoint name. -- `model` (String) The name of the model to operate in. +- `application_name` (String) The name of the application. Changing this value will cause the offer to be destroyed and recreated by terraform. +- `endpoint` (String) The endpoint name. Changing this value will cause the offer to be destroyed and recreated by terraform. +- `model` (String) The name of the model to operate in. Changing this value will cause the offer to be destroyed and recreated by terraform. ### Optional -- `name` (String) The name of the offer. +- `name` (String) The name of the offer. Changing this value will cause the offer to be destroyed and recreated by terraform. ### Read-Only diff --git a/docs/resources/secret.md b/docs/resources/secret.md index 12c01ef1..524f6043 100644 --- a/docs/resources/secret.md +++ b/docs/resources/secret.md @@ -38,7 +38,7 @@ resource "juju_application" "my-application" { ### Required -- `model` (String) The model in which the secret belongs. +- `model` (String) The model in which the secret belongs. Changing this value will cause the secret to be destroyed and recreated by terraform. - `value` (Map of String, Sensitive) The value map of the secret. There can be more than one key-value pair. ### Optional diff --git a/docs/resources/user.md b/docs/resources/user.md index 77e145bd..27f84065 100644 --- a/docs/resources/user.md +++ b/docs/resources/user.md @@ -17,12 +17,12 @@ A resource that represents a Juju User. ### Required -- `name` (String) The name to be assigned to the user -- `password` (String, Sensitive) The password to be assigned to the user +- `name` (String) The username to be assigned to the user. Changing this value will cause the user to be destroyed and recreated by terraform. +- `password` (String, Sensitive) The password to be assigned to the user. ### Optional -- `display_name` (String) The display name to be assigned to the user (optional) +- `display_name` (String) The display name to be assigned to the user (optional). ### Read-Only diff --git a/internal/provider/resource_application.go b/internal/provider/resource_application.go index 5a543467..72db6a5c 100644 --- a/internal/provider/resource_application.go +++ b/internal/provider/resource_application.go @@ -130,17 +130,19 @@ func (r *applicationResource) Schema(_ context.Context, _ resource.SchemaRequest " is not supported.", Attributes: map[string]schema.Attribute{ "name": schema.StringAttribute{ - Description: "A custom name for the application deployment. If empty, uses the charm's name.", - Optional: true, - Computed: true, + Description: "A custom name for the application deployment. If empty, uses the charm's name." + + "Changing this value will cause the application to be destroyed and recreated by terraform.", + Optional: true, + Computed: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), stringplanmodifier.UseStateForUnknown(), }, }, "model": schema.StringAttribute{ - Description: "The name of the model where the application is to be deployed.", - Required: true, + Description: "The name of the model where the application is to be deployed. Changing this value" + + " will cause the application to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), }, @@ -157,8 +159,9 @@ func (r *applicationResource) Schema(_ context.Context, _ resource.SchemaRequest ElementType: types.StringType, }, "constraints": schema.StringAttribute{ - Description: "Constraints imposed on this application.", - Optional: true, + Description: "Constraints imposed on this application. Changing this value will cause the" + + " application to be destroyed and recreated by terraform.", + Optional: true, // Set as "computed" to pre-populate and preserve any implicit constraints Computed: true, PlanModifiers: []planmodifier.String{ @@ -213,9 +216,10 @@ func (r *applicationResource) Schema(_ context.Context, _ resource.SchemaRequest Default: booldefault.StaticBool(false), }, "placement": schema.StringAttribute{ - Description: "Specify the target location for the application's units", - Optional: true, - Computed: true, + Description: "Specify the target location for the application's units. Changing this value" + + " will cause the application to be destroyed and recreated by terraform.", + Optional: true, + Computed: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), stringplanmodifier.UseStateForUnknown(), @@ -267,12 +271,13 @@ func (r *applicationResource) Schema(_ context.Context, _ resource.SchemaRequest }, Blocks: map[string]schema.Block{ CharmKey: schema.ListNestedBlock{ - Description: "The name of the charm to be installed from Charmhub.", + Description: "The charm installed from Charmhub.", NestedObject: schema.NestedBlockObject{ Attributes: map[string]schema.Attribute{ "name": schema.StringAttribute{ - Required: true, - Description: "The name of the charm", + Required: true, + Description: "The name of the charm to be deployed. Changing this value will cause" + + " the application to be destroyed and recreated by terraform.", PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), }, diff --git a/internal/provider/resource_credential.go b/internal/provider/resource_credential.go index cfdc00f5..bf1289ed 100644 --- a/internal/provider/resource_credential.go +++ b/internal/provider/resource_credential.go @@ -71,7 +71,7 @@ func (c *credentialResource) Schema(_ context.Context, _ resource.SchemaRequest, }, }, }, - Description: "JuJu Cloud where the credentials will be used to access", + Description: "Juju Cloud where the credentials will be used to access.", PlanModifiers: []planmodifier.List{ listplanmodifier.RequiresReplace(), }, @@ -88,24 +88,25 @@ func (c *credentialResource) Schema(_ context.Context, _ resource.SchemaRequest, Sensitive: true, }, "auth_type": schema.StringAttribute{ - Description: "Credential authorization type", + Description: "Credential authorization type.", Required: true, }, "client_credential": schema.BoolAttribute{ - Description: "Add credentials to the client", + Description: "Add credentials to the client.", Optional: true, Computed: true, Default: booldefault.StaticBool(false), }, "controller_credential": schema.BoolAttribute{ - Description: "Add credentials to the controller", + Description: "Add credentials to the controller.", Optional: true, Computed: true, Default: booldefault.StaticBool(true), }, "name": schema.StringAttribute{ - Description: "The name to be assigned to the credential", - Required: true, + Description: "The name to be assigned to the credential. Changing this value will cause the" + + " credential to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, diff --git a/internal/provider/resource_machine.go b/internal/provider/resource_machine.go index 2d0005d2..63765984 100644 --- a/internal/provider/resource_machine.go +++ b/internal/provider/resource_machine.go @@ -109,15 +109,18 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, }, }, ModelKey: schema.StringAttribute{ - Description: "The Juju model in which to add a new machine.", - Required: true, + Description: "The Juju model in which to add a new machine. Changing this value will cause the machine" + + " to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, }, ConstraintsKey: schema.StringAttribute{ - Description: "Machine constraints that overwrite those available from 'juju get-model-constraints' and provider's defaults.", - Optional: true, + Description: "Machine constraints that overwrite those available from 'juju get-model-constraints' " + + "and provider's defaults. Changing this value will cause the application to be destroyed and" + + " recreated by terraform.", + Optional: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), }, @@ -128,8 +131,9 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, }, }, DisksKey: schema.StringAttribute{ - Description: "Storage constraints for disks to attach to the machine(s).", - Optional: true, + Description: "Storage constraints for disks to attach to the machine(s). Changing this" + + " value will cause the machine to be destroyed and recreated by terraform.", + Optional: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), }, @@ -140,9 +144,10 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, }, }, BaseKey: schema.StringAttribute{ - Description: "The operating system to install on the new machine(s). E.g. ubuntu@22.04.", - Optional: true, - Computed: true, + Description: "The operating system to install on the new machine(s). E.g. ubuntu@22.04. Changing this" + + " value will cause the machine to be destroyed and recreated by terraform.", + Optional: true, + Computed: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), stringplanmodifier.UseStateForUnknown(), @@ -156,9 +161,10 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, }, }, SeriesKey: schema.StringAttribute{ - Description: "The operating system series to install on the new machine(s).", - Optional: true, - Computed: true, + Description: "The operating system series to install on the new machine(s). Changing this value" + + " will cause the machine to be destroyed and recreated by terraform.", + Optional: true, + Computed: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), stringplanmodifier.UseStateForUnknown(), @@ -169,11 +175,13 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, path.MatchRoot(BaseKey), }...), }, - DeprecationMessage: "Configure base instead. This attribute will be removed in the next major version of the provider.", + DeprecationMessage: "Configure base instead. This attribute will be removed in the next" + + " major version of the provider.", }, PlacementKey: schema.StringAttribute{ - Description: "Additional information about how to allocate the machine in the cloud.", - Optional: true, + Description: "Additional information about how to allocate the machine in the cloud. Changing" + + " this value will cause the application to be destroyed and recreated by terraform.", + Optional: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), stringplanmodifier.UseStateForUnknown(), @@ -192,7 +200,8 @@ func (r *machineResource) Schema(_ context.Context, req resource.SchemaRequest, }, SSHAddressKey: schema.StringAttribute{ Description: "The user@host directive for manual provisioning an existing machine via ssh. " + - "Requires public_key_file & private_key_file arguments.", + "Requires public_key_file & private_key_file arguments. Changing this value will cause the" + + " machine to be destroyed and recreated by terraform.", Optional: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplaceIfConfigured(), diff --git a/internal/provider/resource_model.go b/internal/provider/resource_model.go index ea09f972..16b3025c 100644 --- a/internal/provider/resource_model.go +++ b/internal/provider/resource_model.go @@ -121,7 +121,8 @@ func (r *modelResource) Schema(_ context.Context, _ resource.SchemaRequest, resp }, Blocks: map[string]schema.Block{ "cloud": schema.ListNestedBlock{ - Description: "JuJu Cloud where the model will operate", + Description: "Juju Cloud where the model will operate. Changing this value will cause the" + + " model to be destroyed and recreated by terraform.", PlanModifiers: []planmodifier.List{ listplanmodifier.RequiresReplace(), }, diff --git a/internal/provider/resource_offer.go b/internal/provider/resource_offer.go index d25c6fbb..34dc822e 100644 --- a/internal/provider/resource_offer.go +++ b/internal/provider/resource_offer.go @@ -56,16 +56,18 @@ func (o *offerResource) Schema(_ context.Context, req resource.SchemaRequest, re Description: "A resource that represent a Juju Offer.", Attributes: map[string]schema.Attribute{ "model": schema.StringAttribute{ - Description: "The name of the model to operate in.", - Required: true, + Description: "The name of the model to operate in. Changing this value will cause the" + + " offer to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, }, "name": schema.StringAttribute{ - Description: "The name of the offer.", - Optional: true, - Computed: true, + Description: "The name of the offer. Changing this value will cause the offer" + + " to be destroyed and recreated by terraform.", + Optional: true, + Computed: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), stringplanmodifier.RequiresReplaceIfConfigured(), @@ -73,15 +75,17 @@ func (o *offerResource) Schema(_ context.Context, req resource.SchemaRequest, re }, }, "application_name": schema.StringAttribute{ - Description: "The name of the application.", - Required: true, + Description: "The name of the application. Changing this value will cause the offer" + + " to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, }, "endpoint": schema.StringAttribute{ - Description: "The endpoint name.", - Required: true, + Description: "The endpoint name. Changing this value will cause the offer" + + " to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, diff --git a/internal/provider/resource_secret.go b/internal/provider/resource_secret.go index f82d2c2d..7e64121f 100644 --- a/internal/provider/resource_secret.go +++ b/internal/provider/resource_secret.go @@ -113,8 +113,9 @@ func (s *secretResource) Schema(_ context.Context, req resource.SchemaRequest, r Description: "A resource that represents a Juju secret.", Attributes: map[string]schema.Attribute{ "model": schema.StringAttribute{ - Description: "The model in which the secret belongs.", - Required: true, + Description: "The model in which the secret belongs. Changing this value will cause the secret" + + " to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, diff --git a/internal/provider/resource_user.go b/internal/provider/resource_user.go index 95b2dc2a..5ff97be8 100644 --- a/internal/provider/resource_user.go +++ b/internal/provider/resource_user.go @@ -73,18 +73,19 @@ func (r *userResource) Schema(ctx context.Context, req resource.SchemaRequest, r // terraform method to say the items are immutable. // Juju has no way to update a username today. "name": schema.StringAttribute{ - Description: "The name to be assigned to the user", - Required: true, + Description: "The username to be assigned to the user. Changing this value will cause the" + + " user to be destroyed and recreated by terraform.", + Required: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.RequiresReplace(), }, }, "display_name": schema.StringAttribute{ - Description: "The display name to be assigned to the user (optional)", + Description: "The display name to be assigned to the user (optional).", Optional: true, }, "password": schema.StringAttribute{ - Description: "The password to be assigned to the user", + Description: "The password to be assigned to the user.", Required: true, Sensitive: true, }, From a31d1229d704f550793a40b591a2713ee32eb942 Mon Sep 17 00:00:00 2001 From: Heather Lanigan Date: Wed, 23 Oct 2024 12:08:38 +0000 Subject: [PATCH 2/3] docs: update offer_url use in integration resource Per #449, indicate that offer_url and name/endpoint are mutually exclusive in an integration resource. --- docs/resources/integration.md | 12 ++++---- docs/resources/offer.md | 9 +++--- examples/resources/juju_offer/resource.tf | 9 +++--- internal/provider/resource_integration.go | 34 ++++++++++++++++++----- templates/resources/integration.md.tmpl | 6 ++-- 5 files changed, 46 insertions(+), 24 deletions(-) diff --git a/docs/resources/integration.md b/docs/resources/integration.md index 4632e927..1a4b57a8 100644 --- a/docs/resources/integration.md +++ b/docs/resources/integration.md @@ -68,13 +68,14 @@ resource "juju_integration" "this" { Optional: -- `endpoint` (String) The endpoint name. -- `name` (String) The name of the application. -- `offer_url` (String) The URL of a remote application. +- `endpoint` (String) The endpoint name. This attribute may not be used at the same time as the offer_url. +- `name` (String) The name of the application. This attribute may not be used at the same time as the offer_url. +- `offer_url` (String) The URL of a remote application. This attribute may not be used at the same time as name and endpoint. ### Notes -When creating this resource the `offer_url` property will show `(known after apply)` as below: +When creating this resource the `offer_url` property will show `(known after apply)` if a `name` or + `name` and `endpoint` are supplied as below: ``` + resource "juju_integration" "this" { + id = (known after apply) @@ -88,7 +89,8 @@ When creating this resource the `offer_url` property will show `(known after app } } ``` -This is due to a bug in the sdk this provider uses - this property will never be computed and can only be provided by the user. +This is due to an integration requiring a name/endpoint combination or an offer_url, but not both +bits of data together. ## Import diff --git a/docs/resources/offer.md b/docs/resources/offer.md index a145fefd..02c94610 100644 --- a/docs/resources/offer.md +++ b/docs/resources/offer.md @@ -13,23 +13,22 @@ A resource that represent a Juju Offer. ## Example Usage ```terraform -resource "juju_offer" "this" { +resource "juju_offer" "myoffer" { model = juju_model.development.name application_name = juju_application.percona-cluster.name endpoint = server } -// an offer can then be used in an integration as below: -resource "juju_integration" "this" { +// an offer can then be used in an cross model integration as below: +resource "juju_integration" "myintegration" { model = juju_model.development-destination.name application { name = juju_application.wordpress.name endpoint = "db" } - application { - offer_url = juju_offer.this.url + offer_url = juju_offer.myoffer.url } } ``` diff --git a/examples/resources/juju_offer/resource.tf b/examples/resources/juju_offer/resource.tf index 84e714a5..a7be5728 100644 --- a/examples/resources/juju_offer/resource.tf +++ b/examples/resources/juju_offer/resource.tf @@ -1,19 +1,18 @@ -resource "juju_offer" "this" { +resource "juju_offer" "myoffer" { model = juju_model.development.name application_name = juju_application.percona-cluster.name endpoint = server } -// an offer can then be used in an integration as below: -resource "juju_integration" "this" { +// an offer can then be used in an cross model integration as below: +resource "juju_integration" "myintegration" { model = juju_model.development-destination.name application { name = juju_application.wordpress.name endpoint = "db" } - application { - offer_url = juju_offer.this.url + offer_url = juju_offer.myoffer.url } } diff --git a/internal/provider/resource_integration.go b/internal/provider/resource_integration.go index 99e23881..70587a23 100644 --- a/internal/provider/resource_integration.go +++ b/internal/provider/resource_integration.go @@ -10,6 +10,7 @@ import ( "strings" "github.com/hashicorp/terraform-plugin-framework-validators/setvalidator" + "github.com/hashicorp/terraform-plugin-framework-validators/stringvalidator" "github.com/hashicorp/terraform-plugin-framework/diag" "github.com/hashicorp/terraform-plugin-framework/path" "github.com/hashicorp/terraform-plugin-framework/resource" @@ -138,20 +139,39 @@ func (r *integrationResource) Schema(_ context.Context, _ resource.SchemaRequest NestedObject: schema.NestedBlockObject{ Attributes: map[string]schema.Attribute{ "name": schema.StringAttribute{ - Description: "The name of the application.", - Optional: true, + Description: "The name of the application. This attribute may not be used at the" + + " same time as the offer_url.", + Optional: true, + Validators: []validator.String{ + stringvalidator.ConflictsWith(path.Expressions{ + path.MatchRelative().AtParent().AtName("offer_url"), + }...), + }, }, "endpoint": schema.StringAttribute{ - Description: "The endpoint name.", - Optional: true, - Computed: true, + Description: "The endpoint name. This attribute may not be used at the" + + " same time as the offer_url.", + Optional: true, + Computed: true, + Validators: []validator.String{ + stringvalidator.ConflictsWith(path.Expressions{ + path.MatchRelative().AtParent().AtName("offer_url"), + }...), + }, }, "offer_url": schema.StringAttribute{ - Description: "The URL of a remote application.", - Optional: true, + Description: "The URL of a remote application. This attribute may not be used at the" + + " same time as name and endpoint.", + Optional: true, PlanModifiers: []planmodifier.String{ stringplanmodifier.UseStateForUnknown(), }, + Validators: []validator.String{ + stringvalidator.ConflictsWith(path.Expressions{ + path.MatchRelative().AtParent().AtName("name"), + path.MatchRelative().AtParent().AtName("endpoint"), + }...), + }, }, }, }, diff --git a/templates/resources/integration.md.tmpl b/templates/resources/integration.md.tmpl index bfea91e6..b422bafb 100644 --- a/templates/resources/integration.md.tmpl +++ b/templates/resources/integration.md.tmpl @@ -19,7 +19,8 @@ description: |- ### Notes -When creating this resource the `offer_url` property will show `(known after apply)` as below: +When creating this resource the `offer_url` property will show `(known after apply)` if a `name` or + `name` and `endpoint` are supplied as below: ``` + resource "juju_integration" "this" { + id = (known after apply) @@ -33,7 +34,8 @@ When creating this resource the `offer_url` property will show `(known after app } } ``` -This is due to a bug in the sdk this provider uses - this property will never be computed and can only be provided by the user. +This is due to an integration requiring a name/endpoint combination or an offer_url, but not both +bits of data together. {{ if .HasImport -}} ## Import From bef5faf1366356b50a21061bacfd417fec1dbfad Mon Sep 17 00:00:00 2001 From: Heather Lanigan Date: Wed, 23 Oct 2024 12:24:03 +0000 Subject: [PATCH 3/3] docs: add warning to application template for config Requested in GH issue #393. --- docs/resources/application.md | 9 +++++-- templates/resources/application.md.tmpl | 32 +++++++++++++++++++++++++ 2 files changed, 39 insertions(+), 2 deletions(-) create mode 100644 templates/resources/application.md.tmpl diff --git a/docs/resources/application.md b/docs/resources/application.md index 8e91204f..07c19244 100644 --- a/docs/resources/application.md +++ b/docs/resources/application.md @@ -1,5 +1,5 @@ --- -# generated by https://github.com/hashicorp/terraform-plugin-docs +# generated using template templates/resources/application.md.tmpl page_title: "juju_application Resource - terraform-provider-juju" subcategory: "" description: |- @@ -11,7 +11,6 @@ description: |- A resource that represents a single Juju application deployment from a charm. Deployment of bundles is not supported. ## Example Usage - ```terraform resource "juju_application" "this" { name = "my-application" @@ -124,6 +123,12 @@ Read-Only: - `pool` (String) Name of the storage pool. - `size` (String) The size of each volume. + +### Notes + +Removing the config map will not reset the charm config to defaults per [GH issue #393](https://github.com/juju/terraform-provider-juju/issues/393) + + ## Import Import is supported using the following syntax: diff --git a/templates/resources/application.md.tmpl b/templates/resources/application.md.tmpl new file mode 100644 index 00000000..c9e6c0e1 --- /dev/null +++ b/templates/resources/application.md.tmpl @@ -0,0 +1,32 @@ +--- +# generated using template templates/resources/application.md.tmpl +page_title: "{{.Name}} {{.Type}} - {{.ProviderName}}" +subcategory: "" +description: |- +{{ .Description | plainmarkdown | trimspace | prefixlines " " }} +--- + +# {{.Name}} ({{.Type}}) + +{{ .Description | trimspace }} + +{{ if .HasExample -}} +## Example Usage +{{tffile "examples/resources/juju_application/resource.tf"}} +{{- end }} + +{{ .SchemaMarkdown | trimspace }} + + +### Notes + +Removing the config map will not reset the charm config to defaults per [GH issue #393](https://github.com/juju/terraform-provider-juju/issues/393) + + +{{ if .HasImport -}} +## Import + +Import is supported using the following syntax: + +{{codefile "shell" "examples/resources/juju_application/import.sh"}} +{{- end }}