Skip to content

Commit

Permalink
feat: Adds StreamConfig attribute to mongodbatlas_stream_instance r…
Browse files Browse the repository at this point in the history
…esource and datasources (#1989)

* add new attribute to resource

* wip: fix nil

* fix existing tests

* remove unnecessary parameters

* add tests for config with stream_config

* separate stream_config.tier to avoid breaking migration test

* add stream config in data source

* unit tests

* add documentation

* typo

* update example

* use new
  • Loading branch information
oarbusi authored Mar 8, 2024
1 parent f899b80 commit a1cc2a4
Show file tree
Hide file tree
Showing 12 changed files with 172 additions and 8 deletions.
5 changes: 4 additions & 1 deletion examples/mongodbatlas_stream_instance/main.tf
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,7 @@ resource "mongodbatlas_stream_instance" "example" {
region = "VIRGINIA_USA"
cloud_provider = "AWS"
}
}
stream_config = {
tier = "SP30"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,14 @@ func DSAttributes(withArguments bool) map[string]schema.Attribute {
ElementType: types.StringType,
Computed: true,
},
"stream_config": schema.SingleNestedAttribute{
Computed: true,
Attributes: map[string]schema.Attribute{
"tier": schema.StringAttribute{
Computed: true,
},
},
},
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,10 @@ func TestAccStreamDSStreamInstance_basic(t *testing.T) {
Steps: []resource.TestStep{
{
Config: streamInstanceDataSourceConfig(orgID, projectName, instanceName, region, cloudProvider),
Check: streamInstanceAttributeChecks(dataSourceName, orgID, projectName, instanceName, region, cloudProvider),
Check: resource.ComposeTestCheckFunc(
streamInstanceAttributeChecks(dataSourceName, instanceName, region, cloudProvider),
resource.TestCheckResourceAttr(dataSourceName, "stream_config.tier", "SP30"),
),
},
},
})
Expand Down
24 changes: 22 additions & 2 deletions internal/service/streaminstance/model_stream_instance.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,14 +16,24 @@ func NewStreamInstanceCreateReq(ctx context.Context, plan *TFStreamInstanceModel
if diags := plan.DataProcessRegion.As(ctx, dataProcessRegion, basetypes.ObjectAsOptions{}); diags.HasError() {
return nil, diags
}
return &admin.StreamsTenant{
streamTenant := &admin.StreamsTenant{
GroupId: plan.ProjectID.ValueStringPointer(),
Name: plan.InstanceName.ValueStringPointer(),
DataProcessRegion: &admin.StreamsDataProcessRegion{
CloudProvider: dataProcessRegion.CloudProvider.ValueString(),
Region: dataProcessRegion.Region.ValueString(),
},
}, nil
}
if !plan.StreamConfig.IsNull() && !plan.StreamConfig.IsUnknown() {
streamConfig := new(TFInstanceStreamConfigSpecModel)
if diags := plan.StreamConfig.As(ctx, streamConfig, basetypes.ObjectAsOptions{}); diags.HasError() {
return nil, diags
}
streamTenant.StreamConfig = &admin.StreamConfig{
Tier: streamConfig.Tier.ValueStringPointer(),
}
}
return streamTenant, nil
}

func NewStreamInstanceUpdateReq(ctx context.Context, plan *TFStreamInstanceModel) (*admin.StreamsDataProcessRegion, diag.Diagnostics) {
Expand All @@ -49,6 +59,15 @@ func NewTFStreamInstance(ctx context.Context, apiResp *admin.StreamsTenant) (*TF
dataProcessRegion = returnedProcessRegion
diags.Append(diagsProcessRegion...)
}
var streamConfig = types.ObjectNull(StreamConfigObjectType.AttrTypes)
apiStreamConfig := apiResp.StreamConfig
if apiStreamConfig != nil && apiStreamConfig.Tier != nil {
returnedStreamConfig, diagsStreamConfig := types.ObjectValueFrom(ctx, StreamConfigObjectType.AttrTypes, TFInstanceStreamConfigSpecModel{
Tier: types.StringPointerValue(apiStreamConfig.Tier),
})
streamConfig = returnedStreamConfig
diags.Append(diagsStreamConfig...)
}
if diags.HasError() {
return nil, diags
}
Expand All @@ -58,6 +77,7 @@ func NewTFStreamInstance(ctx context.Context, apiResp *admin.StreamsTenant) (*TF
InstanceName: types.StringPointerValue(apiResp.Name),
ProjectID: types.StringPointerValue(apiResp.GroupId),
DataProcessRegion: dataProcessRegion,
StreamConfig: streamConfig,
Hostnames: hostnames,
}, nil
}
Expand Down
43 changes: 42 additions & 1 deletion internal/service/streaminstance/model_stream_instance_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ const (
cloudProvider = "AWS"
region = "VIRGINIA_USA"
instanceName = "InstanceName"
tier = "SP30"
)

