Admin Table State Builder
Builds filter, search, pagination, and sort state for admin tables.
Function signature
ogBuildAdminTableState(request = array(), options = array())
Categories
- Admin Tools
Parameters
requestRead-only request/filter data selected by the caller for table-state normalization.optionsOptional documented policy controls for this helper.Return value
Public-safe status string returned by the function for explicit controller branching or logging.
- success
- message
- data
Compatibility
Existing function name, slug, path, and call order preserved; advertised metadata corrected to the actual source behavior.
Minimum PHP version: 7.4
Security notes
Use caller-owned allowlists and context-specific escaping; validate admin actions, export fields, privacy plans, cache keys, templates, settings, routes, and ecommerce policies before production use.
Code
<?php
/*
* Copyright (c) 2026 Jeffery L. Paris <jparis@phpog.com>.
* Free for personal and internal use. Paid project use requires visible credit
* to Jeffery L. Paris. Corporate use requires a paid license fee unless a
* separate written license states otherwise.
*/
/**
* Builds filter, search, pagination, and sort state for admin tables.
*
* Sort fields are allowlisted. Search text is normalized but must still be escaped
* for its final output context or bound as a query parameter by the caller.
*
* @param array $request Read-only request/filter values.
* @param array $options Allowed sort fields, defaults, and pagination limits.
* @return array Admin table state.
*/
function ogBuildAdminTableState($request = array(), $options = array()) {
$result = array(
'success' => false,
'message' => '',
'data' => array()
);
if (!is_array($request)) {
$result['message'] = 'Request data must be an array.';
return $result;
}
if (!is_array($options)) {
$options = array();
}
$allowed_sort_fields = array('id', 'title', 'created_at', 'updated_at');
if (!empty($options['allowed_sort_fields']) && is_array($options['allowed_sort_fields'])) {
$allowed_sort_fields = $options['allowed_sort_fields'];
}
$default_sort = 'id';
if (!empty($options['default_sort']) && in_array($options['default_sort'], $allowed_sort_fields, true)) {
$default_sort = (string)$options['default_sort'];
}
$page = 1;
if (!empty($request['page'])) {
$page = (int)$request['page'];
}
if ($page < 1) {
$page = 1;
}
$per_page = 25;
if (!empty($request['per_page'])) {
$per_page = (int)$request['per_page'];
} elseif (!empty($options['default_per_page'])) {
$per_page = (int)$options['default_per_page'];
}
if ($per_page < 1) {
$per_page = 25;
}
if ($per_page > 100) {
$per_page = 100;
}
$sort = $default_sort;
if (!empty($request['sort']) && in_array($request['sort'], $allowed_sort_fields, true)) {
$sort = (string)$request['sort'];
}
$direction = 'ASC';
if (!empty($request['direction'])) {
$direction_candidate = strtoupper(trim((string)$request['direction']));
if ($direction_candidate == 'DESC') {
$direction = 'DESC';
}
}
$search = '';
if (!empty($request['search'])) {
$search = trim(strip_tags((string)$request['search']));
$search = preg_replace('/\s+/', ' ', $search);
if (strlen($search) > 120) {
$search = substr($search, 0, 120);
}
}
$filters = array();
if (!empty($request['filters']) && is_array($request['filters'])) {
foreach ($request['filters'] as $key => $value) {
$key = preg_replace('/[^a-zA-Z0-9_]/', '', (string)$key);
if (!empty($key) && is_scalar($value)) {
$filters[$key] = trim((string)$value);
}
}
}
$offset = ($page - 1) * $per_page;
$result['success'] = true;
$result['message'] = 'Admin table state built.';
$result['data'] = array(
'page' => $page,
'per_page' => $per_page,
'offset' => $offset,
'sort' => $sort,
'direction' => $direction,
'search' => $search,
'filters' => $filters
);
return $result;
}