NewWe open-sourced 50+ Laravel packages
Custom AI apps, agents and automation — Roundly ConsultingRoundly
All packages

Three equivalent entry points run the same code. The facade is the shortest and the recommended default. RoundlyConsulting\RefreshTokens\RefreshTokensManager — the facade’s root, a container singleton — gives the identical API as an explicit constructor dependency, with no static calls. And every method is backed by a single-purpose action with an execute() method, for composing into your own actions, jobs or commands:

use RoundlyConsulting\RefreshTokens\Actions\RotateRefreshTokenAction;
use RoundlyConsulting\RefreshTokens\RefreshTokensManager;

final class RefreshController
{
    public function __construct(private RefreshTokensManager $refreshTokens) {}

    public function __invoke(Request $request): JsonResponse
    {
        $rotation = $this->refreshTokens->rotate($request->string('refresh_token')->value());
        // …
    }
}

// The raw action:
$rotation = app(RotateRefreshTokenAction::class)->execute($plain, new RotationContext);

The same call in all three forms:

// Facade
RefreshTokens::sessions($user)->revokeOthers($currentJti);

// Dependency injection
public function __construct(private RefreshTokensManager $refreshTokens) {}
$this->refreshTokens->sessions($user)->revokeOthers($currentJti);

// The raw action
app(RevokeOtherSessionsAction::class)->execute($user, $currentJti, RevocationReason::LogoutAll);

Facade method → action

Facade methodAction
issue() / for()->issue()IssueRefreshTokenAction
redeem()RedeemRefreshTokenAction
rotate()RotateRefreshTokenAction
revoke()RevokeRefreshTokenAction
prune()PruneRefreshTokensAction
sessions()->all() / find()ListSessionsAction / FindSessionAction
sessions()->revoke()RevokeSessionByFamilyAction
sessions()->revokeOthers() / revokeAllExcept() / revokeAll()RevokeOtherSessionsAction / RevokeAllSessionsExceptAction / RevokeAllSessionsAction
session()->enrich() / revoke()EnrichSessionAction / RevokeSessionAction

Every manager and handle method resolves its action from the container per call, so your rebindings and Event::fake() apply. RefreshTokens::fake() swaps the manager in the container as well as behind the facade, so injected managers and the trait are recorded too.

Internal building blocks

RevokeTokenFamilyAction (the family revoke inside reuse detection) and SealPendingRotationsAction (sealing sessions caught mid-rotation) are @internal and not on the facade — they run inside redeem() and the session revokes, so don’t call them directly.

Show your open-source love

This package is free and MIT-licensed. If it saves you time, a one-off donation or a Patreon membership keeps it maintained, tested and documented.

More ways to support, including crypto

By donating, you agree to our donation terms.

Want this built into your product?

We integrate our packages into custom Laravel and AI builds. Tell us what you're working on and we'll reply within 48 hours.