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

Provide request input sanitization #358

Merged
merged 4 commits into from
Apr 10, 2024
Merged

Conversation

devmount
Copy link
Collaborator

@devmount devmount commented Apr 8, 2024

Description of the Change

This PR provides a new middleware to strip all html tags from data changing requests using nh3.
I added one test case for schedule updates, we can add more if we need them at other places.

Benefits

Prevent XSS.

Applicable Issues

Closes #263

@devmount devmount added this to the v0.2 milestone Apr 8, 2024
@devmount devmount requested a review from MelissaAutumn April 8, 2024 15:21
@devmount devmount self-assigned this Apr 8, 2024


async def __call__(self, scope: Scope, receive: Receive, send: Send) -> None:
if "method" not in scope or scope["method"] in ("GET", "HEAD", "OPTIONS"):
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I just went with those methods. Please adjust this line, if we want to make this middleware more specific to special header configurations.

Copy link
Member

Choose a reason for hiding this comment

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

No POST?

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

This conditional asserts all exclude options as true. Since we like to sanitize POST, it's not listed here. Or do I misunderstood something?

Copy link
Member

Choose a reason for hiding this comment

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

oh by returning none it will move forward with the middleware? if so can you explicitly return none.

if thats not it, i need to look at the starlette docs again 😅

Copy link
Member

@MelissaAutumn MelissaAutumn Apr 8, 2024

Choose a reason for hiding this comment

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

ohh. the sanitize functions are in call. okay i just cant read indents today. my b.

We might want to sanitize GETs though. we can coms back to that

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Only the sanitize_request_body def is in __call__, sorry if this is confusing 🙈 When I implemented it, it made perfectly sense 😂 Always open for suggestions.

Comment on lines 47 to 52
if isinstance(value, dict):
json_body[key] = __class__.sanitize_dict(value)
elif isinstance(value, list):
json_body[key] = __class__.sanitize_list(value)
else:
json_body[key] = __class__.sanitize_str(value)
Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I thought handling dicts, lists and strings would be sufficient for now. But let me know, if we need more checks here.



async def __call__(self, scope: Scope, receive: Receive, send: Send) -> None:
if "method" not in scope or scope["method"] in ("GET", "HEAD", "OPTIONS"):
Copy link
Member

Choose a reason for hiding this comment

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

No POST?

return message
if not isinstance(body, bytes) :
return message
json_body = json.loads(body)
Copy link
Member

Choose a reason for hiding this comment

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

I think we use formData for login/password form. So this might not work here. 🤔

I guess you could catch the exception and sanitize body input itself.

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

Good point, will add that

Copy link
Collaborator Author

Choose a reason for hiding this comment

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

I provided a is_json() utility function now.

@devmount devmount requested a review from MelissaAutumn April 9, 2024 04:42
@devmount
Copy link
Collaborator Author

devmount commented Apr 9, 2024

@MelissaAutumn This PR should be ready now, I added an example test case for schedule updates. We can add more tests for different endpoints in the future, if we need them.

Copy link
Member

@MelissaAutumn MelissaAutumn 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 now! Thanks!

I'm guessing this doesn't sanitize formData? If not we can look into other solutions for that but I don't think it's a problem right now since we don't exactly have it on stage/prod.

@MelissaAutumn MelissaAutumn merged commit af0daaf into main Apr 10, 2024
2 checks passed
@MelissaAutumn MelissaAutumn deleted the features/263-sanitize-input branch April 10, 2024 15:36
@devmount
Copy link
Collaborator Author

Since we're only using formData for temporary dev login for now, let's take a look at that again if we need it somewhere else.

jdbass pushed a commit that referenced this pull request May 17, 2024
* ➕ Provide request input sanitization

* 🔨 Check for json request body

* ➕ Add test  for input sanitization
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.

Sanitize input
2 participants