mirror of
https://github.com/coder/coder.git
synced 2026-09-21 20:51:01 +08:00
chore: loosen static validation when using dynamic parameters (#17516)
Co-authored-by: Steven Masley <stevenmasley@gmail.com>
This commit is contained in:
Generated
+3
@@ -11453,6 +11453,9 @@ const docTemplate = `{
|
||||
"autostart_schedule": {
|
||||
"type": "string"
|
||||
},
|
||||
"enable_dynamic_parameters": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"name": {
|
||||
"type": "string"
|
||||
},
|
||||
|
||||
Generated
+3
@@ -10211,6 +10211,9 @@
|
||||
"autostart_schedule": {
|
||||
"type": "string"
|
||||
},
|
||||
"enable_dynamic_parameters": {
|
||||
"type": "boolean"
|
||||
},
|
||||
"name": {
|
||||
"type": "string"
|
||||
},
|
||||
|
||||
@@ -676,6 +676,9 @@ func createWorkspace(
|
||||
if req.TemplateVersionID != uuid.Nil {
|
||||
builder = builder.VersionID(req.TemplateVersionID)
|
||||
}
|
||||
if req.EnableDynamicParameters && api.Experiments.Enabled(codersdk.ExperimentDynamicParameters) {
|
||||
builder = builder.UsingDynamicParameters()
|
||||
}
|
||||
|
||||
workspaceBuild, provisionerJob, provisionerDaemons, err = builder.Build(
|
||||
ctx,
|
||||
|
||||
@@ -51,10 +51,11 @@ type Builder struct {
|
||||
logLevel string
|
||||
deploymentValues *codersdk.DeploymentValues
|
||||
|
||||
richParameterValues []codersdk.WorkspaceBuildParameter
|
||||
initiator uuid.UUID
|
||||
reason database.BuildReason
|
||||
templateVersionPresetID uuid.UUID
|
||||
richParameterValues []codersdk.WorkspaceBuildParameter
|
||||
dynamicParametersEnabled bool
|
||||
initiator uuid.UUID
|
||||
reason database.BuildReason
|
||||
templateVersionPresetID uuid.UUID
|
||||
|
||||
// used during build, makes function arguments less verbose
|
||||
ctx context.Context
|
||||
@@ -178,6 +179,11 @@ func (b Builder) MarkPrebuild() Builder {
|
||||
return b
|
||||
}
|
||||
|
||||
func (b Builder) UsingDynamicParameters() Builder {
|
||||
b.dynamicParametersEnabled = true
|
||||
return b
|
||||
}
|
||||
|
||||
// SetLastWorkspaceBuildInTx prepopulates the Builder's cache with the last workspace build. This allows us
|
||||
// to avoid a repeated database query when the Builder's caller also needs the workspace build, e.g. auto-start &
|
||||
// auto-stop.
|
||||
@@ -578,6 +584,7 @@ func (b *Builder) getParameters() (names, values []string, err error) {
|
||||
if err != nil {
|
||||
return nil, nil, BuildError{http.StatusBadRequest, "Unable to build workspace with unsupported parameters", err}
|
||||
}
|
||||
|
||||
resolver := codersdk.ParameterResolver{
|
||||
Rich: db2sdk.WorkspaceBuildParameters(lastBuildParameters),
|
||||
}
|
||||
@@ -586,16 +593,24 @@ func (b *Builder) getParameters() (names, values []string, err error) {
|
||||
if err != nil {
|
||||
return nil, nil, BuildError{http.StatusInternalServerError, "failed to convert template version parameter", err}
|
||||
}
|
||||
value, err := resolver.ValidateResolve(
|
||||
tvp,
|
||||
b.findNewBuildParameterValue(templateVersionParameter.Name),
|
||||
)
|
||||
if err != nil {
|
||||
// At this point, we've queried all the data we need from the database,
|
||||
// so the only errors are problems with the request (missing data, failed
|
||||
// validation, immutable parameters, etc.)
|
||||
return nil, nil, BuildError{http.StatusBadRequest, fmt.Sprintf("Unable to validate parameter %q", templateVersionParameter.Name), err}
|
||||
|
||||
var value string
|
||||
if !b.dynamicParametersEnabled {
|
||||
var err error
|
||||
value, err = resolver.ValidateResolve(
|
||||
tvp,
|
||||
b.findNewBuildParameterValue(templateVersionParameter.Name),
|
||||
)
|
||||
if err != nil {
|
||||
// At this point, we've queried all the data we need from the database,
|
||||
// so the only errors are problems with the request (missing data, failed
|
||||
// validation, immutable parameters, etc.)
|
||||
return nil, nil, BuildError{http.StatusBadRequest, fmt.Sprintf("Unable to validate parameter %q", templateVersionParameter.Name), err}
|
||||
}
|
||||
} else {
|
||||
value = resolver.Resolve(tvp, b.findNewBuildParameterValue(templateVersionParameter.Name))
|
||||
}
|
||||
|
||||
names = append(names, templateVersionParameter.Name)
|
||||
values = append(values, value)
|
||||
}
|
||||
|
||||
@@ -227,6 +227,7 @@ type CreateWorkspaceRequest struct {
|
||||
RichParameterValues []WorkspaceBuildParameter `json:"rich_parameter_values,omitempty"`
|
||||
AutomaticUpdates AutomaticUpdates `json:"automatic_updates,omitempty"`
|
||||
TemplateVersionPresetID uuid.UUID `json:"template_version_preset_id,omitempty" format:"uuid"`
|
||||
EnableDynamicParameters bool `json:"enable_dynamic_parameters,omitempty"`
|
||||
}
|
||||
|
||||
func (c *Client) OrganizationByName(ctx context.Context, name string) (Organization, error) {
|
||||
|
||||
@@ -190,6 +190,26 @@ func (r *ParameterResolver) ValidateResolve(p TemplateVersionParameter, v *Works
|
||||
return resolvedValue.Value, nil
|
||||
}
|
||||
|
||||
// Resolve returns the value of the parameter. It does not do any validation,
|
||||
// and is meant for use with the new dynamic parameters code path.
|
||||
func (r *ParameterResolver) Resolve(p TemplateVersionParameter, v *WorkspaceBuildParameter) string {
|
||||
prevV := r.findLastValue(p)
|
||||
// First, the provided value
|
||||
resolvedValue := v
|
||||
// Second, previous value if not ephemeral
|
||||
if resolvedValue == nil && !p.Ephemeral {
|
||||
resolvedValue = prevV
|
||||
}
|
||||
// Last, default value
|
||||
if resolvedValue == nil {
|
||||
resolvedValue = &WorkspaceBuildParameter{
|
||||
Name: p.Name,
|
||||
Value: p.DefaultValue,
|
||||
}
|
||||
}
|
||||
return resolvedValue.Value
|
||||
}
|
||||
|
||||
// findLastValue finds the value from the previous build and returns it, or nil if the parameter had no value in the
|
||||
// last build.
|
||||
func (r *ParameterResolver) findLastValue(p TemplateVersionParameter) *WorkspaceBuildParameter {
|
||||
|
||||
Generated
+2
@@ -1462,6 +1462,7 @@ None
|
||||
{
|
||||
"automatic_updates": "always",
|
||||
"autostart_schedule": "string",
|
||||
"enable_dynamic_parameters": true,
|
||||
"name": "string",
|
||||
"rich_parameter_values": [
|
||||
{
|
||||
@@ -1484,6 +1485,7 @@ CreateWorkspaceRequest provides options for creating a new workspace. Only one o
|
||||
|------------------------------|-------------------------------------------------------------------------------|----------|--------------|---------------------------------------------------------------------------------------------------------|
|
||||
| `automatic_updates` | [codersdk.AutomaticUpdates](#codersdkautomaticupdates) | false | | |
|
||||
| `autostart_schedule` | string | false | | |
|
||||
| `enable_dynamic_parameters` | boolean | false | | |
|
||||
| `name` | string | true | | |
|
||||
| `rich_parameter_values` | array of [codersdk.WorkspaceBuildParameter](#codersdkworkspacebuildparameter) | false | | Rich parameter values allows for additional parameters to be provided during the initial provision. |
|
||||
| `template_id` | string | false | | Template ID specifies which template should be used for creating the workspace. |
|
||||
|
||||
Generated
+2
@@ -25,6 +25,7 @@ of the template will be used.
|
||||
{
|
||||
"automatic_updates": "always",
|
||||
"autostart_schedule": "string",
|
||||
"enable_dynamic_parameters": true,
|
||||
"name": "string",
|
||||
"rich_parameter_values": [
|
||||
{
|
||||
@@ -605,6 +606,7 @@ of the template will be used.
|
||||
{
|
||||
"automatic_updates": "always",
|
||||
"autostart_schedule": "string",
|
||||
"enable_dynamic_parameters": true,
|
||||
"name": "string",
|
||||
"rich_parameter_values": [
|
||||
{
|
||||
|
||||
Generated
+1
@@ -467,6 +467,7 @@ export interface CreateWorkspaceRequest {
|
||||
readonly rich_parameter_values?: readonly WorkspaceBuildParameter[];
|
||||
readonly automatic_updates?: AutomaticUpdates;
|
||||
readonly template_version_preset_id?: string;
|
||||
readonly enable_dynamic_parameters?: boolean;
|
||||
}
|
||||
|
||||
// From codersdk/deployment.go
|
||||
|
||||
@@ -282,6 +282,7 @@ const CreateWorkspacePageExperimental: FC = () => {
|
||||
|
||||
const workspace = await createWorkspaceMutation.mutateAsync({
|
||||
...workspaceRequest,
|
||||
enable_dynamic_parameters: true,
|
||||
userId: owner.id,
|
||||
});
|
||||
onCreateWorkspace(workspace);
|
||||
|
||||
Reference in New Issue
Block a user