Installation
composer require besimple/sso-auth-bundle
Add to config/bundles.php:
BeSimple\SsoAuthBundle\BeSimpleSsoAuthBundle::class => ['all' => true],
Configuration
Update config/packages/besimple_sso_auth.yaml:
besimple_sso_auth:
cas:
enabled: true
server_url: 'https://your-cas-server/login'
service_url: 'https://your-app.com/login_check'
validate_server_certificate: true
First Use Case
/login):
// src/Controller/AuthController.php
use BeSimple\SsoAuthBundle\Security\Authenticator\CasAuthenticator;
public function login(CasAuthenticator $authenticator): Response
{
return $authenticator->start('https://your-app.com/login');
}
security.yaml:
security:
firewalls:
main:
custom_authenticators:
- besimple_sso_auth.cas_authenticator
Trusted SSO (CAS)
/login → redirected to CAS server.service_url with ticket.User object.// Validate ticket manually (e.g., in a controller)
$ticket = $request->query->get('ticket');
$user = $authenticator->authenticateTicket($ticket);
Open SSO (Future-Proofing)
AuthenticatorInterface:
class OpenIdAuthenticator implements AuthenticatorInterface {
public function start($targetUrl) { /* ... */ }
public function authenticate(Request $request) { /* ... */ }
}
Register in services.yaml:
services:
App\Security\OpenIdAuthenticator:
tags: [security.authenticator]
Post-Authentication Logic
USER_PROVIDER_KEY in controllers:
public function dashboard(UserInterface $user): Response
{
// $user is hydrated by the bundle
return $this->render('dashboard.html.twig', ['user' => $user]);
}
Custom User Provider:
Override the default user provider to map CAS attributes to your User entity:
besimple_sso_auth:
cas:
user_provider: 'app.user_provider' # Service ID
// src/Service/UserProvider.php
class UserProvider implements UserProviderInterface {
public function loadUserByUsername($username) { /* ... */ }
public function refreshUser(UserInterface $user) { /* ... */ }
public function supportsClass($class) { /* ... */ }
}
CSRF Protection:
Disable CSRF for CAS endpoints if needed (not recommended for service_url):
security:
firewalls:
main:
form_login:
csrf_token_generator: security.csrf.token_manager
custom_authenticators:
- besimple_sso_auth.cas_authenticator
Logging:
Enable debug logs in config/packages/dev/besimple_sso_auth.yaml:
besimple_sso_auth:
debug: true
Certificate Validation
validate_server_certificate: false, the bundle skips SSL validation for CAS. Avoid in production unless you control the CAS server.debug: true to log certificate errors.Ticket Expiry
CasException for expired tickets:
try {
$user = $authenticator->authenticateTicket($ticket);
} catch (CasException $e) {
// Redirect to CAS login again
return $authenticator->start($request->getUri());
}
Service URL Mismatch
service_url in config must match the URL users are redirected to after CAS. Mismatches cause authentication failures.curl -v to verify redirects.User Provider Conflicts
User entity implements UserInterface and matches the attributes returned by CAS (e.g., username, email).uid but your provider expects email.Symfony 5+ Compatibility
symfony/security-bundle:^5.0 and adapt security.yaml:
firewalls:
main:
custom_authenticators:
- besimple_sso_auth.cas_authenticator
Enable Debug Mode:
besimple_sso_auth:
debug: true
Logs appear in var/log/dev.log.
Manual Ticket Validation: Test ticket validation with:
$validator = $this->container->get('besimple_sso_auth.cas_validator');
$user = $validator->validateTicket($ticket, $serviceUrl);
Common Errors:
| Error | Solution |
|---|---|
Invalid ticket |
Check service_url and CAS server configuration. |
SSL certificate problem |
Set validate_server_certificate: false (temporarily) or fix certs. |
User not found |
Implement a custom UserProvider to map CAS attributes to your users. |
Authentication failed |
Verify CAS server is reachable and server_url is correct. |
Custom Authenticators
Extend AbstractAuthenticator for new protocols (e.g., SAML):
class SamlAuthenticator extends AbstractAuthenticator {
protected function getLoginUrl(): string { /* ... */ }
protected function validateResponse($response) { /* ... */ }
}
Attribute Mapping Override the default attribute mapper:
besimple_sso_auth:
cas:
attribute_mapper: 'app.custom_attribute_mapper'
class CustomAttributeMapper implements AttributeMapperInterface {
public function mapAttributes(array $attributes): array { /* ... */ }
}
Event Listeners
Listen to cas.authenticate.success or cas.authenticate.failure:
// src/EventListener/CasListener.php
class CasListener {
public function onAuthSuccess(AuthenticateSuccessEvent $event) {
// Custom logic after successful auth
}
}
Register in services.yaml:
services:
App\EventListener\CasListener:
tags:
- { name: kernel.event_listener, event: cas.authenticate.success, method: onAuthSuccess }
Proxy Support
For CAS behind a proxy, configure PHP’s curl options:
besimple_sso_auth:
cas:
proxy: 'http://proxy.example.com:8080'
How can I help you explore Laravel packages today?