@PostMapping(ENDPOINT_QR_VERIFY)
    @ResponseBody
    @Operation(summary = "Verify QR code token",
        parameters = {
            @Parameter(name = "token", required = true, in = ParameterIn.QUERY, description = "Session token"),
            @Parameter(name = "ticket", required = true, in = ParameterIn.QUERY, description = "Ticket id"),
            @Parameter(name = "principal", required = true, in = ParameterIn.QUERY, description = "Principal id")
        })
    public ModelAndView verifyCode(
        @RequestParam("token")
        final String sessionToken,
        @RequestParam("ticket")
        final String ticketId,
        @RequestParam("principal")
        final String principalId) throws Throwable {
        try {
            verifyQRCodeAuthenticationIsEnabled();
            val transientTicket = ticketRegistry.getTicket(ticketId, TransientSessionTicket.class);
            Assert.isTrue(transientTicket != null && !transientTicket.isExpired(), "Ticket is not found or has expired");
            Assert.isTrue(webAuthnCredentialRepository.userExists(principalId), "Principal not found");
            val principal = transientTicket.getProperty(Principal.class.getName(), Principal.class);
            val credential = new WebAuthnCredential(sessionToken);
            val session = sessionManager.getSession(WebAuthnCredential.from(credential));
            FunctionUtils.throwIf(session.isEmpty(), () -> new IllegalStateException("Session not found for the given credential"));
            val result = webAuthnCredentialRepository.getUsernameForUserHandle(session.get());
            FunctionUtils.throwIf(result.isEmpty(), () -> new IllegalStateException("Unable to locate user based on the given user handle"));
            transientTicket.putProperty(WebAuthnCredential.class.getName(), credential);
            ticketRegistry.updateTicket(transientTicket);
            return new ModelAndView(CasWebflowConstants.VIEW_ID_WEBAUTHN_QRCODE_VERIFY_DONE,
                Map.of("principal", principal, "success", true));
        } catch (final Exception e) {
            LoggingUtils.error(LOGGER, e);
            ticketRegistry.deleteTicket(ticketId);
            return new ModelAndView(CasWebflowConstants.VIEW_ID_WEBAUTHN_QRCODE_VERIFY_DONE, Map.of("success", false));
        }
    }
Verify code.

@param sessionToken the session token
@param ticketId     the ticket id
@param principalId  the principal id
@return the model and view
@throws Throwable the throwable
support/cas-server-support-webauthn-core/src/main/java/org/apereo/cas/webauthn/web/WebAuthnQRCodeController.java