|
@@ -9,6 +9,8 @@ import (
|
|
|
"github.com/hashicorp-demoapp/hashicups-client-go"
|
|
|
"github.com/hashicorp/terraform-plugin-framework/resource"
|
|
|
"github.com/hashicorp/terraform-plugin-framework/resource/schema"
|
|
|
+ "github.com/hashicorp/terraform-plugin-framework/resource/schema/planmodifier"
|
|
|
+ "github.com/hashicorp/terraform-plugin-framework/resource/schema/stringplanmodifier"
|
|
|
"github.com/hashicorp/terraform-plugin-framework/types"
|
|
|
)
|
|
|
|
|
@@ -23,35 +25,50 @@ func NewOrderResource() resource.Resource {
|
|
|
return &orderResource{}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
type orderResource struct {
|
|
|
client *hashicups.Client
|
|
|
}
|
|
|
|
|
|
-func (r *orderResource) Configure(ctx context.Context, req resource.ConfigureRequest, resp *resource.ConfigureResponse) {
|
|
|
-
|
|
|
-
|
|
|
- if req.ProviderData == nil {
|
|
|
- return
|
|
|
- }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+type orderResourceModel struct {
|
|
|
+ ID types.String `tfsdk:"id"`
|
|
|
+ Items []orderItemModel `tfsdk:"items"`
|
|
|
+ LastUpdated types.String `tfsdk:"last_updated"`
|
|
|
+}
|
|
|
|
|
|
- client, ok := req.ProviderData.(*hashicups.Client)
|
|
|
- if !ok {
|
|
|
- resp.Diagnostics.AddError("Unexpected Resource Configure Type",
|
|
|
- fmt.Sprintf("Expected *hashicups.Client, got: %T. Please report this issue to the provider developers.", req.ProviderData))
|
|
|
- return
|
|
|
- }
|
|
|
- r.client = client
|
|
|
+
|
|
|
+type orderItemModel struct {
|
|
|
+ Coffee orderItemCoffeeModel `tfsdk:"coffee"`
|
|
|
+ Quantity types.Int64 `tfsdk:"quantity"`
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
+type orderItemCoffeeModel struct {
|
|
|
+ ID types.Int64 `tfsdk:"id"`
|
|
|
+ Name types.String `tfsdk:"name"`
|
|
|
+ Teaser types.String `tfsdk:"teaser"`
|
|
|
+ Description types.String `tfsdk:"description"`
|
|
|
+ Price types.Float64 `tfsdk:"price"`
|
|
|
+ Image types.String `tfsdk:"image"`
|
|
|
}
|
|
|
|
|
|
-func (r *orderResource) Metadata(ctx context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) {
|
|
|
+
|
|
|
+func (r *orderResource) Metadata(_ context.Context, req resource.MetadataRequest, resp *resource.MetadataResponse) {
|
|
|
resp.TypeName = req.ProviderTypeName + "_order"
|
|
|
}
|
|
|
|
|
|
-func (r *orderResource) Schema(ctx context.Context, req resource.SchemaRequest, resp *resource.SchemaResponse) {
|
|
|
+
|
|
|
+func (r *orderResource) Schema(_ context.Context, _ resource.SchemaRequest, resp *resource.SchemaResponse) {
|
|
|
resp.Schema = schema.Schema{
|
|
|
Attributes: map[string]schema.Attribute{
|
|
|
"id": schema.StringAttribute{
|
|
|
Computed: true,
|
|
|
+ PlanModifiers: []planmodifier.String{
|
|
|
+ stringplanmodifier.UseStateForUnknown(),
|
|
|
+ },
|
|
|
},
|
|
|
"last_updated": schema.StringAttribute{
|
|
|
Computed: true,
|
|
@@ -93,6 +110,27 @@ func (r *orderResource) Schema(ctx context.Context, req resource.SchemaRequest,
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
+func (r *orderResource) Configure(_ context.Context, req resource.ConfigureRequest, resp *resource.ConfigureResponse) {
|
|
|
+ if req.ProviderData == nil {
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ client, ok := req.ProviderData.(*hashicups.Client)
|
|
|
+
|
|
|
+ if !ok {
|
|
|
+ resp.Diagnostics.AddError(
|
|
|
+ "Unexpected Resource Configure Type",
|
|
|
+ fmt.Sprintf("Expected *hashicups.Client, got: %T. Please report this issue to the provider developers.", req.ProviderData),
|
|
|
+ )
|
|
|
+
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+ r.client = client
|
|
|
+}
|
|
|
+
|
|
|
+
|
|
|
func (r *orderResource) Create(ctx context.Context, req resource.CreateRequest, resp *resource.CreateResponse) {
|
|
|
var plan orderResourceModel
|
|
|
|
|
@@ -114,7 +152,7 @@ func (r *orderResource) Create(ctx context.Context, req resource.CreateRequest,
|
|
|
return
|
|
|
}
|
|
|
|
|
|
-
|
|
|
+
|
|
|
|
|
|
|
|
|
var items []hashicups.OrderItem
|
|
@@ -133,12 +171,12 @@ func (r *orderResource) Create(ctx context.Context, req resource.CreateRequest,
|
|
|
if err != nil {
|
|
|
resp.Diagnostics.AddError(
|
|
|
"Error creating order",
|
|
|
- err.Error(),
|
|
|
+ "Could not create order, unexpected error: "+err.Error(),
|
|
|
)
|
|
|
return
|
|
|
}
|
|
|
|
|
|
-
|
|
|
+
|
|
|
|
|
|
plan.ID = types.StringValue(strconv.Itoa(order.ID))
|
|
|
for orderItemIndex, orderItem := range order.Items {
|
|
@@ -166,6 +204,7 @@ func (r *orderResource) Create(ctx context.Context, req resource.CreateRequest,
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
func (r *orderResource) Read(ctx context.Context, req resource.ReadRequest, resp *resource.ReadResponse) {
|
|
|
var state orderResourceModel
|
|
|
|
|
@@ -194,8 +233,8 @@ func (r *orderResource) Read(ctx context.Context, req resource.ReadRequest, resp
|
|
|
order, err := r.client.GetOrder(id)
|
|
|
if err != nil {
|
|
|
resp.Diagnostics.AddError(
|
|
|
- "Error reading HashiCups order",
|
|
|
- "Could not read HashiCups order "+state.ID.ValueString()+": "+err.Error(),
|
|
|
+ "Error Reading HashiCups Order",
|
|
|
+ "Could not read HashiCups order ID "+state.ID.ValueString()+": "+err.Error(),
|
|
|
)
|
|
|
return
|
|
|
}
|
|
@@ -205,7 +244,7 @@ func (r *orderResource) Read(ctx context.Context, req resource.ReadRequest, resp
|
|
|
|
|
|
state.Items = []orderItemModel{}
|
|
|
for _, item := range order.Items {
|
|
|
- itemState := orderItemModel{
|
|
|
+ state.Items = append(state.Items, orderItemModel{
|
|
|
Coffee: orderItemCoffeeModel{
|
|
|
ID: types.Int64Value(int64(item.Coffee.ID)),
|
|
|
Name: types.StringValue(item.Coffee.Name),
|
|
@@ -215,8 +254,7 @@ func (r *orderResource) Read(ctx context.Context, req resource.ReadRequest, resp
|
|
|
Image: types.StringValue(item.Coffee.Image),
|
|
|
},
|
|
|
Quantity: types.Int64Value(int64(item.Quantity)),
|
|
|
- }
|
|
|
- state.Items = append(state.Items, itemState)
|
|
|
+ })
|
|
|
}
|
|
|
|
|
|
|
|
@@ -229,33 +267,84 @@ func (r *orderResource) Read(ctx context.Context, req resource.ReadRequest, resp
|
|
|
}
|
|
|
}
|
|
|
|
|
|
+
|
|
|
func (r *orderResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) {
|
|
|
- return
|
|
|
-}
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ var plan orderResourceModel
|
|
|
+ diags := req.Plan.Get(ctx, &plan)
|
|
|
+ resp.Diagnostics.Append(diags...)
|
|
|
+ if resp.Diagnostics.HasError() {
|
|
|
+ return
|
|
|
+ }
|
|
|
|
|
|
-func (r *orderResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) {
|
|
|
- return
|
|
|
-}
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ var hashicupsItems []hashicups.OrderItem
|
|
|
+ for _, item := range plan.Items {
|
|
|
+ hashicupsItems = append(hashicupsItems, hashicups.OrderItem{
|
|
|
+ Coffee: hashicups.Coffee{
|
|
|
+ ID: int(item.Coffee.ID.ValueInt64()),
|
|
|
+ },
|
|
|
+ Quantity: int(item.Quantity.ValueInt64()),
|
|
|
+ })
|
|
|
+ }
|
|
|
|
|
|
-
|
|
|
-
|
|
|
-
|
|
|
-type orderResourceModel struct {
|
|
|
- ID types.String `tfsdk:"id"`
|
|
|
- Items []orderItemModel `tfsdk:"items"`
|
|
|
- LastUpdated types.String `tfsdk:"last_updated"`
|
|
|
-}
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ _, err := r.client.UpdateOrder(plan.ID.ValueString(), hashicupsItems)
|
|
|
+ if err != nil {
|
|
|
+ resp.Diagnostics.AddError(
|
|
|
+ "Error Reading HashiCups Order",
|
|
|
+ "Could not read HashiCups order ID "+plan.ID.ValueString()+": "+err.Error(),
|
|
|
+ )
|
|
|
+ }
|
|
|
|
|
|
-type orderItemModel struct {
|
|
|
- Quantity types.Int64 `tfsdk:"quantity"`
|
|
|
- Coffee orderItemCoffeeModel `tfsdk:"coffee"`
|
|
|
+
|
|
|
+ order, err := r.client.GetOrder(plan.ID.ValueString())
|
|
|
+ if err != nil {
|
|
|
+ resp.Diagnostics.AddError(
|
|
|
+ "Error Reading HashiCups Order",
|
|
|
+ "Could not read HashiCups order ID "+plan.ID.ValueString()+": "+err.Error(),
|
|
|
+ )
|
|
|
+ return
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ plan.Items = []orderItemModel{}
|
|
|
+ for _, orderItem := range order.Items {
|
|
|
+ plan.Items = append(plan.Items, orderItemModel{
|
|
|
+ Coffee: orderItemCoffeeModel{
|
|
|
+ ID: types.Int64Value(int64(orderItem.Coffee.ID)),
|
|
|
+ Name: types.StringValue(orderItem.Coffee.Name),
|
|
|
+ Teaser: types.StringValue(orderItem.Coffee.Teaser),
|
|
|
+ Description: types.StringValue(orderItem.Coffee.Description),
|
|
|
+ Price: types.Float64Value(orderItem.Coffee.Price),
|
|
|
+ Image: types.StringValue(orderItem.Coffee.Image),
|
|
|
+ },
|
|
|
+ Quantity: types.Int64Value(int64(orderItem.Quantity)),
|
|
|
+ })
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ plan.LastUpdated = types.StringValue(time.Now().Format(time.RFC850))
|
|
|
+
|
|
|
+
|
|
|
+ diags = resp.State.Set(ctx, plan)
|
|
|
+ resp.Diagnostics.Append(diags...)
|
|
|
+
|
|
|
+
|
|
|
+ if resp.Diagnostics.HasError() {
|
|
|
+ return
|
|
|
+ }
|
|
|
}
|
|
|
|
|
|
-type orderItemCoffeeModel struct {
|
|
|
- ID types.Int64 `tfsdk:"id"`
|
|
|
- Name types.String `tfsdk:"name"`
|
|
|
- Teaser types.String `tfsdk:"teaser"`
|
|
|
- Description types.String `tfsdk:"description"`
|
|
|
- Price types.Float64 `tfsdk:"price"`
|
|
|
- Image types.String `tfsdk:"image"`
|
|
|
+
|
|
|
+func (r *orderResource) Delete(ctx context.Context, req resource.DeleteRequest, resp *resource.DeleteResponse) {
|
|
|
+ return
|
|
|
}
|