func()

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)...)
}