The problem:
Admin generator fields that are not part of the main object are not sortable.
Example: if I have a translated Entity with a [Doctrine] schema like this:
Entity:
actAs:
I18n:
fields: [longname]
columns:
id:
type: integer(10)
primary: true
autoincrement: true
longname: string(60)
I can create a table_method that efficiently pulls in the longname field, but I cannot easily sort the results based on the longname. The table_method would have a line looking like this:
public function retrieveBackendEntityList(Doctrine_Query $q)
{
$rootAlias = $q->getRootAlias();
$q->leftJoin($rootAlias . '.Translation ct WITH (ct.lang = ?)', 'en_GB');
return $q;
}
Which means that we know the table alias of the joined table (ct) and we know the field we want to sort by (longname), which leads me to...
The solution
I propose adding a "sort_field" parameter at the "fields" level in the generator.yml files. This would allow you to say "If I click this column header, I want to sort the results by %sort_field%".
This would give you a generator.yml that looks something like this:
...
config:
fields:
longname:
sort_field: ct.longname
...
This would then be simply implemented by changing how the headers in _list_th_tabular are rendered
In this example the longname header would change FROM:
<th class="sf_admin_text sf_admin_list_th_longname">
<?php echo __('Longname', array(), 'messages') ?>
</th>
TO:
<th class="sf_admin_text sf_admin_list_th_longname">
<?php if ('ct.longname' == $sort[0]): ?>
<?php echo link_to(__('Longname', array(), 'messages'), '@category_category?sort=ct.longname&sort_type='.($sort[1] == 'asc' ? 'desc' : 'asc')) ?>
<?php echo image_tag(sfConfig::get('sf_admin_module_web_dir').'/images/'.$sort[1].'.png', array('alt' => __($sort[1], array(), 'sf_admin'), 'title' => __($sort[1], array(), 'sf_admin'))) ?>
<?php else: ?>
<?php echo link_to(__('Longname', array(), 'messages'), '@category_category?sort=ct.longname&sort_type=asc') ?>
<?php endif; ?>
</th>
Which is effectively the same as a "normal" column with native sort-ability (but using the sort_field value instead of the field's own name:
<th class="sf_admin_text sf_admin_list_th_id">
<?php if ('id' == $sort[0]): ?>
<?php echo link_to(__('Id', array(), 'messages'), '@category_category?sort=id&sort_type='.($sort[1] == 'asc' ? 'desc' : 'asc')) ?>
<?php echo image_tag(sfConfig::get('sf_admin_module_web_dir').'/images/'.$sort[1].'.png', array('alt' => __($sort[1], array(), 'sf_admin'), 'title' => __($sort[1], array(), 'sf_admin'))) ?>
<?php else: ?>
<?php echo link_to(__('Id', array(), 'messages'), '@category_category?sort=id&sort_type=asc') ?>
<?php endif; ?>
</th>
I have manually changed the code in _list_th_tabular and it all seems to work as expected. (Although I have not yet fully tested my 'solution' to the problem yet)
However, changing the admin generator to do this automatically is beyond my symfony knowledge, so I leave it to you who are wiser and more experienced to decide if this is a worthy need and then code it in accordingly.
I eagerly anticipate the fruits of your labours! (Largely because I don't want to manage lots of manually created list headers....)
Yours,
C