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

Improve authentication #1348

Merged
merged 5 commits into from
Feb 5, 2025
Merged

Improve authentication #1348

merged 5 commits into from
Feb 5, 2025

Conversation

csutter
Copy link
Contributor

@csutter csutter commented Jan 27, 2025

This improves various aspects of the authentication logic in this app, including:

  • Adding model tests for the User model
  • Moving the check on User permissions back into the model (which doesn't belong in the controller)
  • Adding request tests that ensure authentication is actually enforced
  • Cleaning up how system and request tests deal with setting the GDS SSO test user, and fixing a bug where the test user wasn't reset properly in the after(:all) block
  • Adding a Current singleton through ActiveSupport::CurrentAttributes to store the user for cross-cutting concerns

This adds the GDS SSO shared "linting" examples to make sure the `User`
model satisfies its contract.
This is a model concern and shouldn't be on the controller. Also adds
tests.
This is neater, and will let us re-use it in request specs too.
This adds a request spec that tests that all `ApplicationController`
descendants actually enforce authentication.
This creates an idiomatic Rails per-request attributes singleton
`Current`, using [`ActiveSupport::CurrentAttributes`], and stores the
current user in it. This will allow us to access the currently active
user in cross-cutting concerns, without having to deeply pass it around.

`CurrentAttributes` is a "sharp tool" that should be used with caution
as it creates global state for a request, but is an ideal tool for
dealing with auditing and logging concerns (which we'll soon introduce)
where you need to have global awareness of certain request attributes
outside of just the controller layer.

We have prior art for this pattern, for example in Whitehall.

[`ActiveSupport::CurrentAttributes`]: https://edgeapi.rubyonrails.org/classes/ActiveSupport/CurrentAttributes.html
@@ -0,0 +1,14 @@
# Enforces user authentication for a controller and stores the authenticated user in `Current`
module AuthenticatesUser
Copy link
Contributor Author

Choose a reason for hiding this comment

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

To anticipate a conversation we've had before: the default naming convention for concerns tends to be _____able, but I do like to diverge from that in two cases:

  • something sets up a relationship (where I'd go for Has_____), or
  • non-model concerns, which tend to be a more diverse bunch (like here)

DoesThing (AuthenticatesUser) feels natural here to me but I'm open for debate!

I'll point to Gitlab's controller concerns as some prior art, with concerns like:

  • AuthenticatesWithTwoFactor
  • ChecksCollaboration
  • RendersNotes

Copy link
Contributor

Choose a reason for hiding this comment

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

To be fair -able doesn't really fit with Authenticate, so I have no concerns (see what I did there?) about the name AuthenticatesUser.

Thanks for explaining your choice though 🎉

Copy link
Contributor

@leenagupte leenagupte left a comment

Choose a reason for hiding this comment

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

Thanks for adding tests to make sure the user is authenticated. I think that's something we generally omit.

CurrentAttributes looks interesting. I'm sure the real power of it will become more obvious as more features are added.

@@ -0,0 +1,14 @@
# Enforces user authentication for a controller and stores the authenticated user in `Current`
module AuthenticatesUser
Copy link
Contributor

Choose a reason for hiding this comment

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

To be fair -able doesn't really fit with Authenticate, so I have no concerns (see what I did there?) about the name AuthenticatesUser.

Thanks for explaining your choice though 🎉

@csutter csutter merged commit d94c841 into main Feb 5, 2025
10 checks passed
@csutter csutter deleted the improve-auth branch February 5, 2025 16:47
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.

2 participants