in internal/provider/resource_gitlab_group_issue_board.go [204:332]
func (r *gitlabGroupIssueBoardResource) Update(ctx context.Context, req resource.UpdateRequest, resp *resource.UpdateResponse) {
var data *gitlabGroupIssueBoardResourceModel
// Read Terraform plan data into the model
resp.Diagnostics.Append(req.Plan.Get(ctx, &data)...)
if resp.Diagnostics.HasError() {
return
}
groupID, boardID, err := utils.ParseTwoPartID(data.Id.ValueString())
if err != nil {
resp.Diagnostics.AddError(
"Invalid resource ID format",
fmt.Sprintf("The resource ID '%s' has an invalid format in Update. It should be '<group-id>:<board-id>'. Error: %s", data.Id.ValueString(), err.Error()),
)
return
}
boardId, err := strconv.Atoi(boardID)
if err != nil {
resp.Diagnostics.AddError(
"Internal provider error",
fmt.Sprintf("Unable to convert board id to int: %s", err.Error()),
)
return
}
// local copies of plan arguments
// read all information for refresh from resource id
boardName := data.Name.ValueString()
optionsUpdate := &gitlab.UpdateGroupIssueBoardOptions{
Name: gitlab.Ptr(boardName),
}
if !data.MilestoneId.IsNull() && !data.MilestoneId.IsUnknown() {
optionsUpdate.MilestoneID = gitlab.Ptr(int(data.MilestoneId.ValueInt64()))
}
if !data.Labels.IsNull() && !data.Labels.IsUnknown() {
// convert the Set to a []string and pass it in
var labels []string
data.Labels.ElementsAs(ctx, &labels, true)
gitlabLabels := gitlab.LabelOptions(labels)
optionsUpdate.Labels = &gitlabLabels
}
issueBoard, _, err := r.client.GroupIssueBoards.UpdateIssueBoard(groupID, boardId, optionsUpdate, gitlab.WithContext(ctx))
if err != nil {
// persist API response in state model
data.Id = types.StringValue(fmt.Sprintf("%s:%d", groupID, issueBoard.ID))
r.groupIssueBoardToStateModel(ctx, groupID, issueBoard, data)
// Save updated data into Terraform state
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
if api.Is404(err) {
resp.Diagnostics.AddError(
"GitLab Feature not available",
fmt.Sprintf("The group issue board feature is not available on this group. Make sure it's part of an enterprise plan. Error: %s", err.Error()),
)
return
}
resp.Diagnostics.AddError("GitLab API error occurred", fmt.Sprintf("Unable to update issue board: %s", err.Error()))
return
}
for _, d := range issueBoard.Lists {
_, err := r.client.GroupIssueBoards.DeleteGroupIssueBoardList(groupID, issueBoard.ID, d.ID, gitlab.WithContext(ctx))
if err != nil {
// persist API response in state model
data.Id = types.StringValue(fmt.Sprintf("%s:%d", groupID, issueBoard.ID))
r.groupIssueBoardToStateModel(ctx, groupID, issueBoard, data)
// Save updated data into Terraform state
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
resp.Diagnostics.AddError("GitLab API error occurred", "failed to delete list ")
}
}
if resp.Diagnostics.HasError() {
return
}
listsData := make([]*gitlab.BoardList, len(data.Lists))
// Sort data.Lists based on list Position
sort.Slice(data.Lists, func(i, j int) bool {
labelPosI := data.Lists[i].Position
labelPosJ := data.Lists[j].Position
// Handle nil values
if (labelPosI.IsNull() || labelPosI.IsUnknown()) && (labelPosJ.IsNull() || labelPosJ.IsUnknown()) {
return false // Treat two nils as equal
} else if labelPosI.IsNull() || labelPosI.IsUnknown() {
return true // Nil should come after non-nil
} else if labelPosJ.IsNull() || labelPosJ.IsUnknown() {
return false // Non-nil should come before nil
}
return labelPosI.ValueInt64() < labelPosJ.ValueInt64()
})
for i, v := range data.Lists {
listOptions := &gitlab.CreateGroupIssueBoardListOptions{}
listOptions.LabelID = gitlab.Ptr(int(v.LabelId.ValueInt64()))
issueBoardList, _, err := r.client.GroupIssueBoards.CreateGroupIssueBoardList(groupID, issueBoard.ID, listOptions, gitlab.WithContext(ctx))
if err != nil {
if api.Is404(err) {
resp.Diagnostics.AddError(
"GitLab Feature not available",
fmt.Sprintf("The group issue board feature is not available on this group. Make sure it's part of an enterprise plan. Error: %s", err.Error()),
)
return
}
resp.Diagnostics.AddError("GitLab API error occurred", fmt.Sprintf("Unable to update issue board lists. Issue board may still have been updated: %s", err.Error()))
return
}
listsData[i] = issueBoardList
}
issueBoard.Lists = listsData
// persist API response in state model
data.Id = types.StringValue(fmt.Sprintf("%s:%d", groupID, issueBoard.ID))
r.groupIssueBoardToStateModel(ctx, groupID, issueBoard, data)
// Log the creation of the resource
tflog.Debug(ctx, "updated a group issue board", map[string]any{
"group": groupID, "board": issueBoard.Name,
})
// Save data into Terraform state
resp.Diagnostics.Append(resp.State.Set(ctx, &data)...)
}