mirror of
https://github.com/coder/coder.git
synced 2026-09-24 15:04:27 +08:00
feat: add user-level parameter autofill (#11731)
This PR solves #10478 by auto-filling previously used template values in create and update workspace flows. I decided against explicit user values in settings for these reasons: * Autofill is far easier to implement * Users benefit from autofill _by default_ — we don't need to teach them new concepts * If we decide that autofill creates more harm than good, we can remove it without breaking compatibility
This commit is contained in:
@@ -23,6 +23,7 @@ import (
|
||||
"github.com/coder/coder/v2/coderd/coderdtest"
|
||||
"github.com/coder/coder/v2/coderd/database"
|
||||
"github.com/coder/coder/v2/coderd/database/dbauthz"
|
||||
"github.com/coder/coder/v2/coderd/database/dbfake"
|
||||
"github.com/coder/coder/v2/coderd/database/dbgen"
|
||||
"github.com/coder/coder/v2/coderd/database/dbtime"
|
||||
"github.com/coder/coder/v2/coderd/rbac"
|
||||
@@ -1721,6 +1722,129 @@ func TestSuspendedPagination(t *testing.T) {
|
||||
require.Equal(t, expected, page.Users, "expected page")
|
||||
}
|
||||
|
||||
func TestUserAutofillParameters(t *testing.T) {
|
||||
t.Parallel()
|
||||
t.Run("NotSelf", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
client1, _, api := coderdtest.NewWithAPI(t, &coderdtest.Options{})
|
||||
|
||||
u1 := coderdtest.CreateFirstUser(t, client1)
|
||||
|
||||
client2, u2 := coderdtest.CreateAnotherUser(t, client1, u1.OrganizationID)
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), testutil.WaitLong)
|
||||
defer cancel()
|
||||
|
||||
db := api.Database
|
||||
|
||||
version := dbfake.TemplateVersion(t, db).Seed(database.TemplateVersion{
|
||||
CreatedBy: u1.UserID,
|
||||
OrganizationID: u1.OrganizationID,
|
||||
}).Params(database.TemplateVersionParameter{
|
||||
Name: "param",
|
||||
Required: true,
|
||||
}).Do()
|
||||
|
||||
_, err := client2.UserAutofillParameters(
|
||||
ctx,
|
||||
u1.UserID.String(),
|
||||
version.Template.ID,
|
||||
)
|
||||
|
||||
var apiErr *codersdk.Error
|
||||
require.ErrorAs(t, err, &apiErr)
|
||||
require.Equal(t, http.StatusBadRequest, apiErr.StatusCode())
|
||||
|
||||
// u1 should be able to read u2's parameters as u1 is site admin.
|
||||
_, err = client1.UserAutofillParameters(
|
||||
ctx,
|
||||
u2.ID.String(),
|
||||
version.Template.ID,
|
||||
)
|
||||
require.NoError(t, err)
|
||||
})
|
||||
|
||||
t.Run("FindsParameters", func(t *testing.T) {
|
||||
t.Parallel()
|
||||
client1, _, api := coderdtest.NewWithAPI(t, &coderdtest.Options{})
|
||||
|
||||
u1 := coderdtest.CreateFirstUser(t, client1)
|
||||
|
||||
client2, u2 := coderdtest.CreateAnotherUser(t, client1, u1.OrganizationID)
|
||||
|
||||
db := api.Database
|
||||
|
||||
version := dbfake.TemplateVersion(t, db).Seed(database.TemplateVersion{
|
||||
CreatedBy: u1.UserID,
|
||||
OrganizationID: u1.OrganizationID,
|
||||
}).Params(database.TemplateVersionParameter{
|
||||
Name: "param",
|
||||
Required: true,
|
||||
},
|
||||
database.TemplateVersionParameter{
|
||||
Name: "param2",
|
||||
Ephemeral: true,
|
||||
},
|
||||
).Do()
|
||||
|
||||
dbfake.WorkspaceBuild(t, db, database.Workspace{
|
||||
OwnerID: u2.ID,
|
||||
TemplateID: version.Template.ID,
|
||||
OrganizationID: u1.OrganizationID,
|
||||
}).Params(
|
||||
database.WorkspaceBuildParameter{
|
||||
Name: "param",
|
||||
Value: "foo",
|
||||
},
|
||||
database.WorkspaceBuildParameter{
|
||||
Name: "param2",
|
||||
Value: "bar",
|
||||
},
|
||||
).Do()
|
||||
|
||||
ctx, cancel := context.WithTimeout(context.Background(), testutil.WaitLong)
|
||||
defer cancel()
|
||||
|
||||
// Use client2 since client1 is site admin, so
|
||||
// we don't get good coverage on RBAC working.
|
||||
params, err := client2.UserAutofillParameters(
|
||||
ctx,
|
||||
u2.ID.String(),
|
||||
version.Template.ID,
|
||||
)
|
||||
require.NoError(t, err)
|
||||
|
||||
require.Equal(t, 1, len(params))
|
||||
|
||||
require.Equal(t, "param", params[0].Name)
|
||||
require.Equal(t, "foo", params[0].Value)
|
||||
|
||||
// Verify that latest parameter value is returned.
|
||||
dbfake.WorkspaceBuild(t, db, database.Workspace{
|
||||
OrganizationID: u1.OrganizationID,
|
||||
OwnerID: u2.ID,
|
||||
TemplateID: version.Template.ID,
|
||||
}).Params(
|
||||
database.WorkspaceBuildParameter{
|
||||
Name: "param",
|
||||
Value: "foo_new",
|
||||
},
|
||||
).Do()
|
||||
|
||||
params, err = client2.UserAutofillParameters(
|
||||
ctx,
|
||||
u2.ID.String(),
|
||||
version.Template.ID,
|
||||
)
|
||||
require.NoError(t, err)
|
||||
|
||||
require.Equal(t, 1, len(params))
|
||||
|
||||
require.Equal(t, "param", params[0].Name)
|
||||
require.Equal(t, "foo_new", params[0].Value)
|
||||
})
|
||||
}
|
||||
|
||||
// TestPaginatedUsers creates a list of users, then tries to paginate through
|
||||
// them using different page sizes.
|
||||
func TestPaginatedUsers(t *testing.T) {
|
||||
|
||||
Reference in New Issue
Block a user