snakeoil
snakeoil

Reputation: 497

Symfony security / access_control, lots of redundant entries

security.yml has access_control entries and each is a combination of:

My understanding is Symfony only matches ONE per request, but this is also the highest-level place to enforce HTTPS.

So then, does this mean a duplicate rule for each unique URL pattern / role requirement?

Upvotes: 2

Views: 112

Answers (1)

yceruto
yceruto

Reputation: 9575

You're right, for each incoming request, Symfony will decide which access_control to use based on the URI, the client's IP address, the incoming "HOST NAME"!, and the request method.

But for your happiness there is a way to not duplicate the rules and achieve the same goal.


"The Special parameters.yml File"

It defines the values that usually change on each server.

First, in your local development machine, define a new parameter into app/config/parameters.yml file, let's named "requires_channel":

# in your local development machine (development)
parameters:
    database_driver: pdo_mysql
    # ...
    requires_channel: http  # <- Wow! I can use this var anywhere into my configuration :)

make the same in production server, but setting https:

# in your deployment server (production)
# app/config/parameters.yml
parameters:
    database_driver: pdo_mysql
    # ...
    requires_channel: https # <- I need enforce https redirection now in production server

Now, you can to define only one rule per entry and use your new %requires_channel% parameter:

# app/config/security.yml
security:
    # ...

    access_control:
        - { path: ^/admin, role: ROLE_ADMIN, requires_channel: '%requires_channel%' }
        # ...

%requires_channel%: its value depends to the host where running your application.

Note that host attribute is not important anymore, because it was needed to differentiate both rules before.


This solution could be done by using environments config files (config_dev.yml and config_prod.yml), but probably you need test your application for prod environment too in localhost (http). So the above solution should be enough for you ;)


I hope I've helped!

Upvotes: 1

Related Questions