If you encounter this error message on a Symfony2 project, you just have to install php5-intl module
apt-get install php5-intl
And don’t forget to restart apache
service apache2 restart
If you encounter this error message on a Symfony2 project, you just have to install php5-intl module
apt-get install php5-intl
And don’t forget to restart apache
service apache2 restart
For some really good reasons or, doctrine2 do not implement the RAND() fonction to sort randomly your query results. Here some dirty ways to do it. Don’t use them it’s bad.
One solution is to shuffle your collection of rows using php
public function getRandom($max = 10,$site) { $results = $this->createQueryBuilder('u') ->where('u.site = :site') ->setParameter('site', $site) ->orderBy('u.sort', 'DESC') ->setMaxResults($max) ->getQuery() ->getResult(); shuffle($results); return $results; }
In this solution, you retrieve the last 10 rows and shuffle them after. Peformances are not too bad but you will always retrieves the same last rows from your table.
Another solution is to use the array_rand php fonction
public function getRandom($site) { $results = $this->createQueryBuilder('u') ->where('u.site = :site') ->setParameter('site', $site) ->orderBy('u.sort', 'DESC') ->getQuery() ->getResult(); $result2 = array_rand($results); return $result2; }
In this case you fetch all rows from your table, this could be slow and memory consuming…
If you need to retrieve only one row, you can use somethinfg like this
public function getOneRandom() { $em = $this->getEntityManager(); $max = $em->createQuery(' SELECT MAX(q.id) FROM questions q ') ->getSingleScalarResult(); return $em->createQuery(' SELECT q FROM questions q WHERE q.id >= :random ORDER BY q.id ASC ') ->setParameter('random',rand(0,$max)) ->setMaxResults(1) ->getSingleResult(); }
This solution can only be used if you want to retrieve any of the tables rows, if you add a filtrer you may return an empty result.
This solution is not dirty it just use 2 queries instead of one. the tips is to use the offset. And you can use a filter !!!
$qCount = Doctrine::getTable('Questions') ->createQuery() ->select('count(*)') ->where('site = :site') ->setParameter('site', $site) ->fetchOne(array(), Doctrine::HYDRATE_NONE); $question = Doctrine::getTable('Questions') ->createQuery() ->select('*') ->where('site = :site') ->setParameter('site', $site) ->limit(1) ->offset(rand(0, $qCount[0] - 1)) ->fetchOne();
And you still can use native queries : http://docs.doctrine-project.org/en/latest/reference/native-sql.html
You are trying to setup a custom validator on Sonata and you get this error :
Fatal error: Declaration of Adin\AdminBundle\Admin\AnnonceAdmin::validate() must be compatible with that of Sonata\AdminBundle\Admin\AdminInterface::validate() in /home/www/arlogis/src/Adin/AdminBundle/Admin/AnnonceAdmin.php on line 250
Don’t panic, just add this at the begining of your class
use Sonata\AdminBundle\Validator\ErrorElement;
in our example it’s in this file : /AdminBundle/Admin/AnnonceAdmin.php
With Doctrine2 you cannot override save method but you can execute preUpdate() method.
See below how to implement it.
On your entity class, for example AdminBundle/Entity/Annonce.php, add the HasLifecycleCallbacks annontation
/** * @ORM\Entity(repositoryClass="Tripix\AdminBundle\Repository\AnnonceRepository") * @ORM\HasLifecycleCallbacks */
And your method, with the annotation
/** @ORM\PreUpdate() */ public function preUpdate() { $this->created_at = new \DateTime("now"); }
That’s all, it should works.
A complete example, just in case :
<?php namespace Tripix\AdminBundle\Entity; use Doctrine\ORM\Mapping as ORM; use Symfony\Component\Validator\Constraints as Assert; use Doctrine\Common\Collections\ArrayCollection; /** * @ORM\Entity(repositoryClass="Tripix\AdminBundle\Repository\AnnonceRepository") * @ORM\HasLifecycleCallbacks */ class Annonce { /** @ORM\PreUpdate() */ public function preUpdate() { $this->created_at = new \DateTime("now"); } public function __construct() { $this->created_at = new \DateTime("now"); $this->visuels = new ArrayCollection(); }
It is possible to change templates use by default.
First, override the controller action method, in your AdminBundle/Controller/SecteurAdminController.php file
/** * return the Response object associated to the list action * * @return Response */ public function listAction() { if (false === $this->admin->isGranted('LIST')) { throw new AccessDeniedException(); } $datagrid = $this->admin->getDatagrid(); $formView = $datagrid->getForm()->createView(); // set the theme for the current Admin Form $this->get('twig')->getExtension('form')->setTheme($formView, $this->admin->getFilterTheme()); //custom code from here $total = 0; $enable = 0; $new = 0; $site = $this->admin->site; $repository = $this->getDoctrine()->getRepository('TripixAdminBundle:Annonce'); $total = $repository->getNombreAnnonceTotal($site); $enable = $repository->getNombreAnnonceEnabled($site); $new = $repository->getNombreAnnonceNew($site); return $this->render('TripixAdminBundle:CRUD:list_secteur.html.twig', array( 'action' => 'list', 'form' => $formView, 'datagrid' => $datagrid, 'total' => $total, 'enable' => $enable, 'new' => $new, )); }
The import thing on previous code is the render() fonction, the first parameter is the template to use.
In our example, the template file will be /AdminBundle/Ressources/view/CRUD/list_secteur.html.twig
You can use the /AdminBundle/Ressources/view/CRUD/base_secteur.html.twig file as example for your custom template.
Parent function to override on the controller are here : /vendor/bundles/Sonata/AdminBundle/Controller/CRUDController.php
To add a custom column on a page list, just follow these steps. In the example, we will add a “Nombre d’annoce(s)” column.
On your admin class file (ex: /AdminBundle/Admin/SecteurAdmin.php), on your configureListFields() fonction, add a new entry on the listMapper object
/** * @param \Sonata\AdminBundle\Datagrid\ListMapper $listMapper * @return void */ protected function configureListFields(ListMapper $listMapper) { $listMapper ->addIdentifier('titre') ->add('Tri', 'string', array('template' => 'TripixAdminBundle:Admin:list_tri.html.twig')) ->add('Nb', 'string', array('label' => 'Nombre d\'annonce(s)', 'template' => 'TripixAdminBundle:Admin:list_nb_annonce.html.twig')) ->add('_action', 'actions', array( 'actions' => array( 'edit' => array(), 'delete' => array(), ) )) ; }
This new entry said to use the TripixADminBundle:Admin:list_tri.html.twig template.
Now, create your template file (list_nb_annonce.html) in the /AdminBundle/ressources/view/admin/ directory.
{% extends 'SonataAdminBundle:CRUD:base_list_field.html.twig' %} {% block field%} {% if admin.datagrid.results|length > 1 %} <div> <strong>{{ object.getNombreAnnonce}}</strong> </div> {% endif %} {% endblock %}
In our example, getNombreAnnonce() is not defined, let’s do it
In the /adminBundle/Entity/Secteur.php file, add
public function getNombreAnnonce() { return count($this->getAnnonces()); }
That’s all.
You are using sonata and want to validate some fields.
You innocently add the validate function to your Admin file
function validate(ErrorElement $errorElement, $object) { }
Then, you get this error :
Fatal error: Declaration of Adin\AdminBundle\Admin\AnnonceAdmin::validate() must be compatible with that of Sonata\AdminBundle\Admin\AdminInterface::validate() in /home/www/arlogis/src/Adin/AdminBundle/Admin/AnnonceAdmin.php on line 251
You checked to AdminInterface file the declaration is the same.
To fix it, you need to use additionnal namespace :
use Sonata\AdminBundle\Validator\ErrorElement; use Symfony\Component\Validator\ValidatorInterface;
An important function is missing on twig : file_exists.
I will show you here how to define a new function for twig.
On your namespace/bundle, add a Twig/Extension directory and create your class file :
/src/Adin/ArlogisBundle/Twig/Extension/FileExistsExtension.php
<?php namespace Adin\ArlogisBundle\Twig\Extension; class FileExistsExtension extends \twig_Extension { /** *Return the function registered as twig extension * *@return array */ public function getFunctions() { return array( 'file_exists' => new \Twig_Function_Function('file_exists'), ); } public function getName() { return 'adin_file_exists'; } } ?>
You then have to register your service, add a
<?xml version="1.0" ?> <container xmlns="http://symfony.com/schema/dic/services" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://symfony.com/schema/dic/services http://symfony.com/schema/dic/services/services-1.0.xsd"> <services> <service id="adin.twig.tripix_extension" class="Adin\ArlogisBundle\Twig\Extension\FileExistsExtension"> <tag name="twig.extension" /> </service> </services> </container>
It’s ready, you can use it on your twig template
{% if file_exists('/var/www/image.jpg') %} File exists {% else %} File not exists {% endif %}
Be carefull, you need to specify the absolute path of the file. You can create a twig global variable root_path.
app/config/config.yml
# Twig Configuration twig: globals: root_path: %kernel.root_dir%/../web
Then on twig template
{% if file_exists({{root_path}}'/var/www/image.jpg') %} File exists {% else %} File not exists {% endif %}
You are using the fanstactic Gregwar/ImageBundle code to manipulate your images on Symfony2 and twig.
But instead of rendering your website, you get this error on your apache error log file
PHP Fatal error: Method Gregwar\\ImageBundle\\ImageHandler::__toString() must not throw an exception in /home/www/recette/app/cache/dev/classes.php on line 7426
or directly on your html genered code
<img src=" Fatal error: Method Gregwar\ImageBundle\ImageHandler::__toString() must not throw an exception in /home/www/recette/app/cache/dev/classes.php on line 7426
this issue may be a rights problem on your cache drectory. By default, gregwar cache directory is on your web so, launch this command
chmod 777 web/cache
This error may also occur if the file doesn’t exist, for a clean code, add
{% if file_exists('uploads/' ~ site.id ~ '.jpg') %} {{ image(site.picture).resize(250, 50) }} {% endif %}
or on twig code
{% if site.has_picture %} {{ image(site.picture).resize(250 ,50) }} {% endif %}
For more informations about file_exists, see here Symfony2 twig add new function file_exists
After installing Symfony 2 instead of viewing your website, you see this error message :
You need to enable either the SQLite3 or PDO_SQLite extension for the profiler to run properly.
It probably means you need to install the sqlite extension for php
apt-get install php5-sqlite
restart apache and that should to the tricks.