Skip to content

[Security] Add simpler customization options #6069

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 7 commits into from
Jun 13, 2013

Conversation

Seldaek
Copy link
Member

@Seldaek Seldaek commented Nov 19, 2012

The goal of this is to provide a simpler extension point for people that don't have the time to dive into the whole security factory + authentication provider + user provider + authentication listener + token mess. As it stands, it gives you a way to just create one class that is handling all the security stuff in one (by implementing SimpleFormAuthenticatorInterface and UserProviderInterface) + one or more token classes.

I would like feedback on whether people think this makes sense or not before continuing and doing a SimpleHttpAuthenticatorInterface for non-form based stuff.

Just FYI that's how it would look in security.yml:

security:
    providers:
        simple:
            id: simple_authenticator
    firewalls:
        foo:
            pattern: ^/
            simple_form:
                provider: simple
                authenticator: simple_authenticator

/cc @atrauzzi (who posted a long rant on the ML about how hard this all is, and I can't agree more - I hope it's the right account on github?)

@dlsniper
Copy link
Contributor

👍 for this, the security component is indeed too much to handle by new people as well as it takes some time to get it right :)

@althaus
Copy link
Contributor

althaus commented Nov 20, 2012

Nice idea. The security component is the one part I try to avoid to dug into by using FOSUserBundle. It is quite complex and the regarding doc pages haven't been at the required level of helpfullness to understand easily what is working in which way (at lest the last time I checked).

So big 👍 for the RFC!

@carlos-granados
Copy link

When I started using Symfony one and a half years ago, the security component is the one that gave me more headaches. I soon was very proficient in everything but security still seemed a bit of a monster. I still have to go back to the book and reread it carefully when I need to do security stuff. It is great to have all these security options but I am sure that the needs of 90% of the people are pretty basic and we could certainly use a class that provided a simple implementation for those 90% of cases. So, I´d say to go ahead

@MasterB
Copy link
Contributor

MasterB commented Nov 20, 2012

Yes. But in practice I use only the Form based authentication.


public function supports(TokenInterface $token, $providerKey);

public function handleAuthenticationFailure(GetResponseEvent $event, AuthenticationException $exception);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This method seems unused

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah I was pondering registering a failure handler automatically and calling that on failure, but not sure yet. Things have to be discussed.

@stof
Copy link
Member

stof commented Nov 20, 2012

how would your authenticator looks like ?

@Seldaek
Copy link
Member Author

Seldaek commented Nov 20, 2012

Here is the sample authenticator + user provider I used for building this, it can only authenticate one hardcoded user but obviously you could hook in anything: https://gist.github.com/4117358

@frosas
Copy link
Contributor

frosas commented Nov 21, 2012

@Seldaek this gist looks nice. Maybe an abstract class implementing these interfaces with some sane default methods would be interesting too.

Anyway the hardest thing to me about the Security component is to understand how it works in the details. Do I need to use a user provider? ("security.providers" section being required in the configuration suggests so). Do I have to implement the UserInterface in my user class? What if I can't loadUserByUsername() because I also need a password to load it? Is it okay to return a made-up user instance in these cases or I shouldn't because then I break the interface as I can't know when to throw a UsernameNotFoundException? Do I have to create and register a Factory if the setup is so specific I'll hardly ever reuse it?

Reading the code helps to figure out these things but it is complex (as it is the problem it solves) and is hard to know if one understands and uses it correctly (which is not fun, specially talking about security).

@catchamonkey
Copy link
Contributor

@Seldaek 👍 for the RFC and that gist is much closer to how a lot of devs want to use it, nice and simple and clear what is going on.

I agree with @frosas in that it's not just knowing what you need to do to get something working, but you want to know the inner details of what parts do what, and what the actual flow of each part is, when is refreshUser called, what effect does it have etc.

I've only got familiar with this sort of thing by speaking in person with Johannes and working through some actual implementations of some more advanced usage. But I can imagine a lot of people wouldn't persevere, they would simply use something else which would be a real shame, so I applaud your efforts and work here.

@atrauzzi
Copy link

👍!

This approach looks a lot more inviting on the surface already. I won't be 100% certain until I get a chance to play with it, but I'd like to see the dust settle first before making an attempt to use it.

