Skip to content

Commit 231a309

Browse files
committed
Merge pull request #171 from tobias-93/many-to-many-filters
Fixes filtering on Many-to-many relations
2 parents 966b46a + d28e82c commit 231a309

File tree

7 files changed

+47
-4
lines changed

7 files changed

+47
-4
lines changed

Builder/Admin/BaseBuilder.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,8 @@ protected function createColumn($columnName, $withForms = false)
110110
)
111111
));
112112

113+
$column->setManyToMany($this->getFieldGuesser()->getManyToMany($this->getVariable('model'), $columnName));
114+
113115
$column->setSortType($this->getFieldGuesser()->getSortType($column->getDbType()));
114116

115117
$column->setPrimaryKey($this->getFieldOption(

Generator/Column.php

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -148,6 +148,8 @@ class Column
148148
/* Used for more verbose error messages */
149149
protected $debug = array();
150150

151+
protected $manyToMany = false;
152+
151153
/**
152154
* @param string $name
153155
* @param array $debug
@@ -438,6 +440,16 @@ public function getGridClass()
438440
return $this->gridClass;
439441
}
440442

443+
public function setManyToMany($manyToMany)
444+
{
445+
$this->manyToMany = $manyToMany;
446+
}
447+
448+
public function getManyToMany()
449+
{
450+
return $this->manyToMany;
451+
}
452+
441453
protected function parseOption($option)
442454
{
443455
if (is_array($option)) {

Guesser/DoctrineODMFieldGuesser.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,12 @@ public function getAllFields($class)
3838
return array_merge($this->getMetadatas($class)->getFieldNames(), $this->getMetadatas($class)->getAssociationNames());
3939
}
4040

41+
public function getManyToMany($model, $fieldPath)
42+
{
43+
$resolved = $this->resolveRelatedField($model, $fieldPath);
44+
return !$this->getMetadatas($resolved['class'])->isAssociationWithSingleJoinColumn($resolved['field']);
45+
}
46+
4147
/**
4248
* Find out the database type for given model field path.
4349
*

Guesser/DoctrineORMFieldGuesser.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -40,6 +40,12 @@ public function getAllFields($class)
4040
return array_merge($this->getMetadatas($class)->getFieldNames(), $this->getMetadatas($class)->getAssociationNames());
4141
}
4242

43+
public function getManyToMany($model, $fieldPath)
44+
{
45+
$resolved = $this->resolveRelatedField($model, $fieldPath);
46+
return !$this->getMetadatas($resolved['class'])->isAssociationWithSingleJoinColumn($resolved['field']);
47+
}
48+
4349
/**
4450
* Find out the database type for given model field path.
4551
*

Guesser/PropelORMFieldGuesser.php

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,16 @@ public function getAllFields($class)
4747
return $return;
4848
}
4949

50+
public function getManyToMany($model, $fieldPath)
51+
{
52+
$resolved = $this->resolveRelatedField($model, $fieldPath);
53+
$relation = $this->getRelation($resolved['field'], $resolved['class']);
54+
55+
if ($relation) {
56+
return \RelationMap::MANY_TO_MANY === $relation->getType();
57+
}
58+
}
59+
5060
/**
5161
* Find out the database type for given model field path.
5262
*

QueryFilter/DoctrineQueryFilter.php

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -80,17 +80,24 @@ public function addTextFilter($field, $value)
8080
$this->addStringFilter($field, $value);
8181
}
8282

83-
public function addCollectionFilter($field, $value)
83+
public function addCollectionFilter($field, $value, $manyToMany = false)
8484
{
8585
list($tableAlias, $filteredField) = $this->addTablePathToField($field);
86-
8786
if (!is_array($value)) {
8887
$value = array($value->getId());
8988
}
9089

9190
$paramName = $this->getParamName($tableAlias.'_'.$filteredField);
91+
92+
if ($manyToMany) {
93+
if (!in_array($filteredField, $this->joins)) {
94+
$this->query->join($tableAlias . '.' . $filteredField, $filteredField . '_table_filter_join');
95+
}
96+
$this->query->andWhere(sprintf('%s.%s IN (:%s)', $filteredField . '_table_filter_join', 'id', $paramName));
97+
} else {
98+
$this->query->andWhere(sprintf('%s.%s IN (:%s)', $tableAlias, $filteredField, $paramName));
99+
}
92100
$this->query->groupBy('q');
93-
$this->query->andWhere(sprintf('%s.%s IN (:%s)', $tableAlias, $filteredField, $paramName));
94101
$this->query->setParameter($paramName, $value);
95102

96103
}

Resources/templates/Doctrine/ListBuilderAction.php.twig

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -149,7 +149,7 @@
149149
*/
150150
protected function filter{{ filter|classify }}($queryFilter, $value)
151151
{
152-
$queryFilter->add{{ builder.fieldGuesser().dbType(model, column.filterOn)|classify }}Filter('{{ column.filterOn }}', $value);
152+
$queryFilter->add{{ builder.fieldGuesser().dbType(model, column.filterOn)|classify }}Filter('{{ column.filterOn }}', $value{{ column.manyToMany ? ', ' ~ column.manyToMany : '' }});
153153
}
154154
{% endfor %}
155155
{% endblock %}

0 commit comments

Comments
 (0)