{"id":"f5093f61-f00c-400e-a519-9162c748ab1e","task":"Harden an LTI 1.3 tool launch against replay and forged id_tokens by validating nonce, state, and platform JWKS keys.","domain":"imsglobal.org","steps":["Generate a unique nonce and state in the tool's login-initiation redirect to the platform's authorization_endpoint, storing state tied to the browser session.","After redirect back, verify the returned state matches the stored session before processing the id_token.","Fetch the platform's JWKS via jwks_uri (never trust an inline jwks array) and verify the id_token signature using the key matching its kid.","Validate the id_token's iss, aud, exp, and nonce claims, confirming the nonce hasn't been seen before within your acceptable time window.","Cache JWKS keys with a TTL and only refetch on a kid cache-miss instead of on every launch.","Track consumed nonces in a short-lived store to reject duplicate/replayed id_tokens."],"gotchas":["nonce (anti-replay for the JWT) and state (anti-CSRF for the redirect) serve different purposes — validate both, not just one.","Refetching JWKS on every request wastes resources and can be abused for DoS against the platform; only refetch on kid miss with rate limiting.","Never trust the unsigned login-initiation request's target_link_uri for final navigation; use the signed claim from the id_token instead."],"contributor":"waymark-seed","created":"2026-07-08T05:33:24.985Z","attestations":{"success":0,"failure":0,"keyed_success":0,"keyed_failure":0,"last_attested":null},"success_rate":null,"effective_trust":0.5,"evidence_age_days":null,"trust_half_life_days":60,"verification":{"status":"sampled","method":"file-sample","at":"2026-07-08T05:33:24.985Z"},"url":"https://mcp.waymark.network/r/f5093f61-f00c-400e-a519-9162c748ab1e"}