Skip to content

Allow early configuration of devise models - #5853

Open
kaisq wants to merge 2 commits into
heartcombo:mainfrom
kaisq:devise-model-registration
Open

Allow early configuration of devise models#5853
kaisq wants to merge 2 commits into
heartcombo:mainfrom
kaisq:devise-model-registration

Conversation

@kaisq

@kaisq kaisq commented Jun 25, 2026

Copy link
Copy Markdown

As of Rails 8, which enables lazy-loaded routes by default, Devise configuration particularly in test environments consistently breaks because tests begin running before routes have been loaded. This causes Devise (and therefore Warden) to operate with only partial configuration, particularly, a stale default_scope among other things.

This change includes a new method to create a skeleton Mapping object which can be used to indicate a Devise-enabled model class that will be used for authentication before the route loading step has been completed. This object will have its configuration finalized once routes have been completed, and the Devise routes for that object are properly drawn.

This is backwards compatible with the current route-centric configuration.

As of Rails 8, which enables lazy-loaded routes by default, Devise
configuration particularly in test environments consistently breaks
because tests begin running before routes have been loaded. This causes
Devise (and therefore Warden) to operate with only partial
configuration, particularly, a stale default_scope among other things.

This change includes a new method to create a skeleton Mapping object
which can be used to indicate a Devise-enabled model class that will be
used for authentication before the route loading step has been
completed. This object will have its configuration finalized once routes
have been completed, and the Devise routes for that object are properly
drawn.

This is backwards compatible with the current route-centric
configuration.
@kaisq

kaisq commented Jun 25, 2026

Copy link
Copy Markdown
Author

This would fix #5752 (I have tested this locally with code that I believe to be hitting the same error) and likely also fixes #5844 (though I do not currently have a broken example of this)

@clarissalimab

Copy link
Copy Markdown

Thank you for working on this!

I've tested this solution against a mini app that reproduces a scenario I faced with a project where we built a custom Warden strategy for a header-based authentication: https://github.com/thoughtbot/devise-eager-load-issue-demo (see this branch).

It works well, but without the Devise model mapping configuration requirement that this introduces, it would introduce a regression on the next version since all requests would fail to authenticate going forward, which we may be hesitant to add.

I wonder if there's a way to have this solution where people can opt-in to use it without introducing the regression. Do you have any ideas? I'd be happy to help digging.

@kaisq

kaisq commented Aug 31, 2026

Copy link
Copy Markdown
Author

@clarissalimab thanks for testing this out, that's a great point. I've fixed that by updating the configure_warden! phase to be called both after the initial registration and after route loading. Would you mind testing again?

For the maintainers: to clarify my goals here, what I mean by "backwards compatible" is that it should be possible to update to a version with this change without making any configuration changes at all. I'm currently achieving this using a "last config wins" strategy if non-route configurations are declared in both locations, but there are a few other options to do this more intelligently and I'm happy to discuss that if we deem this a strategy worth pursuing. The "early config" stage should be entirely optional for projects where the existing route-based configuration is still working.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

3 participants