Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 35 additions & 0 deletions docs/data-sources/iaas_project.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
---
# generated by https://github.com/hashicorp/terraform-plugin-docs
page_title: "stackit_iaas_project Data Source - stackit"
subcategory: ""
description: |-
Project details. Must have a region specified in the provider configuration.
---

# stackit_iaas_project (Data Source)

Project details. Must have a `region` specified in the provider configuration.

## Example Usage

```terraform
data "stackit_iaas_project" "example" {
project_id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
}
```

<!-- schema generated by tfplugindocs -->
## Schema

### Required

- `project_id` (String) STACKIT project ID.

### Read-Only

- `area_id` (String) The area ID to which the project belongs to.
- `created_at` (String) Date-time when the project was created.
- `id` (String) Terraform's internal resource ID. It is structured as "`project_id`".
- `internet_access` (Boolean) Specifies if the project has internet_access
- `state` (String) Specifies the state of the project.
- `updated_at` (String) Date-time when the project was last updated.
3 changes: 3 additions & 0 deletions examples/data-sources/stackit_iaas_project/data-source.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
data "stackit_iaas_project" "example" {
project_id = "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
}
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ require (
github.com/stackitcloud/stackit-sdk-go/services/cdn v1.4.0
github.com/stackitcloud/stackit-sdk-go/services/dns v0.17.1
github.com/stackitcloud/stackit-sdk-go/services/git v0.7.1
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.0
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.1
github.com/stackitcloud/stackit-sdk-go/services/iaasalpha v0.1.21-alpha
github.com/stackitcloud/stackit-sdk-go/services/loadbalancer v1.5.1
github.com/stackitcloud/stackit-sdk-go/services/logme v0.25.1
Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -160,8 +160,8 @@ github.com/stackitcloud/stackit-sdk-go/services/dns v0.17.1 h1:CnhAMLql0MNmAeq4r
github.com/stackitcloud/stackit-sdk-go/services/dns v0.17.1/go.mod h1:7Bx85knfNSBxulPdJUFuBePXNee3cO+sOTYnUG6M+iQ=
github.com/stackitcloud/stackit-sdk-go/services/git v0.7.1 h1:hkFixFnBcQzU4BSIZFITc8N0gK0pUYk7mk0wdUu5Ki8=
github.com/stackitcloud/stackit-sdk-go/services/git v0.7.1/go.mod h1:Ng1EzrRndG3iGXGH90AZJz//wfK+2YOyDwTnTLwX3a4=
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.0 h1:j4FKFOVkcTot8xNxpvDsPzIFyjADE4GxXF0rFE6/Uo4=
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.0/go.mod h1:b/jgJf7QHdRzU2fmZeJJtu5j0TAevDRghzcn5MyRmOI=
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.1 h1:GfE+FaeIKSVaKvgzh8Eacum+bQVyRS6ngltkh0qNGtM=
github.com/stackitcloud/stackit-sdk-go/services/iaas v0.29.1/go.mod h1:b/jgJf7QHdRzU2fmZeJJtu5j0TAevDRghzcn5MyRmOI=
github.com/stackitcloud/stackit-sdk-go/services/iaasalpha v0.1.21-alpha h1:m1jq6a8dbUe+suFuUNdHmM/cSehpGLUtDbK1CqLqydg=
github.com/stackitcloud/stackit-sdk-go/services/iaasalpha v0.1.21-alpha/go.mod h1:Nu1b5Phsv8plgZ51+fkxPVsU91ZJ5Ayz+cthilxdmQ8=
github.com/stackitcloud/stackit-sdk-go/services/loadbalancer v1.5.1 h1:OdJEs8eOfrzn9tCBDLxIyP8hX50zPfcXNYnRoQX+chs=
Expand Down
32 changes: 32 additions & 0 deletions stackit/internal/services/iaas/iaas_acc_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4022,6 +4022,38 @@ func TestAccImageMax(t *testing.T) {
})
}

