add a birthdate filter

This commit is contained in:
Julien Fastré 2017-01-13 21:36:06 +01:00
parent 136f78d4a9
commit cf3f23e6f2
5 changed files with 234 additions and 1 deletions

View File

@ -0,0 +1,133 @@
<?php
/*
* Copyright (C) 2017 Champs-Libres <info@champs-libres.coop>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
namespace Chill\PersonBundle\Export\Filter;
use Chill\MainBundle\Export\FilterInterface;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Validator\Context\ExecutionContextInterface;
use Symfony\Component\Validator\Constraints;
use Symfony\Component\Form\FormEvent;
use Symfony\Component\Form\FormEvents;
use Doctrine\ORM\Query\Expr;
use Chill\MainBundle\Form\Type\Export\FilterType;
use Symfony\Component\Form\FormError;
/**
*
*
* @author Julien Fastré <julien.fastre@champs-libres.coop>
*/
class BirthdateFilter implements FilterInterface
{
public function addRole()
{
return null;
}
public function alterQuery(\Doctrine\ORM\QueryBuilder $qb, $data)
{
$where = $qb->getDQLPart('where');
$clause = $qb->expr()->between('person.birthdate', ':date_from',
':date_to');
if ($where instanceof Expr\Andx) {
$where->add($clause);
} else {
$where = $qb->expr()->andX($clause);
}
$qb->add('where', $where);
$qb->setParameter('date_from', $data['date_from']);
$qb->setParameter('date_to', $data['date_to']);
}
public function applyOn()
{
return 'person';
}
public function buildForm(\Symfony\Component\Form\FormBuilderInterface $builder)
{
$builder->add('date_from', DateType::class, array(
'label' => "Born after this date",
'data' => new \DateTime(),
'attr' => array('class' => 'datepicker'),
'widget'=> 'single_text',
'format' => 'dd-MM-yyyy',
));
$builder->add('date_to', DateType::class, array(
'label' => "Born before this date",
'data' => new \DateTime(),
'attr' => array('class' => 'datepicker'),
'widget'=> 'single_text',
'format' => 'dd-MM-yyyy',
));
$builder->addEventListener(FormEvents::POST_SUBMIT, function(FormEvent $event) {
/* @var $filterForm \Symfony\Component\Form\FormInterface */
$filterForm = $event->getForm()->getParent();
$enabled = $filterForm->get(FilterType::ENABLED_FIELD)->getData();
if ($enabled === true) {
// if the filter is enabled, add some validation
$form = $event->getForm();
$date_from = $form->get('date_from')->getData();
$date_to = $form->get('date_to')->getData();
// check that fields are not empty
if ($date_from === null) {
$form->get('date_from')->addError(new FormError('This field '
. 'should not be empty'));
}
if ($date_to === null) {
$form->get('date_to')->addError(new FormError('This field '
. 'should not be empty'));
}
// check that date_from is before date_to
if (
($date_from !== null && $date_to !== null)
&&
$date_from >= $date_to
) {
$form->get('date_to')->addError(new FormError('This date '
. 'should be after the date given in "born after" field'));
}
}
});
}
public function describeAction($data, $format = 'string')
{
return array('Filtered by person\'s birtdate: '
. 'between %date_from% and %date_to%', array(
'%date_from%' => $data['date_from']->format('d-m-Y'),
'%date_to%' => $data['date_to']->format('d-m-Y')
));
}
public function getTitle()
{
return 'Filter by person\'s birthdate';
}
}

View File

@ -19,6 +19,10 @@ services:
tags:
- { name: chill.export_filter, alias: person_gender_filter }
chill.person.export.filter_birthdate:
class: Chill\PersonBundle\Export\Filter\BirthdateFilter
tags:
- { name: chill.export_filter, alias: person_birthdate_filter }
chill.person.export.filter_nationality:
class: Chill\PersonBundle\Export\Filter\NationalityFilter

View File

@ -154,6 +154,13 @@ Nationalities: Nationalités
Choose countries: Choisir les nationalités
'Filtered by nationality : %nationalities%': 'Filtré par nationalité : seulement %nationalities%'
Filter by person's birthdate: Filtrer par date de naissance de la personne
Born after this date: Nés après cette date
Born before this date: Nés avant cette date
This field should not be empty: Ce champ ne peut pas être vide
This date should be after the date given in "born after" field: Cette date doit être après la date donnée du le champ "nés après le"
"Filtered by person's birtdate: between %date_from% and %date_to%": "Filtré par date de naissance de la personne: uniquement nés entre le %date_from% et %date_to%"
## aggregators
Group people by nationality: Aggréger les personnes par nationalités
Group by level: Grouper par niveau

View File

@ -14,4 +14,8 @@ The date of closing is before the date of opening: La période de fermeture est
The birthdate must be before %date%: La date de naissance doit être avant le %date%
#export list
You must select at least one element: Vous devez sélectionner au moins un élément
You must select at least one element: Vous devez sélectionner au moins un élément
# filter by person birthdate
This field should not be empty: Ce champ ne peut pas être vide
This date should be after the date given in "born after" field: Cette date doit être après la date donnée du le champ "nés après le"

View File

@ -0,0 +1,85 @@
<?php
/*
* Copyright (C) 2017 Champs Libres Cooperative <info@champs-libres.coop>
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
namespace Chill\PersonBundle\Tests\Export\Filter;
use Chill\MainBundle\Test\Export\AbstractFilterTest;
/**
*
*
* @author Julien Fastré <julien.fastre@champs-libres.coop>
*/
class BirthdayFilterTest extends AbstractFilterTest
{
/**
*
* @var \Chill\PersonBundle\Export\Filter\BirthdateFilter
*/
private $filter;
public function setUp()
{
static::bootKernel();
$container = static::$kernel->getContainer();
$this->filter = $container->get('chill.person.export.filter_birthdate');
}
public function getFilter()
{
return $this->filter;
}
public function getFormData()
{
return array(
array(
'date_from' => \DateTime::createFromFormat('Y-m-d', '2000-01-01'),
'date_to' => \DateTime::createFromFormat('Y-m-d', '2010-01-01')
)
);
}
public function getQueryBuilders()
{
if (static::$kernel === null) {
static::bootKernel();
}
$em = static::$kernel->getContainer()
->get('doctrine.orm.entity_manager');
return array(
$em->createQueryBuilder()
->select('p.firstName')
->from('ChillPersonBundle:Person', 'p'),
$em->createQueryBuilder()
->select('p.firstName')
->from('ChillPersonBundle:Person', 'p')
// add a dummy where clause
->where('p.firstname IS NOT NULL'),
$em->createQueryBuilder()
->select('count(IDENTITY(p))')
->from('ChillPersonBundle:Person', 'p')
// add a dummy where clause
->where('p.firstname IS NOT NULL')
);
}
}