DB\Jig\Mapper::find PHP Method

find() public method

Return records that match criteria
public find ( $filter = NULL, array $options = NULL, $ttl, $log = TRUE ) : static[] | FALSE
$filter array
$options array array
$ttl int
$log bool
return static[] | FALSE
    function find($filter = NULL, array $options = NULL, $ttl = 0, $log = TRUE)
    {
        if (!$options) {
            $options = [];
        }
        $options += ['order' => NULL, 'limit' => 0, 'offset' => 0];
        $fw = \Base::instance();
        $cache = \Cache::instance();
        $db = $this->db;
        $now = microtime(TRUE);
        $data = [];
        if (!$fw->get('CACHE') || !$ttl || !($cached = $cache->exists($hash = $fw->hash($this->db->dir() . $fw->stringify([$filter, $options])) . '.jig', $data)) || $cached[0] + $ttl < microtime(TRUE)) {
            $data = $db->read($this->file);
            if (is_null($data)) {
                return FALSE;
            }
            foreach ($data as $id => &$doc) {
                $doc['_id'] = $id;
                unset($doc);
            }
            if ($filter) {
                if (!is_array($filter)) {
                    return FALSE;
                }
                // Normalize equality operator
                $expr = preg_replace('/(?<=[^<>!=])=(?!=)/', '==', $filter[0]);
                // Prepare query arguments
                $args = isset($filter[1]) && is_array($filter[1]) ? $filter[1] : array_slice($filter, 1, NULL, TRUE);
                $args = is_array($args) ? $args : [1 => $args];
                $keys = $vals = [];
                $tokens = array_slice(token_get_all('<?php ' . $this->token($expr)), 1);
                $data = array_filter($data, function ($_row) use($fw, $args, $tokens) {
                    $_expr = '';
                    $ctr = 0;
                    $named = FALSE;
                    foreach ($tokens as $token) {
                        if (is_string($token)) {
                            if ($token == '?') {
                                // Positional
                                $ctr++;
                                $key = $ctr;
                            } else {
                                if ($token == ':') {
                                    $named = TRUE;
                                } else {
                                    $_expr .= $token;
                                }
                                continue;
                            }
                        } elseif ($named && token_name($token[0]) == 'T_STRING') {
                            $key = ':' . $token[1];
                            $named = FALSE;
                        } else {
                            $_expr .= $token[1];
                            continue;
                        }
                        $_expr .= $fw->stringify(is_string($args[$key]) ? addcslashes($args[$key], '\'') : $args[$key]);
                    }
                    // Avoid conflict with user code
                    unset($fw, $tokens, $args, $ctr, $token, $key, $named);
                    extract($_row);
                    // Evaluate pseudo-SQL expression
                    return eval('return ' . $_expr . ';');
                });
            }
            if (isset($options['order'])) {
                $cols = $fw->split($options['order']);
                uasort($data, function ($val1, $val2) use($cols) {
                    foreach ($cols as $col) {
                        $parts = explode(' ', $col, 2);
                        $order = empty($parts[1]) ? SORT_ASC : constant($parts[1]);
                        $col = $parts[0];
                        if (!array_key_exists($col, $val1)) {
                            $val1[$col] = NULL;
                        }
                        if (!array_key_exists($col, $val2)) {
                            $val2[$col] = NULL;
                        }
                        list($v1, $v2) = [$val1[$col], $val2[$col]];
                        if ($out = strnatcmp($v1, $v2) * (($order == SORT_ASC) * 2 - 1)) {
                            return $out;
                        }
                    }
                    return 0;
                });
            }
            $data = array_slice($data, $options['offset'], $options['limit'] ?: NULL, TRUE);
            if ($fw->get('CACHE') && $ttl) {
                // Save to cache backend
                $cache->set($hash, $data, $ttl);
            }
        }
        $out = [];
        foreach ($data as $id => &$doc) {
            unset($doc['_id']);
            $out[] = $this->factory($id, $doc);
            unset($doc);
        }
        if ($log && isset($args)) {
            if ($filter) {
                foreach ($args as $key => $val) {
                    $vals[] = $fw->stringify(is_array($val) ? $val[0] : $val);
                    $keys[] = '/' . (is_numeric($key) ? '\\?' : preg_quote($key)) . '/';
                }
            }
            $db->jot('(' . sprintf('%.1f', 1000.0 * (microtime(TRUE) - $now)) . 'ms) ' . $this->file . ' [find] ' . ($filter ? preg_replace($keys, $vals, $filter[0], 1) : ''));
        }
        return $out;
    }