func TestAccProject(t *testing.T) {
projectId := testutil.ProjectId
resource.ParallelTest(t, resource.TestCase{
ProtoV6ProviderFactories: testutil.TestAccProtoV6ProviderFactories,
Steps: []resource.TestStep{
// Data source
{
ConfigVariables: testConfigKeyPairMin,
Config: fmt.Sprintf(`
%s

data "stackit_iaas_project" "project" {
project_id = %q
}
`,
testutil.IaaSProviderConfig(), testutil.ProjectId,
),
Check: resource.ComposeAggregateTestCheckFunc(
// Instance
resource.TestCheckResourceAttr("data.stackit_iaas_project.project", "project_id", projectId),
resource.TestCheckResourceAttr("data.stackit_iaas_project.project", "id", projectId),
resource.TestCheckResourceAttrSet("data.stackit_iaas_project.project", "area_id"),
resource.TestCheckResourceAttrSet("data.stackit_iaas_project.project", "internet_access"),
resource.TestCheckResourceAttrSet("data.stackit_iaas_project.project", "state"),
resource.TestCheckResourceAttrSet("data.stackit_iaas_project.project", "created_at"),
resource.TestCheckResourceAttrSet("data.stackit_iaas_project.project", "updated_at"),
),
},
},
})
}

func testAccCheckDestroy(s *terraform.State) error {
checkFunctions := []func(s *terraform.State) error{
testAccCheckNetworkV1Destroy,
Expand Down
204 changes: 204 additions & 0 deletions stackit/internal/services/iaas/project/datasource.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,204 @@
package project

import (
"context"
"fmt"
"time"

"github.com/hashicorp/terraform-plugin-framework/datasource"
"github.com/hashicorp/terraform-plugin-framework/datasource/schema"
"github.com/hashicorp/terraform-plugin-framework/schema/validator"
"github.com/hashicorp/terraform-plugin-framework/types"
"github.com/hashicorp/terraform-plugin-framework/types/basetypes"
"github.com/hashicorp/terraform-plugin-log/tflog"
"github.com/stackitcloud/stackit-sdk-go/services/iaas"
"github.com/stackitcloud/terraform-provider-stackit/stackit/internal/conversion"
"github.com/stackitcloud/terraform-provider-stackit/stackit/internal/core"
iaasUtils "github.com/stackitcloud/terraform-provider-stackit/stackit/internal/services/iaas/utils"
"github.com/stackitcloud/terraform-provider-stackit/stackit/internal/utils"
"github.com/stackitcloud/terraform-provider-stackit/stackit/internal/validate"
)

var (
_ datasource.DataSourceWithConfigure = &projectDataSource{}
)

type DatasourceModel struct {
Id types.String `tfsdk:"id"` // needed by TF
ProjectId types.String `tfsdk:"project_id"`
AreaId types.String `tfsdk:"area_id"`
InternetAccess types.Bool `tfsdk:"internet_access"`
State types.String `tfsdk:"state"`
CreatedAt types.String `tfsdk:"created_at"`
UpdatedAt types.String `tfsdk:"updated_at"`
}

// NewProjectDataSource is a helper function to simplify the provider implementation.
func NewProjectDataSource() datasource.DataSource {
return &projectDataSource{}
}

// projectDatasource is the data source implementation.
type projectDataSource struct {
client *iaas.APIClient
}

func (d *projectDataSource) Configure(ctx context.Context, req datasource.ConfigureRequest, resp *datasource.ConfigureResponse) {
providerData, ok := conversion.ParseProviderData(ctx, req.ProviderData, &resp.Diagnostics)
if !ok {
return
}

apiClient := iaasUtils.ConfigureClient(ctx, &providerData, &resp.Diagnostics)
if resp.Diagnostics.HasError() {
return
}
d.client = apiClient
tflog.Info(ctx, "iaas client configured")
}

// Metadata returns the data source type name.
func (d *projectDataSource) Metadata(_ context.Context, req datasource.MetadataRequest, resp *datasource.MetadataResponse) {
resp.TypeName = req.ProviderTypeName + "_iaas_project"
}

// Schema defines the schema for the datasource.
func (d *projectDataSource) Schema(_ context.Context, _ datasource.SchemaRequest, resp *datasource.SchemaResponse) {
descriptions := map[string]string{
"main": "Project details. Must have a `region` specified in the provider configuration.",
"id": "Terraform's internal resource ID. It is structured as \"`project_id`\".",
"project_id": "STACKIT project ID.",
"area_id": "The area ID to which the project belongs to.",
"internet_access": "Specifies if the project has internet_access",
"state": "Specifies the state of the project.",
"created_at": "Date-time when the project was created.",
"updated_at": "Date-time when the project was last updated.",
}
resp.Schema = schema.Schema{
MarkdownDescription: descriptions["main"],
Description: descriptions["main"],
Attributes: map[string]schema.Attribute{
"id": schema.StringAttribute{
Description: descriptions["id"],
Computed: true,
},
"project_id": schema.StringAttribute{
Description: descriptions["project_id"],
Required: true,
Validators: []validator.String{
validate.UUID(),
validate.NoSeparator(),
},
},
"area_id": schema.StringAttribute{
Description: descriptions["area_id"],
Computed: true,
},
"internet_access": schema.BoolAttribute{
Description: descriptions["internet_access"],
Computed: true,
},
"state": schema.StringAttribute{
Description: descriptions["state"],
Computed: true,
},
"created_at": schema.StringAttribute{
Description: descriptions["created_at"],
Computed: true,
},
"updated_at": schema.StringAttribute{
Description: descriptions["updated_at"],
Computed: true,
},
},
}
}

// Read refreshes the Terraform state with the latest data.
func (d *projectDataSource) Read(ctx context.Context, req datasource.ReadRequest, resp *datasource.ReadResponse) { // nolint:gocritic // function signature required by Terraform
var model DatasourceModel
diags := req.Config.Get(ctx, &model)
resp.Diagnostics.Append(diags...)
if resp.Diagnostics.HasError() {
return
}
projectId := model.ProjectId.ValueString()
ctx = tflog.SetField(ctx, "project_id", projectId)

projectResp, err := d.client.GetProjectDetailsExecute(ctx, projectId)
if err != nil {
utils.LogError(
ctx,
&resp.Diagnostics,
err,
"Reading project",
fmt.Sprintf("Project with ID %q does not exists.", projectId),
nil,
)
resp.State.RemoveResource(ctx)
return
}

// Map response body to schema
err = mapDataSourceFields(projectResp, &model)
if err != nil {
core.LogAndAddError(ctx, &resp.Diagnostics, "Error reading project", fmt.Sprintf("Process API payload: %v", err))
return
}
// Set refreshed state
diags = resp.State.Set(ctx, &model)
resp.Diagnostics.Append(diags...)
if resp.Diagnostics.HasError() {
return
}
tflog.Info(ctx, "project read")
}

func mapDataSourceFields(projectResp *iaas.Project, model *DatasourceModel) error {
if projectResp == nil {
return fmt.Errorf("response input is nil")
}
if model == nil {
return fmt.Errorf("model input is nil")
}

var projectId string
if model.ProjectId.ValueString() != "" {
projectId = model.ProjectId.ValueString()
} else if projectResp.ProjectId != nil {
projectId = *projectResp.ProjectId
} else {
return fmt.Errorf("project id is not present")
}

model.Id = utils.BuildInternalTerraformId(projectId)
model.ProjectId = types.StringValue(projectId)

var areaId basetypes.StringValue
if projectResp.AreaId != nil {
if projectResp.AreaId.String != nil {
areaId = types.StringPointerValue(projectResp.AreaId.String)
} else if projectResp.AreaId.StaticAreaID != nil {
areaId = types.StringValue(string(*projectResp.AreaId.StaticAreaID))
}
}

var createdAt basetypes.StringValue
if projectResp.CreatedAt != nil {
createdAtValue := *projectResp.CreatedAt
createdAt = types.StringValue(createdAtValue.Format(time.RFC3339))
}

var updatedAt basetypes.StringValue
if projectResp.UpdatedAt != nil {
updatedAtValue := *projectResp.UpdatedAt
updatedAt = types.StringValue(updatedAtValue.Format(time.RFC3339))
}

model.AreaId = areaId
model.InternetAccess = types.BoolPointerValue(projectResp.InternetAccess)
model.State = types.StringPointerValue(projectResp.State)
model.CreatedAt = createdAt
model.UpdatedAt = updatedAt
return nil
}
Loading
Loading