- Notifications
You must be signed in to change notification settings - Fork928
feat: Add update profile endpoint#916
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 ourterms of service andprivacy statement. We’ll occasionally send you account related emails.
Already on GitHub?Sign in to your account
Uh oh!
There was an error while loading.Please reload this page.
Changes fromall commits
2bdcaa8
a23c561
4418d74
27adb09
25a1a7c
dcb9179
5fe89ba
edd8c1f
d7e749a
b228896
ae22b4b
1e1fb85
c223fcf
b6eb9f7
7803e8f
4531e0d
File filter
Filter by extension
Conversations
Uh oh!
There was an error while loading.Please reload this page.
Jump to
Uh oh!
There was an error while loading.Please reload this page.
Diff view
Diff view
There are no files selected for viewing
Some generated files are not rendered by default. Learn more abouthow customized files appear on GitHub.
Uh oh!
There was an error while loading.Please reload this page.
Some generated files are not rendered by default. Learn more abouthow customized files appear on GitHub.
Uh oh!
There was an error while loading.Please reload this page.
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -40,3 +40,14 @@ INSERT INTO | ||
) | ||
VALUES | ||
($1, $2, $3, $4, FALSE, $5, $6, $7, $8) RETURNING *; | ||
-- name: UpdateUserProfile :one | ||
UPDATE | ||
users | ||
SET | ||
email = $2, | ||
"name" = $3, | ||
BrunoQuaresma marked this conversation as resolved. Show resolvedHide resolvedUh oh!There was an error while loading.Please reload this page. | ||
username = $4, | ||
updated_at = $5 | ||
WHERE | ||
id = $1 RETURNING *; |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -270,6 +270,70 @@ func (*api) userByName(rw http.ResponseWriter, r *http.Request) { | ||
render.JSON(rw, r, convertUser(user)) | ||
} | ||
func (api *api) putUserProfile(rw http.ResponseWriter, r *http.Request) { | ||
user := httpmw.UserParam(r) | ||
BrunoQuaresma marked this conversation as resolved. Show resolvedHide resolvedUh oh!There was an error while loading.Please reload this page. | ||
var params codersdk.UpdateUserProfileRequest | ||
if !httpapi.Read(rw, r, ¶ms) { | ||
return | ||
} | ||
if params.Name == nil { | ||
params.Name = &user.Name | ||
} | ||
existentUser, err := api.Database.GetUserByEmailOrUsername(r.Context(), database.GetUserByEmailOrUsernameParams{ | ||
Email: params.Email, | ||
Username: params.Username, | ||
}) | ||
isDifferentUser := existentUser.ID != user.ID | ||
if err == nil && isDifferentUser { | ||
responseErrors := []httpapi.Error{} | ||
if existentUser.Email == params.Email { | ||
responseErrors = append(responseErrors, httpapi.Error{ | ||
Field: "email", | ||
Code: "exists", | ||
}) | ||
} | ||
if existentUser.Username == params.Username { | ||
responseErrors = append(responseErrors, httpapi.Error{ | ||
Field: "username", | ||
Code: "exists", | ||
}) | ||
} | ||
httpapi.Write(rw, http.StatusConflict, httpapi.Response{ | ||
Message: fmt.Sprintf("user already exists"), | ||
Errors: responseErrors, | ||
}) | ||
BrunoQuaresma marked this conversation as resolved. Show resolvedHide resolvedUh oh!There was an error while loading.Please reload this page. | ||
return | ||
} | ||
if !errors.Is(err, sql.ErrNoRows) && isDifferentUser { | ||
httpapi.Write(rw, http.StatusInternalServerError, httpapi.Response{ | ||
Message: fmt.Sprintf("get user: %s", err), | ||
}) | ||
return | ||
} | ||
updatedUserProfile, err := api.Database.UpdateUserProfile(r.Context(), database.UpdateUserProfileParams{ | ||
ID: user.ID, | ||
Name: *params.Name, | ||
Email: params.Email, | ||
Username: params.Username, | ||
UpdatedAt: database.Now(), | ||
}) | ||
if err != nil { | ||
BrunoQuaresma marked this conversation as resolved. Show resolvedHide resolvedUh oh!There was an error while loading.Please reload this page. | ||
httpapi.Write(rw, http.StatusInternalServerError, httpapi.Response{ | ||
Message: fmt.Sprintf("patch user: %s", err.Error()), | ||
}) | ||
return | ||
} | ||
render.Status(r, http.StatusOK) | ||
render.JSON(rw, r, convertUser(updatedUserProfile)) | ||
} | ||
// Returns organizations the parameterized user has access to. | ||
func (api *api) organizationsByUser(rw http.ResponseWriter, r *http.Request) { | ||
user := httpmw.UserParam(r) | ||
@@ -872,5 +936,6 @@ func convertUser(user database.User) codersdk.User { | ||
Email: user.Email, | ||
CreatedAt: user.CreatedAt, | ||
Username: user.Username, | ||
Name: user.Name, | ||
} | ||
} |
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -200,6 +200,111 @@ func TestPostUsers(t *testing.T) { | ||
}) | ||
} | ||
func TestUpdateUserProfile(t *testing.T) { | ||
t.Parallel() | ||
t.Run("UserNotFound", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
coderdtest.CreateFirstUser(t, client) | ||
_, err := client.UpdateUserProfile(context.Background(), uuid.New(), codersdk.UpdateUserProfileRequest{ | ||
Username: "newusername", | ||
Email: "newemail@coder.com", | ||
}) | ||
var apiErr *codersdk.Error | ||
require.ErrorAs(t, err, &apiErr) | ||
// Right now, we are raising a BAD request error because we don't support a | ||
// user accessing other users info | ||
require.Equal(t, http.StatusBadRequest, apiErr.StatusCode()) | ||
}) | ||
t.Run("ConflictingEmail", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
user := coderdtest.CreateFirstUser(t, client) | ||
existentUser, _ := client.CreateUser(context.Background(), codersdk.CreateUserRequest{ | ||
Email: "bruno@coder.com", | ||
Username: "bruno", | ||
Password: "password", | ||
OrganizationID: user.OrganizationID, | ||
}) | ||
_, err := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: "newusername", | ||
Email: existentUser.Email, | ||
}) | ||
var apiErr *codersdk.Error | ||
require.ErrorAs(t, err, &apiErr) | ||
require.Equal(t, http.StatusConflict, apiErr.StatusCode()) | ||
}) | ||
t.Run("ConflictingUsername", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
user := coderdtest.CreateFirstUser(t, client) | ||
existentUser, _ := client.CreateUser(context.Background(), codersdk.CreateUserRequest{ | ||
Email: "bruno@coder.com", | ||
Username: "bruno", | ||
Password: "password", | ||
OrganizationID: user.OrganizationID, | ||
}) | ||
_, err := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: existentUser.Username, | ||
Email: "newemail@coder.com", | ||
}) | ||
var apiErr *codersdk.Error | ||
require.ErrorAs(t, err, &apiErr) | ||
require.Equal(t, http.StatusConflict, apiErr.StatusCode()) | ||
}) | ||
t.Run("UpdateUsernameAndEmail", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
coderdtest.CreateFirstUser(t, client) | ||
userProfile, err := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: "newusername", | ||
Email: "newemail@coder.com", | ||
}) | ||
require.NoError(t, err) | ||
require.Equal(t, userProfile.Username, "newusername") | ||
require.Equal(t, userProfile.Email, "newemail@coder.com") | ||
}) | ||
t.Run("UpdateUsername", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
coderdtest.CreateFirstUser(t, client) | ||
me, _ := client.User(context.Background(), codersdk.Me) | ||
userProfile, err := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: me.Username, | ||
Email: "newemail@coder.com", | ||
}) | ||
require.NoError(t, err) | ||
require.Equal(t, userProfile.Username, me.Username) | ||
require.Equal(t, userProfile.Email, "newemail@coder.com") | ||
}) | ||
t.Run("KeepUserName", func(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||
coderdtest.CreateFirstUser(t, client) | ||
me, _ := client.User(context.Background(), codersdk.Me) | ||
newName := "New Name" | ||
firstProfile, _ := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: me.Username, | ||
Email: me.Email, | ||
Name: &newName, | ||
}) | ||
t.Log(firstProfile) | ||
userProfile, err := client.UpdateUserProfile(context.Background(), codersdk.Me, codersdk.UpdateUserProfileRequest{ | ||
Username: "newusername", | ||
Email: "newemail@coder.com", | ||
}) | ||
require.NoError(t, err) | ||
require.Equal(t, userProfile.Username, "newusername") | ||
require.Equal(t, userProfile.Email, "newemail@coder.com") | ||
require.Equal(t, userProfile.Name, newName) | ||
}) | ||
} | ||
BrunoQuaresma marked this conversation as resolved. Show resolvedHide resolvedUh oh!There was an error while loading.Please reload this page. | ||
func TestUserByName(t *testing.T) { | ||
t.Parallel() | ||
client := coderdtest.New(t, nil) | ||