This topic contains 3 replies, has 4 voices, and was last updated by Pedro Molina 6 years, 10 months ago.
- Topic
Hello.
I’ve added some custom fields to the Account entity, using the OroExtendExtension, and I’d like them to show up on the Account DataGrid. At first, I found the yaml definition, but this didn’t seem like it was meant to be overridden. Rather, events seem to be the recommended way. This works, but it involves enough code to make me think I’m doing it wrong.
Here’s the calling code:
1234567891011121314151617181920212223242526272829303132<?phpnamespace Vdw\CrmBundle\Event\Listener;use Oro\Bundle\DataGridBundle\Event\BuildBefore;class AccountDataGridListener extends BaseDataGridListener{public function onBuildBefore(BuildBefore $event){$config = $event->getConfig();$columnOrder = ['name','contactName','contactEmail','contactPhone','ownerName','cmsName','serverName','host','updatedAt',];$this->addManyToOne($config, 'cms', 'name', 'CMS');$this->addManyToOne($config, 'server', 'name', 'Server');$this->addSimpleField($config, 'host');$this->dropFromGrid($config, 'createdAt');$this->reorderGrid($config, $columnOrder);}}And the BaseDataGridListener class, the 200-line cause of my suspicions of improper use:
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225<?phpnamespace Vdw\CrmBundle\Event\Listener;use Oro\Bundle\DataGridBundle\Datagrid\Common\DatagridConfiguration;use Symfony\Component\OptionsResolver\OptionsResolver;use Symfony\Component\OptionsResolver\OptionsResolverInterface;class BaseDataGridListener{/*** @var OptionsResolver*/protected $whereResolver;const LEFT_JOINS_PATH = '[source][query][join][left]';const SELECTS_PATH = '[source][query][select]';const FROM_PATH = '[source][query][from]';const COLUMNS_PATH = '[columns]';const SORTERS_PATH = '[sorters][columns]';const FILTERS_PATH = '[filters][columns]';public function __construct(){$this->whereResolver = $this->setWhereDefaults(new OptionsResolver());}/*** @param DatagridConfiguration $config* @param string $field* @param string $label* @param string $type* @param array $where Where to display this field. Valid keys are grid, sortBy and filterBy. Defaults to all.*/protected function addSimpleField(DatagridConfiguration $config, $field, $label = null, $type = 'string', array $where = array()){$where = $this->whereResolver->resolve($where);$selects = $config->offsetGetByPath(self::SELECTS_PATH, []);$selects[] = $selector = sprintf('%s.%s', $this->getTableAlias($config), $field);$config->offsetSetByPath(self::SELECTS_PATH, $selects);if ($where['grid']) {$columns = $config->offsetGetByPath(self::COLUMNS_PATH, []);$columns[$field] = ['label' => $label ?: ucfirst($field)];$config->offsetSetByPath(self::COLUMNS_PATH, $columns);}if ($where['sortBy']) {$sorters = $config->offsetGetByPath(self::SORTERS_PATH, []);$sorters[$field] = ['data_name' => $selector];$config->offsetSetByPath(self::SORTERS_PATH, $sorters);}if ($where['filterBy']) {$filters = $config->offsetGetByPath(self::FILTERS_PATH, []);$filters[$field] = ['data_name' => $selector, 'type' => $type];$config->offsetSetByPath(self::FILTERS_PATH, $filters);}}/*** @param DatagridConfiguration $config* @param string $field The name of the field on the owning entity* @param string $displayField The name of the field on the joined entity to display* @param string $label The label to show on the grid for the joined entity field* @param string $type The type of data stored in the joined entity field* @param array $where Where to display this field. Valid keys are grid, sortBy and filterBy. Defaults to all.*/protected function addManyToOne(DatagridConfiguration $config, $field, $displayField, $label, $type = 'string', array $where = array()){$where = $this->whereResolver->resolve($where);$leftJoins = $config->offsetGetByPath(self::LEFT_JOINS_PATH, []);$leftJoins[] = ['join' => sprintf('%s.%s', $this->getTableAlias($config), $field),'alias' => $field];$config->offsetSetByPath(self::LEFT_JOINS_PATH, $leftJoins);$selectAlias = $field.ucfirst($displayField);$selects = $config->offsetGetByPath(self::SELECTS_PATH, []);$selects[] = sprintf('%s.%s as %s', $field, $displayField, $selectAlias);$config->offsetSetByPath(self::SELECTS_PATH, $selects);if ($where['grid']) {$columns = $config->offsetGetByPath(self::COLUMNS_PATH, []);$columns[$selectAlias] = ['label' => $label];$config->offsetSetByPath(self::COLUMNS_PATH, $columns);}if ($where['sortBy']) {$sorters = $config->offsetGetByPath(self::SORTERS_PATH, []);$sorters[$selectAlias] = ['data_name' => $selectAlias];$config->offsetSetByPath(self::SORTERS_PATH, $sorters);}if ($where['filterBy']) {$filters = $config->offsetGetByPath(self::FILTERS_PATH, []);$filters[$selectAlias] = ['data_name' => $selectAlias, 'type' => $type];$config->offsetSetByPath(self::FILTERS_PATH, $filters);}}/*** Drops a column from the datagrid (and by extension, filters, sorters and the db select)** @param DatagridConfiguration $config* @param string $selectAlias*/protected function dropFromGrid(DatagridConfiguration $config, $selectAlias){$selects = $config->offsetGetByPath(self::SELECTS_PATH, []);$config->offsetSetByPath(self::SELECTS_PATH, $this->drop($selects, $selectAlias, 'value'));$columns = $config->offsetGetByPath(self::COLUMNS_PATH, []);$config->offsetSetByPath(self::COLUMNS_PATH, $this->drop($columns, $selectAlias));$sorters = $config->offsetGetByPath(self::SORTERS_PATH, []);$config->offsetSetByPath(self::SORTERS_PATH, $this->drop($sorters, $selectAlias));$filters = $config->offsetGetByPath(self::FILTERS_PATH, []);$config->offsetSetByPath(self::FILTERS_PATH, $this->drop($filters, $selectAlias));}/*** Reorder the columns of the datagrid** @param DatagridConfiguration $config* @param array $newOrder*/protected function reorderGrid(DatagridConfiguration $config, array $newOrder){$columns = $config->offsetGetByPath(self::COLUMNS_PATH, []);$config->offsetSetByPath(self::COLUMNS_PATH, $this->reorder($columns, $newOrder));$sorters = $config->offsetGetByPath(self::SORTERS_PATH, []);$config->offsetSetByPath(self::SORTERS_PATH, $this->reorder($sorters, $newOrder));$filters = $config->offsetGetByPath(self::FILTERS_PATH, []);$config->offsetSetByPath(self::FILTERS_PATH, $this->reorder($filters, $newOrder));}/*** Get the table's alias from the datagrid config** @param DatagridConfiguration $config* @return string*/protected function getTableAlias(DatagridConfiguration $config){$from = $config->offsetGetByPath(self::FROM_PATH);return $from[0]['alias'];}/*** Returns $array with all keys/values except for $search** @param array $array* @param string $search* @param string $by* @return array*/protected function drop(array $array, $search, $by = 'key'){$result = [];foreach ($array as $k => $v) {if ( ($by == 'key' && $k !== $search)|| ($by == 'value' && strpos($v, '.'.$search) === false && strpos($v, ' as '.$search) === false)) {$result[$k] = $v;}}return $result;}/*** Reorder the items in $array by $newKeyOrder** @param array $array* @param array $newKeyOrder* @return array* @throws \InvalidArgumentException*/protected function reorder(array $array, array $newKeyOrder){$expectedKeys = array_keys($array);if ($missing = array_diff($expectedKeys, $newKeyOrder)) {throw new \InvalidArgumentException('Missing orderBy keys '.implode(', ', $missing));}if ($extra = array_diff($newKeyOrder, $expectedKeys)) {throw new \InvalidArgumentException('Unrecognized orderBy keys '.implode(', ', $extra));}$result = [];foreach ($newKeyOrder as $key) {$result[$key] = $array[$key];}return $result;}protected function setWhereDefaults(OptionsResolverInterface $resolver){$resolver->setRequired(['grid','sortBy','filterBy',]);$resolver->setDefaults(['grid' => true,'sortBy' => true,'filterBy' => true,]);$resolver->setAllowedTypes(['grid' => 'bool','sortBy' => 'bool','filterBy' => 'bool',]);return $resolver;}}Does anybody know of a better way to accomplish what seems like rather basic datagrid-manipulation functionality?
The forum ‘OroCRM – Programming Questions’ is closed to new topics and replies.