I just finished implementing my authentication requirements in a Rails project using Warden. ( https://gist.github.com/0748686eadcf6de51b64 ) The nicest thing it did for me was set up a simple situation where I'm being given all the information, and creating a user and returning it if everything checks out.

Obviously Rails is a lot more willy-nilly than Symfony - but this feels more like that arrangement with the added benefit of the specific authentication data being nicely encapsulated in a token.

So long as registering the custom authentication providers isn't too difficult, this will do nicely!

@evillemez
Copy link

Anything that makes the Security Component seem like less of a mess is good. I say +1 to this this so people can start using a more understandable API with a clearer extension point. Eventually, if we get solid APIs that are generally well-received, Security could (maybe) be refactored to make the underlying implementation less complicated, if possible. Maybe the underlying implementation is already perfect, but the documentation needs to be much better at explaining why it does what it does, and how to use/extend it effectively.

If your needs for a security implementation are fairly basic, right now I think it's hard to justify the complexity of the Security Component when implementing your own simple system might be less work than learning how to effectively extend the current component, and ends up being far less complicated.

Security is one of those pieces you need to understand thoroughly, regardless of implementation. So anything to help on that front is a worthy effort.

This seems to address #5933

@atrauzzi
Copy link

@evillemez Agreed! I've maintained throughout this that the security system in Symfony 2 is well conceived. It's just the implementation and documentation that I think set people up for some hurt.

The best anecdote/lesson here is that I picked up RoR and brought my project up to speed in less time than the time I lost trying to work with Symfonys security component. That includes getting my authentication requirements implemented.

While I tend to prefer the designs found in Symfony, there's obviously something to be said about ease of use. ;)

@Seldaek
Copy link
Member Author

Seldaek commented Apr 12, 2013

Pushed an update to this PR:

  • added a simple_token firewall/factory/whole-shebang for API-key and other usages that don't fit well with user/password forms. You just get a Request in this case and decide what to do with it.
  • renamed a few methods to try and make more sense.

You can check a demo implementation of it in my symfony-standard fork, simplesecurity branch. Here is the diff: Seldaek/symfony-standard@4f7a61c...simplesecurity

This allows you to access the secured area like:

Next step I want to do is add success_handler & failure_handler support to both, called by default on the authenticator service, and perhaps allow them to be configured to some other service like the form_login currently allows. After that I think we have a solid base and it should be documented, but I'm obviously open to any feedback regarding naming or anything else.

@Seldaek
Copy link
Member Author

Seldaek commented Apr 12, 2013

I updated the PR. Things are looking good now, success and failure handlers are supported without configuration (if you implement it it gets called). There is one issue left however, something I must have messed up prevents the two from being used together (if you do, the form login stops working). No time to finish this tonight, but I'll try to get back to it soon, and if anyone has an idea what might cause this please say so.

@althaus
Copy link
Contributor

althaus commented Apr 13, 2013

Looks great so far. I've got one question, cause I had my issues to implement it with the standard form_login: Would it be easy to extend the form itself? Like adding extra fields and use them easily for authentication.

@Seldaek
Copy link
Member Author

Seldaek commented Apr 15, 2013

@althaus you get the Request in the createToken() method, so you should store all information needed from the request into a custom token class, and then use that information authenticateToken() to verify the user. It should indeed be possible this way, and I would be happy if you'd try it and give feedback.

@patwcummins
Copy link

I miss the simple security setup from Symfony 1. Users, permissions and roles with YML to indicate the security per action.

The new features in Symfony 2 are powerful, but too complicated for rapid prototyping.

@bnewton
Copy link

bnewton commented May 1, 2013

I agree with patwcummins security features within Symfony 2 are powerful, much too complicated for rapid prototyping. In my opinion authenticating against a web service should be a lot easier.

@catchamonkey
Copy link
Contributor

I don't think it's that complicated to actually do, it's just getting your head around it all so you know what to do.

@Seldaek
Copy link
Member Author

Seldaek commented May 6, 2013

@catchamonkey yeah but that's the thing, the factory, authentication provider and authentication listener are regrouped into one zero-configuration thing with this PR. This reduces the cognitive overhead quite a bit, and doesn't restrict you so much. I think most things can still be achieved this way.

That said, it's not gonna be as easy as sf1 i guess.

@catchamonkey
Copy link
Contributor

@Seldaek yeah I get that, and definitely think this is a great inclusion, it would have certainly helped when I started, and it's good to have for the quick POC apps too.

fabpot added a commit that referenced this pull request Jun 13, 2013
This PR was merged into the master branch.

Discussion
----------

[Security] Add simpler customization options

The goal of this is to provide a simpler extension point for people that don't have the time to dive into the whole security factory + authentication provider + user provider + authentication listener + token mess. As it stands, it gives you a way to just create one class that is handling all the security stuff in one (by implementing SimpleFormAuthenticatorInterface and UserProviderInterface) + one or more token classes.

I would like feedback on whether people think this makes sense or not before continuing and doing a SimpleHttpAuthenticatorInterface for non-form based stuff.

Just FYI that's how it would look in security.yml:

```yaml
security:
    providers:
        simple:
            id: simple_authenticator
    firewalls:
        foo:
            pattern: ^/
            simple_form:
                provider: simple
                authenticator: simple_authenticator
```

/cc @atrauzzi (who posted a long rant on the ML about how hard this all is, and I can't agree more - I hope it's the right account on github?)

Commits
-------

74cfc84 marked some classes as being experimental in 2.3
471e5bc [Security] allowed simple pre-auth to be optional if another auth mechanism already authenticated the user
01c913b moved the simple HTTP authenticator to a pre-auth one
887d9b8 fixed wrong Logger interface
65335ea [Security] Renamed simple_token to simple_http, added support for failure and success handler to both simple firewalls
f7a11a1 [Security] Add simple_token auth method
1fe2ed6 [Security] Add SimpleForm authentication
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.