Fork me on GitHub

Security

Silex uses a provider, which provides the security application. It provides authentication, authorization, and other security tasks. This provider installs services such as security, security.token_storage, security.authentication_manager and others.

Silex uses Symfony2 Security component. Details can be see here.

Configuration

Provider configuration is defined in app/Resources/Config/security.yml file.

An example is shown below:

service_providers:
    security:
        class: Providers\Security\MySecurityServiceProvider
        construct_parameters:
            security.role_hierarchy:
                ROLE_ADMIN: [ 'ROLE_USER', 'ROLE_ALLOWED_TO_SWITCH']
            # http://symfony.com/doc/2.3/cookbook/security/access_control.html
            security.access_rules:
                - [ '^/admin', 'ROLE_ADMIN' ]
                - [ '^/test', 'ROLE_ADMIN' ]
                - [ '^/tasks', 'ROLE_ADMIN' ]
                - [ '^/account$', 'ROLE_USER' ]
                - [ '^/blog/new$', 'ROLE_USER' ]
                - [ '^/todo$', 'ROLE_USER' ]
                - [ '^/login$', 'IS_AUTHENTICATED_ANONYMOUSLY' ]
            security.firewalls:
                default:
                    pattern:   ^/.*$
                    # When securing only some parts of your website, 
                    # the user information are not available in non-secured areas. 
                    # To make the user accessible in such areas, 
                    # enabled the anonymous authentication mechanism
                    anonymous: true
                    # http://example.com/somewhere?_switch_user=thomas
                    # http://example.com/somewhere?_switch_user=_exit
                    switch_user: true
                    form:
                        login_path: /login
                        check_path: /login_check
                        use_referer: true
                    logout:
                        logout_path: /logout
                    users: ~

In the configuration specified user roles and their hierarchy, user access rights to resources and a method for user authentication.

If the number of users is limited (like it's your own website), the description of user identification data (login, password) can be specified in the configuration file app/Resources/Config/security.yml.

An example is shown below:

...
users:
    admin:
        - ROLE_ADMIN
        # raw password is foo
        - 5FZ2Z8QIkA7UTZ4BYkoC+GsReLf569mSKDsfods6LYQ8t+a8EW9oaircfMpmaLbPBh4FOBiiFyLfuZmTSUwzZg==
    user:
        - ROLE_USER
        # raw password is foo
        - 5FZ2Z8QIkA7UTZ4BYkoC+GsReLf569mSKDsfods6LYQ8t+a8EW9oaircfMpmaLbPBh4FOBiiFyLfuZmTSUwzZg==   
...

If the number of users can be large, as in this case, then you must define a custom User Provider for the database you are using. This provider will store the data of new users in the database.

In our case, identified three User Providers:

  1. DbalUserProvider app/Providers/Security/DbalUserProvider.php for Doctrine(DBAL)
  2. OrmUserProvider app/Providers/Security/OrmUserProvider.php for Doctrine(ORM)
  3. ArUserProvider app/Providers/Security/ArUserProvider.php for PHP ActiveRecord

Which one to choose is given in class MySecurityServiceProvider app/Providers/Security/MySecurityServiceProvider.php, which defines the class Security in the configuration file app/Resources/Config/security.yml.

service_providers:
    security:
        class: Providers\Security\MySecurityServiceProvider
...

Using

Additional functions for security applications are given in trait app/Controllers/Helper/SecurityTrait.

In our application, the user authentication is determined by action loginAction of controller class SecurityController app/Controllers/SecurityController.php by calling the form app/Views/Controller/security/login.html.twig.

In the form are two levels of validation: client level and server level.

At the client level validation is done by adding the service FormValidation.

Example of adding a validation service can be viewed below:

...
<script type="text/javascript">
    BSA.ScriptResources.push('FormValidation');
    addScriptParams('FormValidation',
            {
                form: 'form[name="login"]',
                rules: {
                    _username: {
                        required: true,
                        minlength: 3
                    },
                    _password: {
                        required: true,
                        minlength: 3
                    }
                },
                ...
            });
</script>
...