-
Notifications
You must be signed in to change notification settings - Fork 12
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
Report better errors on user CRUD operations #621
Conversation
This warning has become an error in PHP 8. We also remove some unused code.
The HybridUserDAO matches user data with the LDAP and keeps them in sync with the local database, to maintain the relations with other data tables. We modify the create operation in this DAO to return OperationResult, matching the new expectations of the upper layers. We change the Hybrid DAO to extend the Postgres DAO, so we can reuse the SQL operations. In this case, we call the create operation from the Postgres DAO after we do the corresponding LDAP checks.
model/dao/UserDAO/HybridUserDAO.php
Outdated
@@ -417,35 +418,14 @@ public function getJourneyHistory($userId) { | |||
/** User updater for LDAP/PostgreSQL Hybrid. | |||
* | |||
* This function updates the data of a User by its {@link UserVO}. | |||
* WARNING: this function allows to update to a name that does not exist in LDAP. | |||
* Do we really want this behavior? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do we do something about this? This could make sense as a transient state before we change the user in LDAP, and in this state the user would not be able to login. Alternatively, we could check that we rename to another login that exists in LDAP so we would have to modify LDAP first. In any case, this should be a very rarely used operation.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree that this is such a rare case that we can leave it like this for now.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, I think I'll rewrite the warning message to state the consequences clearly instead of asking this open question.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is great, thank you! Sorry for the late review
if($ldapResult["count"] == 0) { | ||
$result = new OperationResult(false); | ||
$result->setResponseCode(400); | ||
$result->setErrorNumber(1234); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just double checking if 1234 is correct?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same question here. I'm guessing you are picking an arbitrary error code here since we wouldn't have a php or sql error code in this instance.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, sorry, I'm not really keeping track of what the error codes are and we aren't really using them. We'd have to follow up with a general review...
model/dao/UserDAO/HybridUserDAO.php
Outdated
@@ -417,35 +418,14 @@ public function getJourneyHistory($userId) { | |||
/** User updater for LDAP/PostgreSQL Hybrid. | |||
* | |||
* This function updates the data of a User by its {@link UserVO}. | |||
* WARNING: this function allows to update to a name that does not exist in LDAP. | |||
* Do we really want this behavior? |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree that this is such a rare case that we can leave it like this for now.
|
||
$result->setIsSuccessful(true); | ||
$result->setMessage('User updated successfully.'); | ||
$result->setResponseCode(201); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: If we are updating here and not creating, then we might want to use the 200 response code (for 'okay')
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks for catching this, this and the other nits are copy&paste issues I was blind to.
$affectedRows = pg_affected_rows($res); | ||
$result->setIsSuccessful(true); | ||
$result->setMessage('User updated successfully.'); | ||
$result->setResponseCode(201); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit: since we're deleting and not creating, a 200 response code might be better here. Also, if we're deleting, perhaps a slightly different message would be clearer? Something like "User deleted successfully".
$errorMessage = $ex->getMessage(); | ||
$resultMessage = "Error updating user:\n"; | ||
if(strpos($errorMessage, "Foreign key violation")) { | ||
$result->setResponseCode(403); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit (again, sorry): My understanding of a 403 is that it means a user doesn't have permission to perform the attempted action. A FK violation feels a little more like a generic 500 to me, but I also recognize that some of these response codes don't always fit every situation.
Same feedback re the message: you might want to specify that that was an error when deleting the user instead of updating.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You are right about 403 doesn't really fit, but I don't want to use 500 because it's defined as a "catch-all" error for unexpected situations. It's possible to trigger this foreign key violation from the UI, if an admin attempts to delete a user and that user has already created tasks, so I don't consider it an unexpected situation. And I decided not to use 400 because I don't think it's a client error either...
Maybe 409 Conflict is a better match?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Picking the correct code is always the hardest part. I've never really used a 409 before, but it could fit here. I'm good with that unless @anarute has another suggestion.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think 409 makes sense too!
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I had a few nits, but nothing to hold up the PR over.
I've pushed fixup patches to address your comments, and a new patch that allows us to report a message from the backend to the UI even in case of success. That's useful to show a warning when updating the login of an LDAP user. |
The changes look good to me! |
This operation did not do anything related with LDAP, so we simply run the corresponding SQL operation. We don't modify the behavior of the operation, so we add a comment about a detected problem. In the web service layer, we add try/catch blocks for the LDAPInvalidOperationException like the ones in the create and delete user services, to prevent crashing on operations that aren't defined in the LDAP backend (namely, assigning users to groups).
When updating a login name in the LDAP backend there is a risk of side effects. With this change, we are able to report the success message from the backend through the UI instead of overwriting it with another string, so we can warn users when doing that operation.
18773ce
to
e0fd789
Compare
Thanks! I've squashed the fixup patches, and will proceed to merge. |
This affects the Postgres and LDAP DAOs. Notice there are many operations in the user management screen (assign users to groups and all the user history assignment) that aren't upgraded yet to OperationResult and they keep working as usual.