Symfony中用户安全页面的最佳方法?

I have for example table in database:

News:
id | user_id | title | body

and CRUD:

public function executeIndex(sfWebRequest $request)
public function executeNew(sfWebRequest $request)
public function executeShow(sfWebRequest $request)
public function executeCreate(sfWebRequest $request)
public function executeEdit(sfWebRequest $request)
public function executeUpdate(sfWebRequest $request)
public function executeDelete(sfWebRequest $request)
protected function processForm(sfWebRequest $request, sfForm $form)

How is the best method for secure this? I would like that USER can Edit, Update and Delete only own News. I can make this - get current ID user and compare with user_id from News and next redirect. Maybe i can make this with preExecute or in yaml file?

I used to do such a thing.

I choose to extend User class (myUser.class.php in application lib directory) with method can($what, Doctrine_Record $with), also declared few types of update types, like: const UPDATE = 'update'; and others, in the same way.

After that in preExecute() I've retrieved the currently requested object, in your case - News object, and calling if (!$this->getUser()->can(myUser::UPDATE, $news)) { /* redirect or whatever */ }.

As you can see, it's very easy readable and maintanable.

This way you have all access logic in one, method - can(), where you can specify any logic you need.

Hope, that helps you.

For your example, can() method would be something like:

switch(get_class($with))
{
    case 'News':
        if ($with->getUserId() != $this->getProfile()->getId()) // Assuming that getProfile() gives me a User class which News record is referenced
        {
            switch ($what)
            {
                case self::UPDATE:
                    return false;
                case self::DELETE:
                    return false;
            }
        }
        else
        {
            return true; // The user is owner - he can do whatever he want.
        }
        break;
    default:
        return false; // or true, don't know what you need
}

I did much the same. But I am not extending the sfUser class. I used the filter chain http://www.symfony-project.org/book/1_2/06-Inside-the-Controller-Layer#chapter_06_filters of symfony and wrote my own SecurityFilter which was able to parse the route configuration.

I added an option to the specific route of my routing.yml

contact_list:
  url: /contacts/:usergroup
  param: { module: contacts, action: index }
    options: { securityManager: UsergroupListSecurityManager }

for example: The securityFilter now uses an instance of UsergroupListSecurityManager to find out whether it is allowed to display the page.

So I was able to set a default "securityManager" and define any specific "securityManagers" on specific routes - I also was able to reuse some "securityManager" on different routes and in other contexts (creating contextmenu or toolbar).