Browser widget in. One-time token out.
The browser receives only a public site key. Your server keeps the secret key and redeems each signed token exactly once.
1. Add the widget
Use your public site key and a stable action name. Identify the controller and provide working privacy and alternative-verification links.
Your public site key
<glint-proof
site-key="gp_site_YOUR_KEY"
action="signup"
controller-name="Your company"
privacy-url="https://example.com/privacy"
alternative-url="https://example.com/verify-another-way"
></glint-proof>
<script async src="https://glintproof.com/widget.js"></script>2. Receive the token
Listen for the verified event and send the token with your form. If you do not use an alternative URL, handle the alternative event and open an equivalent route yourself.
const widget = document.querySelector('glint-proof');
widget
.addEventListener('glintproof:verified', ({ detail }) => {
form.elements.glintproofToken.value = detail.token;
});
widget.addEventListener('glintproof:alternative', () => {
showEmailOrPasskeyVerification();
});3. Verify on your server
Call siteverify with your secret key. Never call this endpoint from browser code.
const check = await fetch('https://glintproof.com/api/siteverify', {
method: 'POST',
headers: {
'Authorization': `Bearer ${process.env.GLINTPROOF_SECRET_KEY}`,
'Content-Type': 'application/json'
},
body: JSON.stringify({ token: req.body.glintproofToken, action: 'signup' })
});
const result = await check.json();
if (!result.success) throw new Error('Human check failed');Successful response
{ "success": true, "action": "signup", "score": 91, "verifiedAt": "2026-07-15T12:00:00.000Z" }Production checklist
- Bind the verified token to the protected form or action.
- Keep the secret key server-side and rotate it if exposed.
- Offer passkey, email, trusted-device, or support alternatives.
- Add edge rate limits and passive risk signals for high-value actions.
- Name the controller, link its privacy notice, and document the legal basis before launch.