Weave Code
Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Larke Jwt Laravel Package

lake/larke-jwt

lake/larke-jwt is a Laravel package for JWT-based authentication, designed to help issue, parse, and validate JSON Web Tokens and integrate stateless API auth with Laravel guards and middleware. It simplifies protecting routes and securing API requests with tokens.

View on GitHub
Deep Wiki
Context7

Getting Started

Confirm the package name first. The listed name lake/larke-jwt is almost certainly a typo for larke/larke-jwt or deatil/larke-jwt (the author deatil publishes the larke-admin ecosystem under both namespaces). Run composer search larke jwt or check the repo's composer.json before you copy-paste a require line.

# Verify the real vendorname before installing
composer require larke/larke-jwt   # or deatil/larke-jwt — check the repo

First place to look is the repo's README and src/ tree. Larke/Deatil JWT packages typically mirror firebase/php-jwt's API surface, so expect roughly:

use Larke\JWT\JWT;

$token = JWT::encode(['sub' => $user->id, 'exp' => time() + 3600], config('jwt.secret'), 'HS256');
$claims = JWT::decode($token, new Key(config('jwt.secret'), 'HS256'));

First use case: stateless API auth. Issue a signed token on login, verify it in a middleware, read sub off the claim. Do not try to build refresh-token rotation on day one — get encode/decode/middleware working against a single user first, then layer the lifecycle.

Publish any shipped config if the package provides one (php artisan vendor:publish --tag=larke-jwt or similar). Even if you end up not using it, it tells you which knobs the author exposed.

Implementation Patterns

Auth middleware. Register a route middleware that pulls Authorization: Bearer <token>, decodes it, and stashes the claims on the request ($request->attributes->set('jwt_claims', $claims)). In Laravel, a dedicated JwtAuth middleware + auth:jwt guard is cleaner than sprinkling JWT::decode through controllers.

// app/Http/Middleware/JwtAuth.php
public function handle($request, Closure $next)
{
    $token = $request->bearerToken();
    if (!$token) {
        return response()->json(['error' => 'missing_token'], 401);
    }
    try {
        $request->attributes->set('jwt', JWT::decode($token, $this->key));
    } catch (\Throwable $e) {
        return response()->json(['error' => 'invalid_token'], 401);
    }
    return $next($request);
}

Custom guard / Auth::viaRequest. Wire the same decode into a guard provider so auth()->user() works normally:

Auth::viaRequest('jwt', function ($request) {
    $claims = $request->attributes->get('jwt');
    return $claims ? User::find($claims->sub) : null;
});

Claims discipline. Keep claims small and typed: sub (user id as string), iat, nbf, exp, jti (UUID for revocation lists), iss/aud when you have multiple services. Don't stuff roles/permissions into the token unless you accept that a revocation requires a token reissue — put roles in the DB lookup instead.

Issuance service. Wrap issuance in a small class (TokenIssuer) rather than calling JWT::encode in controllers. This gives you one place to change TTLs, add jti, and test.

class TokenIssuer {
    public function issue(User $user, int $ttl = 3600): string {
        $now = time();
        return JWT::encode([
            'iss' => config('app.url'),
            'sub' => (string) $user->id,
            'iat' => $now,
            'nbf' => $now,
            'exp' => $now + $ttl,
            'jti' => (string) Str::uuid(),
        ], config('jwt.secret'), 'HS256');
    }
}

Refresh flow. Two-token pattern: short-lived access token (15–60 min) + longer refresh token stored in a refresh_tokens table keyed by jti. Refresh endpoint verifies the refresh token, checks it hasn't been rotated/revoked, issues a new pair, invalidates the old jti. Because JWTs are stateless, revocation must be DB-backed — plan for it from the start.

Testing. Fake tokens in feature tests via the TokenIssuer service (call it directly in setUp or a factory). Keep one integration test that hits /login and then authenticates a protected route with the returned token — that's the path that actually breaks when you upgrade Laravel or PHP.

Gotchas and Tips

Maintenance and adoption risk. 0 stars, 0 dependents, single maintainer. This is a one-person ecosystem package, not firebase/php-jwt. Weigh it against battle-tested alternatives before you build an auth system on it — the API is likely a thin re-implementation, and API-compatible shims (firebase/php-jwt) exist. If you do use it, pin the exact version and vendor-audit before composer update.

Pin the algorithm explicitly. Never pass the algorithm from the token header into decode. Whatever the library exposes, pass 'HS256' (or your fixed algorithm) explicitly and reject tokens signed with none. Algorithm confusion is the #1 JWT vulnerability class, and low-adoption libraries are less likely to have a hardening CVE history documenting their behavior.

Key management. Put JWT_SECRET in .env (not config/jwt.php defaults), generate it with random_bytes(32) — not Str::random() without care. For multi-service setups, use asymmetric (RS256) and distribute only the public key to verifiers. Rotate keys with a kid header and a keyring, not by swapping the secret and invalidating every session.

Clock skew. nbf/exp comparisons are time()-based. If you run multiple app servers, allow 30–60s leeway (many JWT libs expose a static JWT::$leeway or a decode-option). Without it you'll see mysterious 401s on requests that cross a boundary.

Laravel 11+ bootstrapping. If the package ships a service provider, confirm it's registered — older packages use config/app.php providers (works on 11 but deprecation-warned); newer ones use auto-discovery. If it exposes a facade, check the alias is set; otherwise \Larke\JWT\Facades\JWT will 500 with a Class not found that looks like a missing dependency.

Error handling. Don't leak exception messages to the client — JWT::decode throws ExpiredException, SignatureInvalidException, BeforeValidException. Catch by type, return a generic 401, and log the type server-side. Also make sure your middleware handles malformed tokens (base64 decode failures) — these can bubble out as \Throwable, not just JWT-specific exceptions.

Debugging. The fastest way to debug a token is to paste it into jwt.io — but do not do this with production tokens (the secret on the site's demo path is only safe for test tokens). Locally, just base64-decode the payload section: json_decode(base64_decode(explode('.', $token)[1])).

Extension points to look for in the source. Larke packages typically expose: a Key class (secret + algorithm + optional kid), a Payload/claims object, and static config on JWT. If the package supports custom header injection (typ, kid, custom headers), use it for key rotation rather than post-processing the token string. If it doesn't, you'll fight it with key rotation — decide that early.

Testing gotcha. Tokens are time-sensitive. Freeze time (Carbon::setTestNow()) in tests or you'll get flaky failures when exp lands exactly on an assertion. Also assert the claims, not the token string — signatures include iat, so string equality across test runs will never pass.

Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
mrnewport/laravel-plaid
mrnewport/laravel-repo
mrnewport/laravel-docsign
mrnewport/laravel-stow
mrnewport/laravel-flow
mrnewport/laravel-priceable
mrnewport/laravel-nestedterms
fredmeng/laravel-apidoc-generator
itstructure/laravel-multilingual-tools
pdustdar/elasticsearch
markupai/php-sdk
rlacerda83/lumem-microservice-shipment
uni-method/symfony-lib
tacticmedia/scim-server-bundle
neika-ai/symfony-bundle
mattleads/agent-publishing-bundle
glavweb/framework-bundle
glavweb/extra-bundle
glavweb/api-bundle
glavweb/admin-bundle