A comprehensive Nette Forms extension for integrating Cloudflare Turnstile and hCaptcha with your Nette applications.
- โ Cloudflare Turnstile integration (visible, managed, invisible modes)
- โ hCaptcha integration (visible mode)
- โ PHP 8+ support
- โ Server-side validation
- โ Flexible configuration
- โ Easy form integration
- โ Customizable themes and sizes
- PHP: 8.2+
- Nette Framework: 3.0+ (limited by Nette forms 3.2 as min version)
- Extensions:
curl
orallow_url_fopen
for server-side verification
Install via Composer:
composer require drabek-digital/captcha
Register the extension in your config.neon
:
extensions:
captcha: DrabekDigital\Captcha\DI\CaptchaExtension
captcha:
type: turnstile # or hcaptcha
secretKey: your-secret-key
siteKey: your-site-key
theme: auto # light, dark, auto (optional)
size: normal # normal, compact (optional)
Option | Type | Required | Default | Description |
---|---|---|---|---|
type |
string | No | turnstile |
Captcha provider (turnstile or hcaptcha ) |
secretKey |
string | Yes | - | Your secret key from the captcha provider |
siteKey |
string | Yes | - | Your site key from the captcha provider |
verifyUrl |
string | No | - | Custom verification URL (uses default if not set) |
theme |
string | No | auto |
Theme: light , dark , or auto |
size |
string | No | normal |
Size: normal or compact |
First do not forget to render relevant JS script include in your Latte templates:
{* This will include Turnstile or hCaptcha JS code *}
{DrabekDigital\Captcha\Assets\CaptchaFrontend::getJavascriptStatic(\DrabekDigital\Captcha\Enums\CaptchaType::TURNSTILE)|noescape} {* <script src="https://challenges.cloudflare.com/turnstile/v0/api.js" async defer></script> *}
{DrabekDigital\Captcha\Assets\CaptchaFrontend::getJavascriptStatic(\DrabekDigital\Captcha\Enums\CaptchaType::HCAPTCHA)|noescape} {* <script src="https://js.hcaptcha.com/1/api.js" async defer></script> *}
{* Include local JS to make forms validation (prevent submission when verification is missing) and to show managed states labels *}
{* ... or manually link <LIBRARY PATH>/src/Assets/captcha-validation.js *}
{DrabekDigital\Captcha\Assets\CaptchaFrontend::getLocalJavascriptStatic()|noescape}
use Nette\Application\UI\Form;
$form = new Form;
// Simple captcha (required by default)
// The validator is automatically injected by the DI extension
$form->addCaptcha('captcha', 'Verify you are human');
// Handle form submission
$form->onSuccess[] = function($form) {
$values = $form->getValues();
// Process form...
};
// All supported method signatures:
// 1. Simple required visible captcha (Turnstile + hCaptcha)
$form->addCaptcha('captcha', 'Bot protection')
->setRequired(true);
// 2. Simple required visible captcha with custom required message (Turnstile + hCaptcha)
$form->addCaptcha('captcha', 'Bot protection')
->setRequired('Please verify you are human');
// 3. Simple managed captcha (only for Turnstile)
// The control + label will be rendered but the captcha can be shown or hidden based on Turnstile decision so therefore the JS code shows these messages
$form->addCaptcha('captcha', 'Bot protection')
->setManagedMessages('Check will be performed on background', Html::el('em')->setHtml('Check has been performed successfully.'));
// 4. Invisible captcha (only for Turnstile)
// The control + label will be hidden, the only thing that can be shown is required message.
$form->addCaptcha('captcha', 'Bot protection')
->setInvisible(true);
If you need to create the control manually (e.g., for testing):
use DrabekDigital\Captcha\CaptchaControl;
use DrabekDigital\Captcha\CaptchaValidator;
use DrabekDigital\Captcha\Enums\CaptchaType;
// Create validator manually
$validator = new CaptchaValidator('secret-key', 'turnstile');
// Create control (validator is the first mandatory parameter)
$captcha = new CaptchaControl($validator, 'Captcha', 'site-key', CaptchaType::TURNSTILE);
- Only implicit rendering support for both providers (primarily due to reliability).
- For hCaptcha passive mode is not supported at all (no access).
- Custom verification endpoint was not tested.
- Other captcha providers may work but will need custom JS to ensure form validation to work.
MIT License - see LICENSE file for details.
Contributions are welcome! Please feel free to submit a Pull Request, but better to consult via issues before large efforts.
For support, please create an issue on GitHub.