Задать вопрос
  • Что делать с code complete-ом в Symfony2?

    BoShurik
    @BoShurik Куратор тега Symfony
    Symfony developer
    Можно расширить класс контроллера, добавив туда геттеры для часто используемых сервисов, по аналогии с
    getRequest() и getDoctrine()
    В сами сервисы стараюсь не передавать контейнер, поэтому там с этим проблем нет.

    А вот как лучше добавить автокомплит для $this->getDoctrine()->getManager()->getRepository('...') сам пока не решил.
    Ответ написан
    Комментировать
  • Insert в событии postPersist?

    BoShurik
    @BoShurik Куратор тега Symfony
    Symfony developer
    Я делал так.
    class LogListener implements EventSubscriber
    {
        private $container;
    
        public function __construct(ContainerInterface $container)
        {
            $this->container = $container;
        }
    
        public function getSubscribedEvents()
        {
            return array(Events::postUpdate, Events::postPersist, Events::preRemove);
        }
    
        public function postUpdate(LifecycleEventArgs $eventArgs)
        {
            $this->log($eventArgs, Log::ACTION_UPDATE);
        }
    
        public function postPersist(LifecycleEventArgs $eventArgs)
        {
            $this->log($eventArgs, Log::ACTION_PERSIST);
        }
    
        public function preRemove(LifecycleEventArgs $eventArgs)
        {
            $this->log($eventArgs, Log::ACTION_REMOVE);
        }
    
        private function log(LifecycleEventArgs $eventArgs, $action)
        {
            $token = $this->container->get('security.context')->getToken();
            if (!$token) {
                return;
            }
    
            $user = $token->getUser();
            if (!($user instanceof User)) {
                return;
            }
    
            $entity = $eventArgs->getEntity();
            if ($entity instanceof Log) {
                return;
            }
    
            $request = $this->container->get('request');
    
            $log = new Log();
            $log->setAction($action);
            $log->setUser($user);
            $log->setIp($request->server->get('REMOTE_ADDR'));
            $log->setEntityClass(get_class($entity));
            $log->setEntityId($entity->getId());
    
            $em = $this->container->get('doctrine')->getEntityManager();
    
            $meta = $em->getClassMetadata(get_class($log));
            $conn = $em->getConnection();
    
            foreach ($meta->getReflectionProperties() as $fieldName => $reflProp) {
                if (!$meta->isIdentifier($fieldName)) {
                    $columns[] = $fieldName;
                    $values[] = ':' . $fieldName;
                }
            }
    
            $insertSql = 'INSERT INTO ' . $meta->getQuotedTableName($conn->getDatabasePlatform())
                . ' (' . implode(', ', $columns) . ') '
                . 'VALUES (' . implode(', ', $values) . ')';
    
            $stmt = $conn->prepare($insertSql);
    
            $fields = $meta->getFieldNames();
            $association = $meta->getAssociationNames();
    
            foreach ($meta->getReflectionProperties() as $fieldName => $reflProp) {
                if (!$meta->isIdentifier($fieldName)) {
                    $value = $reflProp->getValue($log);
                    if (in_array($fieldName, $fields)) {
                        $mapping = $meta->getFieldMapping($fieldName);
                        $stmt->bindValue($meta->getColumnName($fieldName), $value, $mapping['type']);
                    } else if (in_array($fieldName, $association)) {
                        $classMeta = $em->getClassMetadata($meta->getAssociationTargetClass($fieldName));
                        list($classId) = $classMeta->getIdentifier();
    
                        $mapping = $classMeta->getFieldMapping($classId);
    
                        $associationIdProperty = $classMeta->getReflectionProperty($classId);
                        $associationValue = $associationIdProperty->getValue($value);
    
                        $stmt->bindValue($meta->getColumnName($fieldName), $associationValue, $mapping['type']);
                    } else {
                        throw new \Exception('Exception in log listener');
                    }
                }
            }
    
            $stmt->execute();
        }
    }
    
    Ответ написан
    Комментировать
  • Каким образом можно сделать валидацию данных формы для логина используя Security Bundle?

    BoShurik
    @BoShurik Куратор тега Symfony
    Symfony developer
    Еще, как вариант, создать свой UserProvider
    (можно унаследовать от github.com/symfony/symfony/blob/master/src/Symfony/Bridge/Doctrine/Security/User/EntityUserProvider.php), у которого в методе loadUserByUsername сначала проверять $username на валидность.
    Ответ написан
  • Каким образом можно сделать валидацию данных формы для логина используя Security Bundle?

    BoShurik
    @BoShurik Куратор тега Symfony
    Symfony developer
    Склоняюсь ко второму варианту, но без failure_handler
    С точки зрения пользователя форма была отправлена и неважно был запрос к базе или нет.
    // src/Acme/SecurityBundle/Controller/Main;
    namespace Acme\SecurityBundle\Controller;
    
    use Symfony\Bundle\FrameworkBundle\Controller\Controller;
    use Symfony\Component\Security\Core\SecurityContext;
    
    class SecurityController extends Controller
    {
        public function loginAction()
        {
            $request = $this->getRequest();
            $session = $request->getSession();
    
            // get the login error if there is one
            if ($request->attributes->has(SecurityContext::AUTHENTICATION_ERROR)) {
                $error = $request->attributes->get(SecurityContext::AUTHENTICATION_ERROR);
            } else {
                $error = $session->get(SecurityContext::AUTHENTICATION_ERROR);
                $session->remove(SecurityContext::AUTHENTICATION_ERROR);
            }
    
            if ($error && !filter_var(SecurityContext::LAST_USERNAME, FILTER_VALIDATE_EMAIL)) {
                $error = new \Exception('Invalid e-mail');
            }
    
            return $this->render('AcmeSecurityBundle:Security:login.html.twig', array(
                // last username entered by the user
                'last_username' => $session->get(SecurityContext::LAST_USERNAME),
                'error'         => $error,
            ));
        }
    }
    


    плюс проверка на стороне пользователя
    Ответ написан
  • Клонирование строк таблицы с массивами?

    BoShurik
    @BoShurik
    Symfony developer
    Я делаю так:
    <table id="table" data-template="<tr><td><input type=«text» name=«mas[$$id$$]['name']»></td><td><input type=«text» name=«mas[$$id$$][col]»></td></tr>">
     <tr><td><input type=«text» name=«mas[1]['name']»></td><td><input type=«text» name=«mas[1][col]»></td></tr>
     <tr><td><input type=«text» name=«mas[2]['name']»></td><td><input type=«text» name=«mas[2][col]»></td></tr>
     <tr><td><input id="add" type=«button» name=«add» value=«еще»></td></tr>
    </table>
    <script type="text/javascript">
    	$(document).ready(function(){
    		$('#add').click(function(){
    			var template = $('#table').data('template');
    			var index = $('#table > tr').length;
    			template = template.replace(/\$\$id\$\$/g, index);
    			$('#table').append(template);
    		});
    	});
    </script>
    
    Ответ написан
  • Создание бандла в symfony2

    BoShurik
    @BoShurik Куратор тега Symfony
    Symfony developer
    Что выдает route:debug?
    Подозреваю там что-то вроде //helo/{name}.
    Надо «prefix: /» убрать.
    Ответ написан
    4 комментария