brandbaboon/cookie-consent-bundle
Installation:
composer require brandbaboon/cookie-consent-bundle
For Symfony Flex, this auto-enables the bundle. For older setups, add to config/bundles.php:
BrandBaboon\CookieConsentBundle\CookieConsentBundle::class => ['all' => true],
Routing:
Add to config/routes.yaml (Symfony 4.4+):
cookie_consent:
resource: "@CookieConsentBundle/config/routing.yaml"
For older versions, use config/routing.yml.
First Use Case: Trigger the consent dialog by adding the Twig extension to your base template:
{{ cookie_consent() }}
This renders the default banner. Customize via config/packages/cookie_consent.yaml (see below).
Edit config/packages/cookie_consent.yaml:
cookie_consent:
banner:
enabled: true
position: "bottom-right" # top-left, top-right, bottom-left, bottom-right
auto_hide: false
close_button: true
cookies:
analytics: false # Default to "deny" for analytics cookies
marketing: false
statistics: false
functional: true # Functional cookies (e.g., CSRF) are often exempt
storage:
driver: "cookie" # or "session"
name: "cookie_consent"
lifetime: 31536000 # 1 year in seconds
Test the Banner:
Visit your site. The banner should appear (if enabled: true).
Click "Accept All" or toggle individual cookies. Verify cookies are set via browser dev tools (Application > Cookies).
Check Consent Status: In Twig, display consent status:
{% if cookie_consent('analytics') %}
{# Load analytics script #}
<script src="analytics.js"></script>
{% endif %}
Use the CookieConsentService to check consent dynamically:
use BrandBaboon\CookieConsentBundle\Service\CookieConsentService;
class AnalyticsController extends AbstractController
{
public function trackEvent(CookieConsentService $consent): Response
{
if (!$consent->isAllowed('analytics')) {
return $this->json(['error' => 'Analytics disabled'], 403);
}
// Proceed with tracking
}
}
Extend the default Twig template:
vendor/brandbaboon/cookie-consent-bundle/Resources/views/banner.html.twig to templates/cookie_consent/banner.html.twig.<div class="custom-consent-banner">
<p>{{ banner.text }}</p>
<button class="accept-all">{{ banner.accept_all }}</button>
</div>
Define custom cookie groups in config:
cookie_consent:
cookies:
custom_group:
label: "Custom Features"
description: "Enable for personalized content"
default: false
Access in Twig:
{% if cookie_consent('custom_group') %}
{# Load custom scripts #}
{% endif %}
Google Analytics: Use a Twig include to conditionally load scripts:
{% if cookie_consent('analytics') %}
{% include 'google_analytics.html.twig' %}
{% endif %}
API Requests: Pass consent status via headers or query params:
$response = $client->request('GET', '/api/data', [
'headers' => [
'X-Consent-Analytics' => $consent->isAllowed('analytics') ? '1' : '0',
],
]);
For SPAs or AJAX-heavy apps, use the CookieConsentService in JavaScript:
// Fetch consent status via API
fetch('/api/cookie-consent-status')
.then(response => response.json())
.then(data => {
if (data.analytics) {
loadAnalytics();
}
});
Create a controller endpoint:
#[Route('/api/cookie-consent-status', name: 'api_cookie_consent_status')]
public function getConsentStatus(CookieConsentService $consent): JsonResponse
{
return $this->json([
'analytics' => $consent->isAllowed('analytics'),
'marketing' => $consent->isAllowed('marketing'),
]);
}
Cookie Lifetime:
lifetime: 31536000 (1 year) may conflict with GDPR’s "right to erasure." Shorten for stricter compliance:
lifetime: 2592000 # 30 days
Storage Driver:
session storage resets on session expiry. Use cookie for persistence across devices/browsers.Default Values:
default: true for any cookie group automatically accepts it. Avoid for sensitive cookies like analytics.Caching:
X-Consent-Analytics) are respected. Add to varnish.vcl:
if (req.http.X-Consent-Analytics == "0") {
return (pass);
}
Banner Not Showing:
enabled: true in config.{{ dump(cookie_consent) }} to a template).Consent Not Persisting:
storage.driver is set to cookie or session.Application > Cookies) for cookie_consent cookie.CSRF Token Issues:
functional cookies are allowed by default:
cookies:
functional: true
Localization:
Customize banner text per locale in translations/messages.en.yaml:
cookie_consent:
banner:
text: "We use cookies to improve your experience."
accept_all: "Accept All"
customize: "Customize"
Conditional Loading: Lazy-load non-critical scripts after consent:
document.addEventListener('DOMContentLoaded', function() {
if (getCookieConsent('analytics')) {
loadScript('analytics.js');
}
});
Extension Points:
cookie_consent.save event:
$eventDispatcher->addListener('cookie_consent.save', function (CookieConsentEvent $event) {
// Log consent changes or sync to a database
});
BrandBaboon\CookieConsentBundle\Storage\StorageInterface for database storage.Testing:
cookie_consent cookie and verify the banner reappears.auto_hide: true to ensure the banner disappears after user interaction.Performance:
{% if cookie_consent('marketing') %}
<script src="ads.js" defer></script>
{% endif %}
How can I help you explore Laravel packages today?