这是indexloc提供的服务,不要输入任何密码
Skip to content

dgls/rolling release changes #349

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 1 commit into
base: dimitri/rolling-release
Choose a base branch
from
Draft
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
39 changes: 19 additions & 20 deletions client/project_rolling_release.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,33 +14,33 @@ type RollingReleaseStage struct {
RequireApproval bool `json:"requireApproval,omitempty"` // Only in response for manual-approval type
}

// RollingRelease represents the rolling release configuration
type RollingRelease struct {
// RollingReleaseInfo represents the rolling release configuration
type RollingReleaseInfo struct {
Enabled bool `json:"enabled"` // Required
AdvancementType string `json:"advancementType"` // Required when enabled=true: 'automatic' or 'manual-approval'
Stages []RollingReleaseStage `json:"stages"` // Required when enabled=true: 2-10 stages
}

type RollingReleaseInfo struct {
RollingRelease RollingRelease `json:"rollingRelease"`
ProjectID string `json:"projectId"`
TeamID string `json:"teamId"`
type RollingReleaseResponse struct {
RollingRelease RollingReleaseInfo `json:"rollingRelease"`
ProjectID string `json:"-"` // Not in API response
TeamID string `json:"-"` // Not in API response
}

// GetRollingRelease returns the rolling release for a given project.
func (c *Client) GetRollingRelease(ctx context.Context, projectID, teamID string) (RollingReleaseInfo, error) {
func (c *Client) GetRollingRelease(ctx context.Context, projectID, teamID string) (RollingReleaseResponse, error) {
teamId := c.TeamID(teamID)
url := fmt.Sprintf("%s/v1/projects/%s/rolling-release/config?teamId=%s", c.baseURL, projectID, teamId)

var d RollingReleaseInfo
var d RollingReleaseResponse
err := c.doRequest(clientRequest{
ctx: ctx,
method: "GET",
url: url,
}, &d)

if err != nil {
return RollingReleaseInfo{}, fmt.Errorf("error getting rolling-release: %w", err)
return RollingReleaseResponse{}, fmt.Errorf("error getting rolling-release: %w", err)
}

d.ProjectID = projectID
Expand All @@ -49,16 +49,15 @@ func (c *Client) GetRollingRelease(ctx context.Context, projectID, teamID string
return d, nil
}

// UpdateRollingReleaseRequest defines the information that needs to be passed to Vercel in order to
// update a rolling release.
// UpdateRollingReleaseRequest defines the information that needs to be passed to Vercel in order to update a rolling release.
type UpdateRollingReleaseRequest struct {
RollingRelease RollingRelease `json:"rollingRelease"`
ProjectID string `json:"projectId"`
TeamID string `json:"teamId"`
RollingRelease RollingReleaseInfo `json:"rollingRelease"`
ProjectID string `json:"projectId"`
TeamID string `json:"teamId"`
}

// UpdateRollingRelease will update an existing rolling release to the latest information.
func (c *Client) UpdateRollingRelease(ctx context.Context, request UpdateRollingReleaseRequest) (RollingReleaseInfo, error) {
func (c *Client) UpdateRollingRelease(ctx context.Context, request UpdateRollingReleaseRequest) (RollingReleaseResponse, error) {
request.TeamID = c.TeamID(request.TeamID)
if request.RollingRelease.Enabled {
enableRequest := map[string]any{
Expand All @@ -67,15 +66,15 @@ func (c *Client) UpdateRollingRelease(ctx context.Context, request UpdateRolling
"stages": request.RollingRelease.Stages,
}

var result RollingReleaseInfo
var result RollingReleaseResponse
err := c.doRequest(clientRequest{
ctx: ctx,
method: "PATCH",
url: fmt.Sprintf("%s/v1/projects/%s/rolling-release/config?teamId=%s", c.baseURL, request.ProjectID, request.TeamID),
body: string(mustMarshal(enableRequest)),
}, &result)
if err != nil {
return RollingReleaseInfo{}, fmt.Errorf("error enabling rolling release: %w", err)
return RollingReleaseResponse{}, fmt.Errorf("error enabling rolling release: %w", err)
}

result.ProjectID = request.ProjectID
Expand All @@ -88,22 +87,22 @@ func (c *Client) UpdateRollingRelease(ctx context.Context, request UpdateRolling
} else {
// For disabling, just send the request as is
disabledRequest := UpdateRollingReleaseRequest{
RollingRelease: RollingRelease{
RollingRelease: RollingReleaseInfo{
Enabled: false,
AdvancementType: "",
Stages: []RollingReleaseStage{},
},
}

var result RollingReleaseInfo
var result RollingReleaseResponse
err := c.doRequest(clientRequest{
ctx: ctx,
method: "PATCH",
url: fmt.Sprintf("%s/v1/projects/%s/rolling-release/config?teamId=%s", c.baseURL, request.ProjectID, request.TeamID),
body: string(mustMarshal(disabledRequest.RollingRelease)),
}, &result)
if err != nil {
return RollingReleaseInfo{}, fmt.Errorf("error disabling rolling release: %w", err)
return RollingReleaseResponse{}, fmt.Errorf("error disabling rolling release: %w", err)
}

result.ProjectID = request.ProjectID
Expand Down
53 changes: 11 additions & 42 deletions vercel/resource_project_rolling_release.go
Original file line number Diff line number Diff line change
Expand Up @@ -72,22 +72,16 @@ func (r *projectRollingReleaseResource) Schema(ctx context.Context, _ resource.S
MarkdownDescription: "The rolling release configuration.",
Required: true,
Attributes: map[string]schema.Attribute{
"enabled": schema.BoolAttribute{
MarkdownDescription: "Whether rolling releases are enabled.",
Required: true,
},
"advancement_type": schema.StringAttribute{
MarkdownDescription: "The type of advancement between stages. Must be either 'automatic' or 'manual-approval'. Required when enabled is true.",
Optional: true,
Computed: true,
MarkdownDescription: "The type of advancement between stages. Must be either 'automatic' or 'manual-approval'.",
Required: true,
Validators: []validator.String{
advancementTypeValidator{},
},
},
"stages": schema.ListNestedAttribute{
MarkdownDescription: "The stages of the rolling release. Required when enabled is true.",
Optional: true,
Computed: true,
MarkdownDescription: "The stages of the rolling release.",
Required: true,
NestedObject: schema.NestedAttributeObject{
Attributes: map[string]schema.Attribute{
"target_percentage": schema.Int64Attribute{
Expand Down Expand Up @@ -125,7 +119,6 @@ type RollingReleaseStage struct {

// RollingRelease reflects the state terraform stores internally for a project rolling release.
type RollingRelease struct {
Enabled types.Bool `tfsdk:"enabled"`
AdvancementType types.String `tfsdk:"advancement_type"`
Stages types.List `tfsdk:"stages"`
}
Expand All @@ -142,7 +135,6 @@ func (e *RollingReleaseInfo) toUpdateRollingReleaseRequest() (client.UpdateRolli
var advancementType string
var diags diag.Diagnostics

if e.RollingRelease.Enabled.ValueBool() {
advancementType = e.RollingRelease.AdvancementType.ValueString()

// Convert stages from types.List to []client.RollingReleaseStage
Expand Down Expand Up @@ -189,22 +181,16 @@ func (e *RollingReleaseInfo) toUpdateRollingReleaseRequest() (client.UpdateRolli
}
}
}
} else {
// When disabled, don't send any stages or advancement type to the API
stages = []client.RollingReleaseStage{}
advancementType = ""
}

// Log the request for debugging
tflog.Info(context.Background(), "converting to update request", map[string]any{
"enabled": e.RollingRelease.Enabled.ValueBool(),
"advancement_type": advancementType,
"stages_count": len(stages),
})

return client.UpdateRollingReleaseRequest{
RollingRelease: client.RollingRelease{
Enabled: e.RollingRelease.Enabled.ValueBool(),
RollingRelease: client.RollingReleaseInfo{
AdvancementType: advancementType,
Stages: stages,
},
Expand All @@ -213,23 +199,18 @@ func (e *RollingReleaseInfo) toUpdateRollingReleaseRequest() (client.UpdateRolli
}, diags
}

func convertResponseToRollingRelease(response client.RollingReleaseInfo, plan *RollingReleaseInfo, ctx context.Context) (RollingReleaseInfo, diag.Diagnostics) {
func convertResponseToRollingRelease(response client.RollingReleaseResponse, plan *RollingReleaseInfo, ctx context.Context) (RollingReleaseInfo, diag.Diagnostics) {
var diags diag.Diagnostics
advancementType := types.StringNull()
if plan.RollingRelease.Enabled.ValueBool() {
advancementType = plan.RollingRelease.AdvancementType
}
result := RollingReleaseInfo{
RollingRelease: RollingRelease{
Enabled: plan.RollingRelease.Enabled,
AdvancementType: advancementType,
},
ProjectID: types.StringValue(response.ProjectID),
TeamID: types.StringValue(response.TeamID),
}

// If disabled, return empty values
if !plan.RollingRelease.Enabled.ValueBool() {
result.RollingRelease.AdvancementType = types.StringValue("")
// Create an empty list instead of null
emptyStages, stagesDiags := types.ListValueFrom(ctx, types.ObjectType{
Expand All @@ -245,7 +226,6 @@ func convertResponseToRollingRelease(response client.RollingReleaseInfo, plan *R
}
result.RollingRelease.Stages = emptyStages
return result, diags
}

// If we have a plan, try to match stages by target percentage to preserve order
var orderedStages []client.RollingReleaseStage
Expand Down Expand Up @@ -289,7 +269,7 @@ func convertResponseToRollingRelease(response client.RollingReleaseInfo, plan *R

// If duration is not set in plan, handle based on advancement type
if duration.IsNull() {
if plan.RollingRelease.AdvancementType.ValueString() == "automatic" {
if plan != nil && plan.RollingRelease.AdvancementType.ValueString() == "automatic" {
if i < len(orderedStages)-1 {
// For non-last stages in automatic advancement, use the duration from the API
if stage.Duration != nil {
Expand Down Expand Up @@ -338,7 +318,6 @@ func convertResponseToRollingRelease(response client.RollingReleaseInfo, plan *R

// Log the conversion result for debugging
tflog.Info(ctx, "converted rolling release response", map[string]any{
"enabled": result.RollingRelease.Enabled.ValueBool(),
"advancement_type": result.RollingRelease.AdvancementType.ValueString(),
"stages_count": len(stages),
})
Expand All @@ -364,17 +343,13 @@ func (r *projectRollingReleaseResource) Create(ctx context.Context, req resource

// Log the request for debugging
tflog.Info(ctx, "creating rolling release", map[string]any{
"enabled": request.RollingRelease.Enabled,
"advancement_type": request.RollingRelease.AdvancementType,
"stages": request.RollingRelease.Stages,
})

// If we're enabling, first create in disabled state then enable
if request.RollingRelease.Enabled {
// First create in disabled state
disabledRequest := client.UpdateRollingReleaseRequest{
RollingRelease: client.RollingRelease{
Enabled: false,
RollingRelease: client.RollingReleaseInfo{
AdvancementType: "",
Stages: []client.RollingReleaseStage{},
},
Expand All @@ -392,7 +367,6 @@ func (r *projectRollingReleaseResource) Create(ctx context.Context, req resource
)
return
}
}

out, err := r.client.UpdateRollingRelease(ctx, request)
if err != nil {
Expand All @@ -414,7 +388,6 @@ func (r *projectRollingReleaseResource) Create(ctx context.Context, req resource

// Log the result for debugging
tflog.Debug(ctx, "created rolling release", map[string]any{
"enabled": result.RollingRelease.Enabled.ValueBool(),
"advancement_type": result.RollingRelease.AdvancementType.ValueString(),
"stages": result.RollingRelease.Stages,
})
Expand Down Expand Up @@ -454,7 +427,6 @@ func (r *projectRollingReleaseResource) Read(ctx context.Context, req resource.R

// Log the response for debugging
tflog.Debug(ctx, "got rolling release from API", map[string]any{
"enabled": out.RollingRelease.Enabled,
"advancement_type": out.RollingRelease.AdvancementType,
"stages": out.RollingRelease.Stages,
})
Expand All @@ -467,7 +439,6 @@ func (r *projectRollingReleaseResource) Read(ctx context.Context, req resource.R

// Log the result for debugging
tflog.Debug(ctx, "converted rolling release", map[string]any{
"enabled": result.RollingRelease.Enabled.ValueBool(),
"advancement_type": result.RollingRelease.AdvancementType.ValueString(),
"stages": result.RollingRelease.Stages,
})
Expand Down Expand Up @@ -504,15 +475,14 @@ func (r *projectRollingReleaseResource) Update(ctx context.Context, req resource

// Log the request for debugging
tflog.Debug(ctx, "updating rolling release", map[string]any{
"enabled": request.RollingRelease.Enabled,
"advancement_type": request.RollingRelease.AdvancementType,
"stages": request.RollingRelease.Stages,
})

// If we're transitioning from enabled to disabled, first disable
if state.RollingRelease.Enabled.ValueBool() && !request.RollingRelease.Enabled {
disabledRequest := client.UpdateRollingReleaseRequest{
RollingRelease: client.RollingRelease{
RollingRelease: client.RollingReleaseInfo{
Enabled: false,
AdvancementType: "",
Stages: []client.RollingReleaseStage{},
Expand All @@ -536,7 +506,7 @@ func (r *projectRollingReleaseResource) Update(ctx context.Context, req resource
// If we're transitioning from disabled to enabled, first create in disabled state
if !state.RollingRelease.Enabled.ValueBool() && request.RollingRelease.Enabled {
disabledRequest := client.UpdateRollingReleaseRequest{
RollingRelease: client.RollingRelease{
RollingRelease: client.RollingReleaseInfo{
Enabled: false,
AdvancementType: "",
Stages: []client.RollingReleaseStage{},
Expand Down Expand Up @@ -577,7 +547,6 @@ func (r *projectRollingReleaseResource) Update(ctx context.Context, req resource

// Log the result for debugging
tflog.Debug(ctx, "updated rolling release", map[string]any{
"enabled": result.RollingRelease.Enabled.ValueBool(),
"advancement_type": result.RollingRelease.AdvancementType.ValueString(),
"stages": result.RollingRelease.Stages,
})
Expand All @@ -600,7 +569,7 @@ func (r *projectRollingReleaseResource) Delete(ctx context.Context, req resource

// Disable rolling release
request := client.UpdateRollingReleaseRequest{
RollingRelease: client.RollingRelease{
RollingRelease: client.RollingReleaseInfo{
Enabled: false,
AdvancementType: "",
Stages: []client.RollingReleaseStage{},
Expand Down
Loading
Loading