1
0
mirror of https://github.com/processwire/processwire.git synced 2025-08-09 08:17:12 +02:00

Fix issue processwire/processwire-issues#1243 plus some other optimizations in PageFinder

This commit is contained in:
Ryan Cramer
2020-09-14 09:03:45 -04:00
parent 9057ed25e4
commit 6cc5da1e45

View File

@@ -173,12 +173,6 @@ class PageFinder extends Wire {
'bindOptions' => array(), 'bindOptions' => array(),
); );
/**
* @var Fieldgroups|null
*
*/
protected $fieldgroups;
/** /**
* @var Fields * @var Fields
* *
@@ -196,6 +190,30 @@ class PageFinder extends Wire {
* *
*/ */
protected $sanitizer; protected $sanitizer;
/**
* @var WireDatabasePDO
*
*/
protected $database;
/**
* @var Languages|null
*
*/
protected $languages;
/**
* @var Templates
*
*/
protected $templates;
/**
* @var Config
*
*/
protected $config;
/** /**
* Whether to find the total number of matches * Whether to find the total number of matches
@@ -372,10 +390,13 @@ class PageFinder extends Wire {
*/ */
protected function init(Selectors $selectors, array $options) { protected function init(Selectors $selectors, array $options) {
$this->fieldgroups = $this->wire('fieldgroups');
$this->fields = $this->wire('fields'); $this->fields = $this->wire('fields');
$this->pages = $this->wire('pages'); $this->pages = $this->wire('pages');
$this->sanitizer = $this->wire('sanitizer'); $this->sanitizer = $this->wire('sanitizer');
$this->database = $this->wire('database');
$this->languages = $this->wire('languages');
$this->templates = $this->wire('templates');
$this->config = $this->wire('config');
$this->parent_id = null; $this->parent_id = null;
$this->templates_id = null; $this->templates_id = null;
$this->checkAccess = true; $this->checkAccess = true;
@@ -532,7 +553,7 @@ class PageFinder extends Wire {
if(count($hasParents) == 1 && !$hasSort) { if(count($hasParents) == 1 && !$hasSort) {
// if single parent specified and no sort requested, default to the sort specified with the requested parent // if single parent specified and no sort requested, default to the sort specified with the requested parent
try { try {
$parent = $this->wire('pages')->get(reset($hasParents)); $parent = $this->pages->get(reset($hasParents));
} catch(\Exception $e) { } catch(\Exception $e) {
// don't try to add sort // don't try to add sort
$parent = null; $parent = null;
@@ -603,7 +624,7 @@ class PageFinder extends Wire {
$options = $this->init($selectors, $options); $options = $this->init($selectors, $options);
$stopBeforeID = (int) $options['stopBeforeID']; $stopBeforeID = (int) $options['stopBeforeID'];
$startAfterID = (int) $options['startAfterID']; $startAfterID = (int) $options['startAfterID'];
$database = $this->wire('database'); $database = $this->database;
$matches = array(); $matches = array();
$query = $this->getQuery($selectors, $options); /** @var DatabaseQuerySelect $query */ $query = $this->getQuery($selectors, $options); /** @var DatabaseQuerySelect $query */
@@ -912,7 +933,7 @@ class PageFinder extends Wire {
// the `useSortsAfter` option is enabled and potentially applicable // the `useSortsAfter` option is enabled and potentially applicable
$sortsAfter = array(); $sortsAfter = array();
foreach($sortAfterSelectors as $n => $selector) { foreach($sortAfterSelectors as $n => $selector) {
if(!$n && $this->wire('pages')->loader()->isNativeColumn($selector->value)) { if(!$n && $this->pages->loader()->isNativeColumn($selector->value)) {
// first iteration only, see if it's a native column and prevent sortsAfter if so // first iteration only, see if it's a native column and prevent sortsAfter if so
break; break;
} }
@@ -1004,8 +1025,8 @@ class PageFinder extends Wire {
$foundTypes = null; $foundTypes = null;
$replaceFields = array(); $replaceFields = array();
$failFields = array(); $failFields = array();
/** @var Languages|null $languages */ $languages = $this->languages;
$languages = $this->wire('languages'); $fieldtypes = $this->wire()->fieldtypes;
$selectorCopy = null; $selectorCopy = null;
foreach($selector->fields() as $fieldName) { foreach($selector->fields() as $fieldName) {
@@ -1029,9 +1050,9 @@ class PageFinder extends Wire {
if(count($parts)) $subfield = implode('.', $parts); if(count($parts)) $subfield = implode('.', $parts);
} }
$fieldtype = $this->wire('fieldtypes')->get($fieldName); $fieldtype = $fieldtypes->get($fieldName);
if(!$fieldtype) continue; if(!$fieldtype) continue;
$fieldtypeLang = $languages ? $this->wire('fieldtypes')->get("{$fieldName}Language") : null; $fieldtypeLang = $languages ? $fieldtypes->get("{$fieldName}Language") : null;
foreach($this->fields as $f) { foreach($this->fields as $f) {
@@ -1064,7 +1085,7 @@ class PageFinder extends Wire {
if($selectorCopy === null) $selectorCopy = clone $selector; if($selectorCopy === null) $selectorCopy = clone $selector;
$selectorCopy->field = $fName; $selectorCopy->field = $fName;
$selectors->replace($selector, $selectorCopy); $selectors->replace($selector, $selectorCopy);
$count = $this->wire('pages')->count($selectors); $count = $this->pages->count($selectors);
$selectors->replace($selectorCopy, $selector); $selectors->replace($selectorCopy, $selector);
if($count) { if($count) {
if($foundFields === null) { if($foundFields === null) {
@@ -1324,26 +1345,31 @@ class PageFinder extends Wire {
/** @noinspection PhpUnusedLocalVariableInspection */ /** @noinspection PhpUnusedLocalVariableInspection */
list($unused, $fieldName) = explode('.', $fieldName); list($unused, $fieldName) = explode('.', $fieldName);
} }
$field = $this->wire('fields')->get($fieldName); $field = $this->fields->get($fieldName);
if(!$field) continue; if(!$field) continue;
if(!$hasTemplate && $field->template_id) { if(!$hasTemplate && ($field->get('template_id') || $field->get('template_ids'))) {
if(is_array($field->template_id)) { $templateIds = FieldtypePage::getTemplateIDs($field);
$templates = array_merge($templates, $field->template_id); if(count($templateIds)) {
} else { $templates = array_merge($templates, $templateIds);
$templates[] = (int) $field->template_id;
} }
} }
if(!$hasParent && $field->parent_id) { if(!$hasParent) {
if($this->isRepeaterFieldtype($field->type)) { /** @var int|null $parentId */
// repeater items not stored directly under parent_id, but as another parent under parent_id. $parentId = $field->get('parent_id');
// so we use has_parent instead here if($parentId) {
$selectors->prepend(new SelectorEqual('has_parent', $field->parent_id)); if($this->isRepeaterFieldtype($field->type)) {
} else { // repeater items not stored directly under parent_id, but as another parent under parent_id.
// direct parent: FieldtypePage or similar // so we use has_parent instead here
$parents[] = (int) $field->parent_id; $selectors->prepend(new SelectorEqual('has_parent', $parentId));
} else {
// direct parent: FieldtypePage or similar
$parents[] = (int) $parentId;
}
} }
} }
if($field->findPagesSelector && count($fields) == 1) $findSelector = $field->findPagesSelector; if($field->get('findPagesSelector') && count($fields) == 1) {
$findSelector = $field->get('findPagesSelector');
}
} }
if(count($templates)) $selectors->prepend(new SelectorEqual('template', $templates)); if(count($templates)) $selectors->prepend(new SelectorEqual('template', $templates));
@@ -1427,7 +1453,7 @@ class PageFinder extends Wire {
$sortSelectors = array(); // selector containing 'sort=', which gets added last $sortSelectors = array(); // selector containing 'sort=', which gets added last
$subqueries = array(); $subqueries = array();
$joins = array(); $joins = array();
$database = $this->wire('database'); $database = $this->database;
$this->preProcessSelectors($selectors, $options); $this->preProcessSelectors($selectors, $options);
$this->numAltOperators = 0; $this->numAltOperators = 0;
@@ -1528,7 +1554,7 @@ class PageFinder extends Wire {
$subfield = 'data'; $subfield = 'data';
} }
$field = $this->wire('fields')->get($fieldName); $field = $this->fields->get($fieldName);
if(!$field) { if(!$field) {
// field does not exist, see if it can be processed in some other way // field does not exist, see if it can be processed in some other way
@@ -1577,11 +1603,11 @@ class PageFinder extends Wire {
// without this section the query would still work, but a blank value must actually be present in the field // without this section the query would still work, but a blank value must actually be present in the field
$isEmptyValue = $fieldtype->isEmptyValue($field, $value); $isEmptyValue = $fieldtype->isEmptyValue($field, $value);
$useEmpty = $isEmptyValue || $operator[0] === '<' || ((int) $value < 0 && $operator[0] === '>'); $useEmpty = $isEmptyValue || $operator[0] === '<' || ((int) $value < 0 && $operator[0] === '>');
if($subfield == 'data' && $useEmpty && $fieldtype) { // && !$fieldtype instanceof FieldtypeMulti) { if($useEmpty && $fieldtype && strpos($subfield, 'data') === 0) { // && !$fieldtype instanceof FieldtypeMulti) {
if($isEmptyValue) $numEmptyValues++; if($isEmptyValue) $numEmptyValues++;
if(in_array($operator, array('=', '!=', '<', '<=', '>', '>='))) { if(in_array($operator, array('=', '!=', '<', '<=', '>', '>='))) {
// we only accommodate this optimization for single-value selectors... // we only accommodate this optimization for single-value selectors...
if($this->whereEmptyValuePossible($field, $selector, $query, $value, $whereFields)) { if($this->whereEmptyValuePossible($field, $subfield, $selector, $query, $value, $whereFields)) {
if(count($valueArray) > 1 && $operator == '=') $whereFieldsType = 'OR'; if(count($valueArray) > 1 && $operator == '=') $whereFieldsType = 'OR';
continue; continue;
} }
@@ -1786,15 +1812,15 @@ class PageFinder extends Wire {
* can potentially match blank or 0. * can potentially match blank or 0.
* *
* @param Field $field * @param Field $field
* @param string $col
* @param Selector $selector * @param Selector $selector
* @param DatabaseQuerySelect $query * @param DatabaseQuerySelect $query
* @param string $value The value presumed to be blank (passed the empty() test) * @param string $value The value presumed to be blank (passed the empty() test)
* @param string $where SQL where string that will be modified/appended * @param string $where SQL where string that will be modified/appended
* @return bool Whether or not the query was handled and modified * @return bool Whether or not the query was handled and modified
* @throws WireException
* *
*/ */
protected function whereEmptyValuePossible(Field $field, $selector, $query, $value, &$where) { protected function whereEmptyValuePossible(Field $field, $col, $selector, $query, $value, &$where) {
// look in table that has no pages_id relation back to pages, using the LEFT JOIN / IS NULL trick // look in table that has no pages_id relation back to pages, using the LEFT JOIN / IS NULL trick
@@ -1804,7 +1830,7 @@ class PageFinder extends Wire {
$ft = $field->type; $ft = $field->type;
$operator = $selector->operator; $operator = $selector->operator;
$database = $this->wire('database'); $database = $this->database;
$table = $database->escapeTable($field->table); $table = $database->escapeTable($field->table);
$tableAlias = $table . "__blank" . (++$tableCnt); $tableAlias = $table . "__blank" . (++$tableCnt);
$blankValue = $ft->getBlankValue(new NullPage(), $field); $blankValue = $ft->getBlankValue(new NullPage(), $field);
@@ -1823,6 +1849,11 @@ class PageFinder extends Wire {
if($blankIsObject) $blankValue = ''; if($blankIsObject) $blankValue = '';
if(!isset($operators[$operator])) return false; if(!isset($operators[$operator])) return false;
if($selector->not) $operator = $operators[$operator]; // reverse if($selector->not) $operator = $operators[$operator]; // reverse
if($col !== 'data' && !ctype_alnum($col)) {
// check for unsupported column
if(!ctype_alnum(str_replace('_', '', $col))) return false;
}
// ask Fieldtype if it would prefer to handle matching this empty value selector // ask Fieldtype if it would prefer to handle matching this empty value selector
if($ft->isEmptyValue($field, $selector)) { if($ft->isEmptyValue($field, $selector)) {
@@ -1840,15 +1871,17 @@ class PageFinder extends Wire {
// non-presence of row is equal to value being blank // non-presence of row is equal to value being blank
$bindKey = $query->bindValueGetKey($blankValue); $bindKey = $query->bindValueGetKey($blankValue);
if($ft->isEmptyValue($field, $value)) { if($ft->isEmptyValue($field, $value)) {
$sql = "$tableAlias.pages_id IS NULL OR ($tableAlias.data=$bindKey"; $sql = "$tableAlias.$col IS NULL OR ($tableAlias.$col=$bindKey";
} else { } else {
$sql = "($tableAlias.data=$bindKey"; $sql = "($tableAlias.$col=$bindKey";
} }
/*
if($value !== "0" && $blankValue !== "0" && !$ft->isEmptyValue($field, "0")) { if($value !== "0" && $blankValue !== "0" && !$ft->isEmptyValue($field, "0")) {
// if zero is not considered an empty value, exclude it from matching // if zero is not considered an empty value, exclude it from matching
// if the search isn't specifically for a "0" // if the search isn't specifically for a "0"
$sql .= " AND $tableAlias.data!='0'"; $sql .= " AND $tableAlias.$col!='0'";
} }
*/
$sql .= ")"; $sql .= ")";
} else if($operator === '!=' || $operator === '<>') { } else if($operator === '!=' || $operator === '<>') {
@@ -1856,26 +1889,26 @@ class PageFinder extends Wire {
// $whereType = 'AND'; // $whereType = 'AND';
if($value === "0" && !$ft->isEmptyValue($field, "0")) { if($value === "0" && !$ft->isEmptyValue($field, "0")) {
// may match rows with no value present // may match rows with no value present
$sql = "$tableAlias.pages_id IS NULL OR ($tableAlias.data!='0'"; $sql = "$tableAlias.$col IS NULL OR $tableAlias.$col!='0'";
} else if($blankIsObject) { } else if($blankIsObject) {
$sql = "$tableAlias.pages_id IS NOT NULL AND ($tableAlias.data IS NOT NULL"; $sql = "$tableAlias.$col IS NOT NULL";
} else { } else {
$bindKey = $query->bindValueGetKey($blankValue); $bindKey = $query->bindValueGetKey($blankValue);
$sql = "$tableAlias.pages_id IS NOT NULL AND ($tableAlias.data!=$bindKey"; $sql = "$tableAlias.$col IS NOT NULL AND ($tableAlias.$col!=$bindKey";
if($blankValue !== "0" && !$ft->isEmptyValue($field, "0")) { if($blankValue !== "0" && !$ft->isEmptyValue($field, "0")) {
$sql .= " OR $tableAlias.data='0'"; $sql .= " OR $tableAlias.$col='0'";
} }
$sql .= ")";
} }
$sql .= ")";
} else if($operator == '<' || $operator == '<=') { } else if($operator == '<' || $operator == '<=') {
// less than // less than
if($value > 0 && $ft->isEmptyValue($field, "0")) { if($value > 0 && $ft->isEmptyValue($field, "0")) {
// non-rows can be included as counting for 0 // non-rows can be included as counting for 0
$bindKey = $query->bindValueGetKey($value); $bindKey = $query->bindValueGetKey($value);
$sql = "$tableAlias.pages_id IS NULL OR $tableAlias.data$operator$bindKey"; $sql = "$tableAlias.$col IS NULL OR $tableAlias.$col$operator$bindKey";
} else { } else {
// we won't handle it here // we won't handle it here
return false; return false;
@@ -1884,12 +1917,11 @@ class PageFinder extends Wire {
if($value < 0 && $ft->isEmptyValue($field, "0")) { if($value < 0 && $ft->isEmptyValue($field, "0")) {
// non-rows can be included as counting for 0 // non-rows can be included as counting for 0
$bindKey = $query->bindValueGetKey($value); $bindKey = $query->bindValueGetKey($value);
$sql = "$tableAlias.pages_id IS NULL OR $tableAlias.data$operator$bindKey"; $sql = "$tableAlias.$col IS NULL OR $tableAlias.$col$operator$bindKey";
} else { } else {
// we won't handle it here // we won't handle it here
return false; return false;
} }
} }
$query->leftjoin("$table AS $tableAlias ON $tableAlias.pages_id=pages.id"); $query->leftjoin("$table AS $tableAlias ON $tableAlias.pages_id=pages.id");
@@ -1912,7 +1944,7 @@ class PageFinder extends Wire {
if(!$this->checkAccess) return; if(!$this->checkAccess) return;
// no need to perform this checking if the user is superuser // no need to perform this checking if the user is superuser
$user = $this->wire('user'); $user = $this->wire()->user;
if($user->isSuperuser()) return; if($user->isSuperuser()) return;
static $where = null; static $where = null;
@@ -1928,7 +1960,7 @@ class PageFinder extends Wire {
$cacheUserID = $user->id; $cacheUserID = $user->id;
} }
$hasWhereHook = $this->wire('hooks')->isHooked('PageFinder::getQueryAllowedTemplatesWhere()'); $hasWhereHook = $this->wire()->hooks->isHooked('PageFinder::getQueryAllowedTemplatesWhere()');
// if a template was specified in the search, then we won't attempt to verify access // if a template was specified in the search, then we won't attempt to verify access
// if($this->templates_id) return; // if($this->templates_id) return;
@@ -1954,12 +1986,12 @@ class PageFinder extends Wire {
// array of templates they are NOT allowed to access // array of templates they are NOT allowed to access
$noTemplates = array(); $noTemplates = array();
$guestRoleID = $this->wire('config')->guestUserRolePageID; $guestRoleID = $this->config->guestUserRolePageID;
$cacheUserID = $user->id; $cacheUserID = $user->id;
if($user->isGuest()) { if($user->isGuest()) {
// guest // guest
foreach($this->wire('templates') as $template) { foreach($this->templates as $template) {
if($template->guestSearchable || !$template->useRoles) { if($template->guestSearchable || !$template->useRoles) {
$yesTemplates[$template->id] = $template; $yesTemplates[$template->id] = $template;
continue; continue;
@@ -1978,7 +2010,7 @@ class PageFinder extends Wire {
$userRoleIDs[] = $role->id; $userRoleIDs[] = $role->id;
} }
foreach($this->wire('templates') as $template) { foreach($this->templates as $template) {
if($template->guestSearchable || !$template->useRoles) { if($template->guestSearchable || !$template->useRoles) {
$yesTemplates[$template->id] = $template; $yesTemplates[$template->id] = $template;
continue; continue;
@@ -1992,7 +2024,7 @@ class PageFinder extends Wire {
} }
// determine which templates the user is not allowed to access // determine which templates the user is not allowed to access
foreach($this->wire('templates') as $template) { foreach($this->templates as $template) {
if(!isset($yesTemplates[$template->id])) $noTemplates[$template->id] = $template; if(!isset($yesTemplates[$template->id])) $noTemplates[$template->id] = $template;
} }
@@ -2063,11 +2095,11 @@ class PageFinder extends Wire {
// $field = is_array($selector->field) ? reset($selector->field) : $selector->field; // $field = is_array($selector->field) ? reset($selector->field) : $selector->field;
$values = is_array($selector->value) ? $selector->value : array($selector->value); $values = is_array($selector->value) ? $selector->value : array($selector->value);
$fields = $this->wire('fields'); $fields = $this->fields;
$pages = $this->wire('pages'); $pages = $this->pages;
$database = $this->wire('database'); $database = $this->database;
$user = $this->wire('user'); $user = $this->wire()->user;
$language = $this->wire('languages') && $user->language ? $user->language : null; $language = $this->languages && $user->language ? $user->language : null;
foreach($values as $value) { foreach($values as $value) {
@@ -2150,7 +2182,7 @@ class PageFinder extends Wire {
if($field->type instanceof FieldtypePage) { if($field->type instanceof FieldtypePage) {
$blankValue = new PageArray(); $blankValue = new PageArray();
} else { } else {
$blankValue = $field->type->getBlankValue($this->wire('pages')->newNullPage(), $field); $blankValue = $field->type->getBlankValue($this->pages->newNullPage(), $field);
} }
$query->leftjoin("$table AS $tableAlias ON $tableAlias.pages_id=pages.$idColumn"); $query->leftjoin("$table AS $tableAlias ON $tableAlias.pages_id=pages.$idColumn");
@@ -2170,7 +2202,7 @@ class PageFinder extends Wire {
if(!$subValue) $subValue = 'name'; if(!$subValue) $subValue = 'name';
$tableAlias2 = "_sort_" . ($useParent ? 'parent' : 'page') . "_$fieldName" . ($subValue ? "_$subValue" : ''); $tableAlias2 = "_sort_" . ($useParent ? 'parent' : 'page') . "_$fieldName" . ($subValue ? "_$subValue" : '');
if($this->wire('fields')->isNative($subValue) && $pages->loader()->isNativeColumn($subValue)) { if($this->fields->isNative($subValue) && $pages->loader()->isNativeColumn($subValue)) {
$query->leftjoin("pages AS $tableAlias2 ON $tableAlias.data=$tableAlias2.$idColumn"); $query->leftjoin("pages AS $tableAlias2 ON $tableAlias.data=$tableAlias2.$idColumn");
$value = "$tableAlias2.$subValue"; $value = "$tableAlias2.$subValue";
if($subValue == 'name' && $language && !$language->isDefault() && $this->supportsLanguagePageNames()) { if($subValue == 'name' && $language && !$language->isDefault() && $this->supportsLanguagePageNames()) {
@@ -2182,7 +2214,7 @@ class PageFinder extends Wire {
$value = "$tableAlias2.name"; $value = "$tableAlias2.name";
} else { } else {
$subValueField = $this->wire('fields')->get($subValue); $subValueField = $this->fields->get($subValue);
if($subValueField) { if($subValueField) {
$subValueTable = $database->escapeTable($subValueField->getTable()); $subValueTable = $database->escapeTable($subValueField->getTable());
$query->leftjoin("$subValueTable AS $tableAlias2 ON $tableAlias.data=$tableAlias2.pages_id"); $query->leftjoin("$subValueTable AS $tableAlias2 ON $tableAlias.data=$tableAlias2.pages_id");
@@ -2223,7 +2255,7 @@ class PageFinder extends Wire {
if($limit) { if($limit) {
$limit = (int) $limit; $limit = (int) $limit;
$input = $this->wire('input'); $input = $this->wire()->input;
$sql = ''; $sql = '';
if(is_null($start) && $input) { if(is_null($start) && $input) {
@@ -2256,14 +2288,14 @@ class PageFinder extends Wire {
*/ */
protected function ___getQueryJoinPath(DatabaseQuerySelect $query, $selector) { protected function ___getQueryJoinPath(DatabaseQuerySelect $query, $selector) {
$database = $this->wire()->database; $database = $this->database;
$modules = $this->wire()->modules; $modules = $this->wire()->modules;
$sanitizer = $this->wire()->sanitizer; $sanitizer = $this->sanitizer;
// determine whether we will include use of multi-language page names // determine whether we will include use of multi-language page names
if($this->supportsLanguagePageNames()) { if($this->supportsLanguagePageNames()) {
$langNames = array(); $langNames = array();
foreach($this->wire()->languages as $language) { foreach($this->languages as $language) {
if(!$language->isDefault()) $langNames[$language->id] = "name" . (int) $language->id; if(!$language->isDefault()) $langNames[$language->id] = "name" . (int) $language->id;
} }
if(!count($langNames)) $langNames = null; if(!count($langNames)) $langNames = null;
@@ -2361,9 +2393,7 @@ class PageFinder extends Wire {
$values = $selector->values(true); $values = $selector->values(true);
$SQL = ''; $SQL = '';
/** @var WireDatabasePDO $database */ $database = $this->database;
$database = $this->wire('database');
/** @var Sanitizer $sanitizer */
$sanitizer = $this->sanitizer; $sanitizer = $this->sanitizer;
foreach($fields as $field) { foreach($fields as $field) {
@@ -2387,7 +2417,7 @@ class PageFinder extends Wire {
if($field == 'sort' && $subfield) $subfield = ''; if($field == 'sort' && $subfield) $subfield = '';
if($field == 'child') $field = 'children'; if($field == 'child') $field = 'children';
if($field != 'children' && !$this->wire('fields')->isNative($field)) { if($field != 'children' && !$this->fields->isNative($field)) {
$subfield = $field; $subfield = $field;
$field = '_pages'; $field = '_pages';
} }
@@ -2484,7 +2514,7 @@ class PageFinder extends Wire {
// allows selectors like 'template=my_template_name' // allows selectors like 'template=my_template_name'
$field = 'templates_id'; $field = 'templates_id';
if(count($values) == 1 && $selector->operator() === '=') $this->templates_id = reset($values); if(count($values) == 1 && $selector->operator() === '=') $this->templates_id = reset($values);
if(!ctype_digit("$value")) $value = (($template = $this->wire('templates')->get($value)) ? $template->id : 0); if(!ctype_digit("$value")) $value = (($template = $this->templates->get($value)) ? $template->id : 0);
} else if(in_array($field, array('created', 'modified', 'published'))) { } else if(in_array($field, array('created', 'modified', 'published'))) {
// prepare value for created, modified or published date fields // prepare value for created, modified or published date fields
@@ -2652,7 +2682,7 @@ class PageFinder extends Wire {
// parent_id is a path, convert a path to a parent // parent_id is a path, convert a path to a parent
$parent = $this->pages->newNullPage(); $parent = $this->pages->newNullPage();
$path = $this->sanitizer->path($parent_id); $path = $this->sanitizer->path($parent_id);
if($path) $parent = $this->wire('pages')->get('/' . trim($path, '/') . '/'); if($path) $parent = $this->pages->get('/' . trim($path, '/') . '/');
$parent_id = $parent->id; $parent_id = $parent->id;
if(!$parent_id) { if(!$parent_id) {
$query->where("1>2"); // force the query to fail $query->where("1>2"); // force the query to fail
@@ -2800,7 +2830,7 @@ class PageFinder extends Wire {
$singles = array(); $singles = array();
foreach($fields as $name) { foreach($fields as $name) {
if($this->wire('fields')->isNative($name)) { if($this->fields->isNative($name)) {
$native[] = $name; $native[] = $name;
} else { } else {
$custom[] = $name; $custom[] = $name;
@@ -2812,7 +2842,7 @@ class PageFinder extends Wire {
if(count($singles) && count($fields) > 1) { if(count($singles) && count($fields) > 1) {
// field in use that may no be combined with others // field in use that may no be combined with others
if($this->wire('config')->debug || $this->wire('config')->installed > 1549299319) { if($this->config->debug || $this->config->installed > 1549299319) {
// debug mode or anything installed after February 4th, 2019 // debug mode or anything installed after February 4th, 2019
$f = reset($singles); $f = reset($singles);
$fs = implode('|', $fields); $fs = implode('|', $fields);
@@ -2933,10 +2963,10 @@ class PageFinder extends Wire {
return false; return false;
} }
} }
$field = $this->wire('fields')->get($fieldName); $field = $this->fields->get($fieldName);
} else { } else {
$field = $this->wire('fields')->get($fieldName); $field = $this->fields->get($fieldName);
} }
if($field) { if($field) {
@@ -3019,7 +3049,7 @@ class PageFinder extends Wire {
if(!isset(self::$pagesColumns[$instanceID])) { if(!isset(self::$pagesColumns[$instanceID])) {
self::$pagesColumns[$instanceID] = array(); self::$pagesColumns[$instanceID] = array();
if($this->supportsLanguagePageNames()) { if($this->supportsLanguagePageNames()) {
foreach($this->wire()->languages as $language) { foreach($this->languages as $language) {
if($language->isDefault()) continue; if($language->isDefault()) continue;
self::$pagesColumns[$instanceID]["name$language->id"] = true; self::$pagesColumns[$instanceID]["name$language->id"] = true;
self::$pagesColumns[$instanceID]["status$language->id"] = true; self::$pagesColumns[$instanceID]["status$language->id"] = true;
@@ -3031,7 +3061,7 @@ class PageFinder extends Wire {
return self::$pagesColumns[$instanceID][$name]; return self::$pagesColumns[$instanceID][$name];
} }
self::$pagesColumns[$instanceID][$name] = $this->wire()->database->columnExists('pages', $name); self::$pagesColumns[$instanceID][$name] = $this->database->columnExists('pages', $name);
return self::$pagesColumns[$instanceID][$name]; return self::$pagesColumns[$instanceID][$name];
} }
@@ -3068,9 +3098,8 @@ class PageFinder extends Wire {
*/ */
protected function supportsLanguagePageNames() { protected function supportsLanguagePageNames() {
if($this->supportsLanguagePageNames === null) { if($this->supportsLanguagePageNames === null) {
$languages = $this->wire()->languages;
$modules = $this->wire()->modules; $modules = $this->wire()->modules;
$this->supportsLanguagePageNames = $languages && $modules->isInstalled('LanguageSupportPageNames'); $this->supportsLanguagePageNames = $this->languages && $modules->isInstalled('LanguageSupportPageNames');
} }
return $this->supportsLanguagePageNames; return $this->supportsLanguagePageNames;
} }
@@ -3168,7 +3197,7 @@ class PageFinder extends Wire {
if(empty($subfields)) $this->syntaxError("When using owner a subfield is required"); if(empty($subfields)) $this->syntaxError("When using owner a subfield is required");
list($ownerFieldName,) = explode('__owner', $fieldName); list($ownerFieldName,) = explode('__owner', $fieldName);
$ownerField = $this->wire('fields')->get($ownerFieldName); $ownerField = $this->fields->get($ownerFieldName);
if(!$ownerField) return false; if(!$ownerField) return false;
$ownerTypes = array('FieldtypeRepeater', 'FieldtypePageTable', 'FieldtypePage'); $ownerTypes = array('FieldtypeRepeater', 'FieldtypePageTable', 'FieldtypePage');
@@ -3180,7 +3209,7 @@ class PageFinder extends Wire {
// determine which templates are using $ownerFieldName // determine which templates are using $ownerFieldName
$templateIDs = array(); $templateIDs = array();
foreach($this->wire('templates') as $template) { foreach($this->templates as $template) {
if($template->hasField($ownerFieldName)) { if($template->hasField($ownerFieldName)) {
$templateIDs[$template->id] = $template->id; $templateIDs[$template->id] = $template->id;
} }
@@ -3317,7 +3346,7 @@ class PageFinder extends Wire {
if($fieldName !== null) { if($fieldName !== null) {
if(strpos($fieldName, '.')) list($fieldName,) = explode('.', $fieldName, 2); if(strpos($fieldName, '.')) list($fieldName,) = explode('.', $fieldName, 2);
if($this->wire('fields')->isNative($fieldName)) return true; if($this->fields->isNative($fieldName)) return true;
} }
if(count($fieldNames)) { if(count($fieldNames)) {