var hostnames = &[]string{"atlas-stream.virginia-usa.a.query.mongodb-dev.net"}
Expand All @@ -36,6 +37,9 @@ func TestStreamInstanceSDKToTFModel(t *testing.T) {
CloudProvider: cloudProvider,
Region: region,
},
StreamConfig: &admin.StreamConfig{
Tier: admin.PtrString(tier),
},
GroupId: admin.PtrString(dummyProjectID),
Hostnames: hostnames,
Name: admin.PtrString(instanceName),
Expand All @@ -46,10 +50,11 @@ func TestStreamInstanceSDKToTFModel(t *testing.T) {
ProjectID: types.StringValue(dummyProjectID),
Hostnames: tfHostnamesList(t, hostnames),
InstanceName: types.StringValue(instanceName),
StreamConfig: tfStreamConfigObject(t, tier),
},
},
{
name: "Empty hostnames and dataProcessRegion in response", // should never happen, but verifying it is handled gracefully
name: "Empty hostnames, streamConfig and dataProcessRegion in response", // should never happen, but verifying it is handled gracefully
SDKResp: &admin.StreamsTenant{
Id: admin.PtrString(dummyStreamInstanceID),
GroupId: admin.PtrString(dummyProjectID),
Expand All @@ -61,6 +66,7 @@ func TestStreamInstanceSDKToTFModel(t *testing.T) {
ProjectID: types.StringValue(dummyProjectID),
Hostnames: types.ListNull(types.StringType),
InstanceName: types.StringValue(instanceName),
StreamConfig: types.ObjectNull(streaminstance.StreamConfigObjectType.AttrTypes),
},
},
}
Expand Down Expand Up @@ -100,6 +106,9 @@ func TestStreamInstancesSDKToTFModel(t *testing.T) {
GroupId: admin.PtrString(dummyProjectID),
Hostnames: hostnames,
Name: admin.PtrString(instanceName),
StreamConfig: &admin.StreamConfig{
Tier: admin.PtrString(tier),
},
},
},
TotalCount: admin.PtrInt(1),
Expand All @@ -121,6 +130,7 @@ func TestStreamInstancesSDKToTFModel(t *testing.T) {
ProjectID: types.StringValue(dummyProjectID),
Hostnames: tfHostnamesList(t, hostnames),
InstanceName: types.StringValue(instanceName),
StreamConfig: tfStreamConfigObject(t, tier),
},
},
},
Expand Down Expand Up @@ -168,6 +178,26 @@ func TestStreamInstanceTFToSDKCreateModel(t *testing.T) {
testCases := []tfToSDKCreateModelTestCase{
{
name: "Complete TF state",
tfModel: &streaminstance.TFStreamInstanceModel{
DataProcessRegion: tfRegionObject(t, cloudProvider, region),
ProjectID: types.StringValue(dummyProjectID),
InstanceName: types.StringValue(instanceName),
StreamConfig: tfStreamConfigObject(t, tier),
},
expectedSDKReq: &admin.StreamsTenant{
DataProcessRegion: &admin.StreamsDataProcessRegion{
CloudProvider: cloudProvider,
Region: region,
},
GroupId: admin.PtrString(dummyProjectID),
Name: admin.PtrString(instanceName),
StreamConfig: &admin.StreamConfig{
Tier: admin.PtrString(tier),
},
},
},
{
name: "TF State without StreamConfig",
tfModel: &streaminstance.TFStreamInstanceModel{
DataProcessRegion: tfRegionObject(t, cloudProvider, region),
ProjectID: types.StringValue(dummyProjectID),
Expand Down Expand Up @@ -246,6 +276,17 @@ func tfRegionObject(t *testing.T, cloudProvider, region string) types.Object {
return dataProcessRegion
}

func tfStreamConfigObject(t *testing.T, tier string) types.Object {
t.Helper()
streamConfig, diags := types.ObjectValueFrom(context.Background(), streaminstance.StreamConfigObjectType.AttrTypes, streaminstance.TFInstanceStreamConfigSpecModel{
Tier: types.StringValue(tier),
})
if diags.HasError() {
t.Errorf("failed to create terraform data process region model: %s", diags.Errors()[0].Summary())
}
return streamConfig
}

func tfHostnamesList(t *testing.T, hostnames *[]string) types.List {
t.Helper()
resultList, diags := types.ListValueFrom(context.Background(), types.StringType, hostnames)
Expand Down
19 changes: 19 additions & 0 deletions internal/service/streaminstance/resource_stream_instance.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ type TFStreamInstanceModel struct {
InstanceName types.String `tfsdk:"instance_name"`
ProjectID types.String `tfsdk:"project_id"`
DataProcessRegion types.Object `tfsdk:"data_process_region"`
StreamConfig types.Object `tfsdk:"stream_config"`
Hostnames types.List `tfsdk:"hostnames"`
}

Expand All @@ -45,11 +46,19 @@ type TFInstanceProcessRegionSpecModel struct {
Region types.String `tfsdk:"region"`
}

type TFInstanceStreamConfigSpecModel struct {
Tier types.String `tfsdk:"tier"`
}

var ProcessRegionObjectType = types.ObjectType{AttrTypes: map[string]attr.Type{
"cloud_provider": types.StringType,
"region": types.StringType,
}}

var StreamConfigObjectType = types.ObjectType{AttrTypes: map[string]attr.Type{
"tier": types.StringType,
}}

func (r *streamInstanceRS) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) {
resp.Schema = schema.Schema{
Attributes: map[string]schema.Attribute{
Expand Down Expand Up @@ -83,6 +92,16 @@ func (r *streamInstanceRS) Schema(ctx context.Context, req resource.SchemaReques
ElementType: types.StringType,
Computed: true,
},
"stream_config": schema.SingleNestedAttribute{
Optional: true,
Computed: true,
Attributes: map[string]schema.Attribute{
"tier": schema.StringAttribute{
Optional: true,
Computed: true,
},
},
},
},
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ func TestAccMigrationStreamRSStreamInstance_basic(t *testing.T) {
{
ExternalProviders: mig.ExternalProviders(),
Config: acc.StreamInstanceConfig(orgID, projectName, instanceName, region, cloudProvider),
Check: streamInstanceAttributeChecks(resourceName, orgID, projectName, instanceName, region, cloudProvider),
Check: streamInstanceAttributeChecks(resourceName, instanceName, region, cloudProvider),
},
{
ProtoV6ProviderFactories: acc.TestAccProviderV6Factories,
Expand Down
36 changes: 34 additions & 2 deletions internal/service/streaminstance/resource_stream_instance_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,10 @@ func TestAccStreamRSStreamInstance_basic(t *testing.T) {
Steps: []resource.TestStep{
{
Config: acc.StreamInstanceConfig(orgID, projectName, instanceName, region, cloudProvider), // as of now there are no values that can be updated because only one region is supported
Check: streamInstanceAttributeChecks(resourceName, orgID, projectName, instanceName, region, cloudProvider),
Check: resource.ComposeTestCheckFunc(
streamInstanceAttributeChecks(resourceName, instanceName, region, cloudProvider),
resource.TestCheckResourceAttr(resourceName, "stream_config.tier", "SP30"),
),
},
{
ResourceName: resourceName,
Expand All @@ -37,7 +40,36 @@ func TestAccStreamRSStreamInstance_basic(t *testing.T) {
})
}

func streamInstanceAttributeChecks(resourceName, orgID, projectName, instanceName, region, cloudProvider string) resource.TestCheckFunc {
func TestAccStreamRSStreamInstance_withStreamConfig(t *testing.T) {
var (
resourceName = "mongodbatlas_stream_instance.test"
orgID = os.Getenv("MONGODB_ATLAS_ORG_ID")
projectName = acc.RandomProjectName()
instanceName = acc.RandomName()
)
resource.ParallelTest(t, resource.TestCase{
PreCheck: func() { acc.PreCheckBetaFlag(t); acc.PreCheckBasic(t) },
ProtoV6ProviderFactories: acc.TestAccProviderV6Factories,
CheckDestroy: acc.CheckDestroyStreamInstance,
Steps: []resource.TestStep{
{
Config: acc.StreamInstanceWithStreamConfigConfig(orgID, projectName, instanceName, region, cloudProvider), // as of now there are no values that can be updated because only one region is supported
Check: resource.ComposeTestCheckFunc(
streamInstanceAttributeChecks(resourceName, instanceName, region, cloudProvider),
resource.TestCheckResourceAttr(resourceName, "stream_config.tier", "SP30"),
),
},
{
ResourceName: resourceName,
ImportStateIdFunc: checkStreamInstanceImportStateIDFunc(resourceName),
ImportState: true,
ImportStateVerify: true,
},
},
})
}

func streamInstanceAttributeChecks(resourceName, instanceName, region, cloudProvider string) resource.TestCheckFunc {
resourceChecks := []resource.TestCheckFunc{
checkSearchInstanceExists(),
resource.TestCheckResourceAttrSet(resourceName, "id"),
Expand Down
21 changes: 21 additions & 0 deletions internal/testutil/acc/stream_instance.go
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,27 @@ func StreamInstanceConfig(orgID, projectName, instanceName, region, cloudProvide
`, orgID, projectName, instanceName, region, cloudProvider)
}

func StreamInstanceWithStreamConfigConfig(orgID, projectName, instanceName, region, cloudProvider string) string {
return fmt.Sprintf(`
resource "mongodbatlas_project" "test" {
org_id = %[1]q
name = %[2]q
}
resource "mongodbatlas_stream_instance" "test" {
project_id = mongodbatlas_project.test.id
instance_name = %[3]q
data_process_region = {
region = %[4]q
cloud_provider = %[5]q
}
stream_config = {
tier = "SP30"
}
}
`, orgID, projectName, instanceName, region, cloudProvider)
}

func CheckDestroyStreamInstance(state *terraform.State) error {
if projectDestroyedErr := CheckDestroyProject(state); projectDestroyedErr != nil {
return projectDestroyedErr
Expand Down
5 changes: 5 additions & 0 deletions website/docs/d/stream_instance.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,17 @@ data "mongodbatlas_stream_instance" "example" {

* `data_process_region` - Defines the cloud service provider and region where MongoDB Cloud performs stream processing. See [data process region](#data-process-region).
* `hostnames` - List that contains the hostnames assigned to the stream instance.
* `stream_config` - Defines the configuration options for an Atlas Stream Processing Instance. See [stream config](#stream-config)


### Data Process Region

* `cloud_provider` - Label that identifies the cloud service provider where MongoDB Cloud performs stream processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.
* `region` - Name of the cloud provider region hosting Atlas Stream Processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.

### Stream Config

* `tier` - Selected tier for the Stream Instance. Configures Memory / VCPU allowances. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.

To learn more, see: [MongoDB Atlas API - Stream Instance](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) Documentation.
The [Terraform Provider Examples Section](https://github.com/mongodb/terraform-provider-mongodbatlas/blob/master/examples/mongodbatlas_stream_instance/atlas-streams-user-journey.md) also contains details on the overall support for Atlas Streams Processing in Terraform.
5 changes: 5 additions & 0 deletions website/docs/d/stream_instances.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -41,11 +41,16 @@ In addition to all arguments above, it also exports the following attributes:
* `instance_name` - Human-readable label that identifies the stream instance.
* `data_process_region` - Defines the cloud service provider and region where MongoDB Cloud performs stream processing. See [data process region](#data-process-region).
* `hostnames` - List that contains the hostnames assigned to the stream instance.
* `stream_config` - Defines the configuration options for an Atlas Stream Processing Instance. See [stream config](#stream-config)

### Data Process Region

* `cloud_provider` - Label that identifies the cloud service provider where MongoDB Cloud performs stream processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.
* `region` - Name of the cloud provider region hosting Atlas Stream Processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.

### Stream Config

* `tier` - Selected tier for the Stream Instance. Configures Memory / VCPU allowances. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.

To learn more, see: [MongoDB Atlas API - Stream Instance](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) Documentation.
The [Terraform Provider Examples Section](https://github.com/mongodb/terraform-provider-mongodbatlas/blob/master/examples/mongodbatlas_stream_instance/atlas-streams-user-journey.md) also contains details on the overall support for Atlas Streams Processing in Terraform.
7 changes: 7 additions & 0 deletions website/docs/r/stream_instance.html.markdown
Original file line number Diff line number Diff line change
Expand Up @@ -30,12 +30,19 @@ resource "mongodbatlas_stream_instance" "test" {
* `project_id` - (Required) Unique 24-hexadecimal digit string that identifies your project.
* `instance_name` - (Required) Human-readable label that identifies the stream instance.
* `data_process_region` - (Required) Cloud service provider and region where MongoDB Cloud performs stream processing. See [data process region](#data-process-region).
* `stream_config` - (Optional) Configuration options for an Atlas Stream Processing Instance. See [stream config](#stream-config)


### Data Process Region

* `cloud_provider` - (Required) Label that identifies the cloud service provider where MongoDB Cloud performs stream processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.
* `region` - (Required) Name of the cloud provider region hosting Atlas Stream Processing. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.

### Stream Config

* `tier` - (Required) Selected tier for the Stream Instance. Configures Memory / VCPU allowances. The [MongoDB Atlas API](https://www.mongodb.com/docs/atlas/reference/api-resources-spec/#tag/Streams/operation/createStreamInstance) describes the valid values.


## Attributes Reference

In addition to all arguments above, the following attributes are exported:
Expand Down

0 comments on commit a1cc2a4

Please sign in to comment.