Tools For Better Developers

Osm Admin: Filters

2022 January Osm Admin

4 months ago ∙ 3 minutes read

Note. This feature is being implemented, and some details are likely to change.

In the user interface, you can narrow displayed data using grid column filters, or filters displayed in the sidebar. To enable that, apply #[Filter\*] attributes to class properties.

Applied filters appear in the URL query parameters, for example, .../edit?id=5+16+19, and on the page.

You can apply filters not only to a grid page, but also to a form page - to mass edit all matching objects, or to an action URL (edit, delete, or custom) - to perform the action on all matching objects.

In the same way, you can apply filters to the API URLs in order to retrieve or modify matching objects in a script.

Let's examine filters in more detail:

Defining Filterable Properties

To make a filterable property, add a #[Filter\*] attribute to it. For example:

use Osm\Admin\Base\Attributes\Filter;
use Osm\Admin\Base\Attributes\Interface_;
use Osm\Admin\Base\Attributes\Table;
use Osm\Admin\Base\Attributes\Storage;
use Osm\Admin\Base\Traits\Id;
use Osm\Core\Attributes\Serialized;
use Osm\Core\Object_;
...    
/**
 * @property ?int $color_id #[
 *      Serialized,
 *      Table\Int_(unsigned: true, references: 'colors.id', 
 *          on_delete: 'set null'),
 *      Filter\Options,
 * ]
 */
#[Storage\Table('products'), Interface_\Table\Admin('/products', 'Product')]
class Product extends Object_ {
    use Id;
}

Note. The id property, defined in the Id trait, is also filterable.

Filters In User Interface

Currently, I focus on making filters work. Displaying filter options will be implemented later.

However, let's list different ways a user will apply filters visually in the grid/form user interface.

Grid Column Filters

In a grid, columns that are based on a filterable property will display the filter options in the column context menu. It will look similar to Excel or Google Sheets column filters.

If a filterable property is not shown as a grid column, its filter options will appear in the sidebar. It will look similar to the filters displayed in this blog.

Row Filter

In a grid, the user can select one or more rows, and use the Edit action - to open the selection in the mass-editing form, use the Delete action - to delete selected objects, or perform another custom action on selected objects.

Alternatively, the user can select everything and then deselect one or more rows, and use the edit, delete or custom action.

Either way, selected rows will add the id filter to the requested action URL.

Search Filter

Finally, the user can enter a search phrase in the header of the admin area, and it will be added to the grid URL as the q (full-text search) filter.

Filter Syntax

Applied filters will be added to the URL of the grid page, the edit page, or an action route in a form of URL query parameters.

Different types of filters use different syntax.

Option Filters

Option filters, for example the color_id property defined above, allow applying one or more predefined options. The applied options are added to the URL query parameter using the + character as a delimiter:

# edit products having one of specified colors assigned
/products/edit?color_id=5+3+7

# delete products having one of specified colors assigned
/products/delete?color_id=3

Alternatively, you can select all available options and deselect some. In this case, only the deselected options are added to the URL query parameter, and the parameter name has - modifier:

# edit products NOT having any of specified colors assigned
/products/edit?color_id-=3+5

Range Filters

Range filters, for example product price, allow applying one or more value ranges. The applied range is added using .. delimiter. Multiple ranges are combined using the + character as a delimiter:

# edit products having price within the specified ranges
/products/edit?price=..10.51+10.99..30+100..

Note that you can omit one of the range ends using ..N or N.. syntax.

As in an option filter, you can apply all ranges except selected ones:

# edit products NOT having price within any of the specified ranges
/products/edit?price-=..10.51+10.99..30+100..

Boolean Filters

Boolean Filters, for example product enabled, are on, off, or not applied:

# edit enabled products
/products/edit?enabled

# edit disabled products
/products/edit?enabled-

Combining Multiple Filters

Combine multiple filters using & character:

# edit enabled products having one of specified colors assigned
/products/edit?enabled&color_id=5+3+7

Reflection

Filters are introduced in the Osm\Admin\Filters\Module, and they are a part of the class definition:

global $osm_app;

$colorFilter = $osm_app->schema
    ->classes[Product::class]
    ->filters['color_id'];