Skip to content

feat(@xen-orchestra/rest-api): expose get user and get users #8494

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

Open
wants to merge 5 commits into
base: master
Choose a base branch
from

Conversation

MelissaFrncJrg
Copy link
Contributor

Description

Short explanation of this PR (feel free to re-use commit message)

Checklist

  • Commit
    • Title follows commit conventions
    • Reference the relevant issue (Fixes #007, See xoa-support#42, See https://...)
    • If bug fix, add Introduced by
  • Changelog
    • If visible by XOA users, add changelog entry
    • Update "Packages to release" in CHANGELOG.unreleased.md
  • PR
    • If UI changes, add screenshots
    • If not finished or not tested, open as Draft

Review process

This 2-passes review process aims to:

  • develop skills of junior reviewers
  • limit the workload for senior reviewers
  • limit the number of unnecessary changes by the author
  1. The author creates a PR.
  2. Review process:
    1. The author assigns the junior reviewer.
    2. The junior reviewer conducts their review:
      • Resolves their comments if they are addressed.
      • Adds comments if necessary or approves the PR.
    3. The junior reviewer assigns the senior reviewer.
    4. The senior reviewer conducts their review:
      • If there are no unresolved comments on the PR → merge.
      • Otherwise, we continue with 3.
  3. The author responds to comments and/or makes corrections, and we go back to 2.

Notes:

  1. The author can request a review at any time, even if the PR is still a Draft.
  2. In theory, there should not be more than one reviewer at a time.
  3. The author should not make any changes:
    • When a reviewer is assigned.
    • Between the junior and senior reviews.

@MelissaFrncJrg MelissaFrncJrg marked this pull request as ready for review April 8, 2025 13:20
@MelissaFrncJrg MelissaFrncJrg requested a review from b-Nollet April 8, 2025 13:20
href: '/rest/v0/users/722d17b9-699b-49d2-8193-be1ac573d3de',
},
{
email: 'testName',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is this a valid value?

@b-Nollet b-Nollet requested a review from MathieuRA April 9, 2025 07:13
Copy link
Member

@MathieuRA MathieuRA left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please update @vates/type#xoUser.
Properties name and pw_hash are optional. Maybe there are other error in the type definition

Comment on lines 32 to 49
async getUsers(
@Request() req: ExRequest,
@Query() fields?: string,
@Query() filter?: string,
@Query() limit?: number
): Promise<string[] | WithHref<Partial<Unbrand<XoUser>>>[]> {
return this.sendObjects(Object.values(await this.getObjects({ filter, limit })), req)
}

/**
* @example id "722d17b9-699b-49d2-8193-be1ac573d3de"
*/
@Example(user)
@Get('{id}')
@Response(notFoundResp.status, notFoundResp.description)
getUser(@Path() id: string): Promise<Unbrand<XoUser>> {
return this.getObject(id as XoUser['id'])
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These methods will return the pw_hash of a user.
I don't think it's a good practice to return the password (even if it's a hash).
@fbeauchamp Are you agree to not return the hashed password? (The JSON-RPC API does not return it)

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree, even if it's only a salted hash, it has no value , and only add one more risks (at leats questions by user asking if it's safe)

Copy link
Member

@MathieuRA MathieuRA left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You need to update the XoUser type in vates/types.
The pw_hash property is optional. Make sure there are no other errors in the XoUser type.

Comment on lines +24 to +29
partialUser(user: XoUser): Partial<Unbrand<XoUser>> {
return {
...user,
pw_hash: '***obfuscated***',
}
}
Copy link
Member

@MathieuRA MathieuRA Apr 11, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The type is not valid.
Partial<T> means that all properties of T become optional.
We don't want all other props to be optional simply because of pw_hash

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Only use Unbrand<T> when documenting an endpoint.
Unbrand is a type that converts Branded<string> to string to make it compatible with OpenAPI.

@Query() limit?: number
): Promise<string[] | WithHref<Partial<Unbrand<XoUser>>>[]> {
const users = Object.values(await this.getObjects({ filter, limit })).map(this.partialUser)
return this.sendObjects(users as XoUser[], req)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Avoid to use the as keyword expect if no other solution

Comment on lines +17 to +22
getAllCollectionObjects(): Promise<XoUser[]> {
return this.restApi.xoApp.getAllUsers()
}
getCollectionObject(id: XoUser['id']): Promise<XoUser> {
return this.restApi.xoApp.getUser(id)
}
Copy link
Member

@MathieuRA MathieuRA Apr 11, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

IMO, these methods should return sanitized users. This way, every time we call this.getObject/this.getObjects, we will get a sanitized user. The REST API does not need to manage user passwords.

Comment on lines +7 to +12
{
permission: 'admin',
name: '[email protected]',
id: '722d17b9-699b-49d2-8193-be1ac573d3de',
href: '/rest/v0/users/722d17b9-699b-49d2-8193-be1ac573d3de',
},
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Try to add another user in your example.
You should have the same number of result between userIds and partialUsers.

partialUser(user: XoUser): Partial<Unbrand<XoUser>> {
return {
...user,
pw_hash: '***obfuscated***',
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

pw_hash can be undefined. Don't obfuscate the password if no password is defined

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants