Skip to content

feat(web)!: throttle in the storage of the application's injector, reset through Throttle - #349

Open
mofr wants to merge 1 commit into
feat/response-headersfrom
feat/throttling
Open

mofr wants to merge 1 commit into
feat/response-headersfrom
feat/throttling

Conversation

@mofr

@mofr mofr commented Oct 27, 2026

Copy link
Copy Markdown
Collaborator

Stacked on #348.

What

  • Throttling counts in the ThrottlingStorage that the injector of the application binds: binder.bind(ThrottlingStorage, to=RedisThrottlingStorage(configuration)). An application with @throttling and no storage fails in create_urls instead of on the first throttled request.
  • The adapter passes the identity of its users to handle_request with each request. The Django adapter throttles by the Django user, by the client address otherwise, as before; it no longer installs that into a process-global on its first create_urls.
  • An API method with @throttling may declare throttle: winter.web.Throttle; throttle.reset() forgets what the scope has counted for the sender. It deletes the key the request was counted under, so it works even after the method has logged the user in, which reset(request, scope) only did when called before login().
  • The check stays where it was: before the interceptors, so it counts requests that authorization rejects.
  • Gone: set_throttling_storage, get_throttling_storage, set_throttling_identity_resolver, get_throttling_identity, reset(request, scope).
  • The isolation test gains the case of two applications counting in the storages of their own injectors.

Why

The storage and the identity were process-globals, and the Django adapter replaced the identity silently on its first call. The consumer has never configured the identity: its rule is the Django user or the address, so that rule stays the adapter's and needs no code. A custom identity, such as the company of an API key for PO Tracing, can be added later through the injector without breaking this.

🤖 Generated with Claude Code

…set through Throttle

Throttling takes its storage from the injector of the application, and an
application with @throttling and no ThrottlingStorage fails on startup. The
adapter gives handle_request the identity of its users: the Django adapter
throttles by the Django user, by the client address otherwise. An API method
with @throttling receives its Throttle, and throttle.reset() forgets what the
scope counted for the identity the request was counted for.

set_throttling_storage, set_throttling_identity_resolver and reset(request,
scope) are gone.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

This branch has not been deployed

No deployments
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.

1 participant