Skip to content
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

KNOX-3039 Add error message sanitization to GatewayServlet #914

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

Conversation

kardolus
Copy link

@kardolus kardolus commented Jun 4, 2024

What changes were proposed in this pull request?

This pull request introduces a mechanism to sanitize error messages in the GatewayServlet to improve security by hiding IP addresses from exception messages. The following changes were made:

  • Added a isErrorMessageSanitizationEnabled flag to the GatewayServlet to control whether error messages should be sanitized.
  • Implemented the sanitizeException and sanitizeAndRethrow methods in GatewayServlet to handle exception sanitization.
  • Updated the GatewayConfig interface and its implementation GatewayConfigImpl to include a new method isErrorMessageSanitizationEnabled.
  • Created the GatewayServletTest class to parameterize tests for scenarios where sanitization is enabled and disabled.

How was this patch tested?

This patch was tested using the following methods:

  • Parameterized unit tests were added to GatewayServletTest to cover both scenarios where error message sanitization is enabled and disabled.
  • Manual review and inspection of the code changes to ensure accuracy and completeness.

Test steps:

  1. Added unit tests in GatewayServletTest to check for sanitized and non-sanitized error messages.
  2. Verified the new tests pass successfully, ensuring error messages are appropriately sanitized or left unchanged based on the configuration.

@moresandeep moresandeep self-requested a review June 4, 2024 14:15
@pzampino pzampino requested a review from lmccay June 4, 2024 15:19
@kardolus kardolus requested review from pzampino and moresandeep June 6, 2024 14:03
Copy link
Contributor

@moresandeep moresandeep left a comment

Choose a reason for hiding this comment

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

Looks good!

@moresandeep
Copy link
Contributor

It would be nice to have a 4xx and 5xx page for errors. So instead of showing the ugly page with an exception we can show a custom page with a UUID corresponding the the error. This UUID would be the request-id for which the error is thrown so we can cross reference it in the logs. Just a though :) can be a new feature.

@kardolus
Copy link
Author

kardolus commented Jun 6, 2024

@moresandeep I think that is a great idea! I will start a discussion on the Apache mailing list to explore implementing custom 4xx and 5xx error pages.

@kardolus
Copy link
Author

kardolus commented Jun 8, 2024

@pzampino @moresandeep I implemented the SanitizedException. It makes the code a lot cleaner. I am not happy with the fact though that an IOException or a RuntimeException can be converted to a ServletException (a SanitizedException IS-A ServletException) through the sanitization flow.

But maybe I am overthinking things and overengineering. What do y'all think? Is it fine?

@kardolus kardolus requested a review from smolnar82 June 13, 2024 17:20
private <T extends Exception> T logAndSanitizeException(Exception e) throws T {
LOG.failedToExecuteFilter(e);
throw (T) sanitizeException(e);
return new SanitizedException(sanitizedMessage);
Copy link
Contributor

Choose a reason for hiding this comment

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

Why not perform the message sanitization in the SanitizationException class?

Copy link
Author

Choose a reason for hiding this comment

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

@pzampino There are some downsides in moving the logic over to the SanitizationException class. It makes the code less flexible and potentially harder to maintain (e.g. what if other classes want to throw a SanitizedException but with different logic?). It's also a bit of an effort to refactor the tests. We haven't decided yet that this pattern is better than keeping the original Exception type (see my previous comment). Finally, but less important IMO, moving the logic over to SanitizedException can be seen as a violation of the Single Responsibility Principle.

Copy link
Contributor

Choose a reason for hiding this comment

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

I'm not sure I agree about the Single Responsibility Principle. What is the responsibility of the SanitizationException if not to provide a sanitized the message? Otherwise, the burden of message sanitization is on all entities that throw it, AND there is no guarantee that a thrower will have sanitized the message.

If there is a need to customize the sanitization, IMO that is what extensions are for. Nothing would prevent the subsequent creation of classes that extends SanitizationException to override the sanitizing logic.

Personally, I don't think level of effort for refactoring counts for much in these types of decisions, especially refactoring of test code.

Copy link
Author

@kardolus kardolus Jun 14, 2024

Choose a reason for hiding this comment

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

@pzampino Yeah, I am bummed that I didn't receive any feedback on the tests. This class had none until I wrote some. Refactoring could mean I need tests on both classes, and since we didn't discuss whether this new pattern is actually better than the old one, it seems like wasted work. Feel free to commit a patch if you can. I am going to be a bit busy with some other work over the next couple of weeks.

Copy link
Author

Choose a reason for hiding this comment

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

@pzampino The Single Responsibility Principle would be violated because it would make the SanitizedException class responsible for both defining an exception and performing sanitization logic, thus giving it more than one reason to change.

@pzampino
Copy link
Contributor

@pzampino @moresandeep I implemented the SanitizedException. It makes the code a lot cleaner. I am not happy with the fact though that an IOException or a RuntimeException can be converted to a ServletException (a SanitizedException IS-A ServletException) through the sanitization flow.

But maybe I am overthinking things and overengineering. What do y'all think? Is it fine?

Unless the servlet engine treats them differently in some meaningful way, I think it's ok, so long as the exception does not get lost entirely, which in this case, it does not.

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