Instantly share code, notes, and snippets.
Created
August 31, 2012 21:05
-
Star
(3)
3
You must be signed in to star a gist -
Fork
(1)
1
You must be signed in to fork a gist
-
Save somatonic/3558974 to your computer and use it in GitHub Desktop.
Find related pages using Fieldtype Page for tagging. Returns PageArray with added property "score" for later use.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
/** | |
* TagsHelper ProcessWire2.+ Module | |
* | |
* | |
* @author Soma | |
* modified 2012/08/31 | |
* | |
* ProcessWire 2.x | |
* Copyright (C) 2010 by Ryan Cramer | |
* Licensed under GNU/GPL v2, see LICENSE.TXT | |
* | |
* http://www.processwire.com | |
* http://www.ryancramer.com | |
* | |
* | |
* | |
*/ | |
class TagsHelper extends WireData implements Module { | |
/** | |
* getModuleInfo is a module required by all modules to tell ProcessWire about them | |
* | |
* @return array | |
* | |
*/ | |
public static function getModuleInfo() { | |
return array( | |
'title' => 'Tags Helper', | |
'version' => 1, | |
'summary' => 'Finds related pages using a Fieltype Page field with multiple tags. Returns PageArray with added [score] property to page objects or null if none found. Usage: $result = $pages->findRelated( Page $page, PageArray $tags, string $field [, string $tmpl, int $limit] );', | |
'href' => '', | |
'singular' => true, | |
'autoload' => true | |
); | |
} | |
public function init() { | |
// add method to $pages var | |
$this->addHook('Pages::findRelated', $this, 'findRelated'); | |
} | |
/** | |
* Find related pages using Page reference field | |
* | |
* findRelated( Page $page, PageArray $tags, string $field [, string $tmpl, int $limit] ); | |
* | |
* @param HookEvent $event | |
* @return PageArray|null | |
*/ | |
public function findRelated( HookEvent $event ) { | |
// get arguments | |
$page = $event->arguments[0]; | |
if(!$page->id) throw new WireException("findRelated() Error: first argument page is not found."); | |
$tags = $event->arguments[1]; | |
$field = $event->arguments[2]; | |
//$tmplq = isset($event->arguments[3]) ? ",template=".$event->arguments[3] : ''; | |
if(isset($event->arguments[3])){ | |
$tmpl = $event->arguments[3]; | |
if(strpos($tmpl,"|") !== false){ | |
$tmpls = explode("|",$tmpl); | |
foreach($tmpls as $t) { | |
if( $tt = wire("templates")->get($t) ) | |
$tmplIDs[] = $tt->id; | |
else throw new WireException("findRelated() Error: template '$t' could not be found."); | |
} | |
$tmplq = " AND pages.templates_id in(" . implode(',',$tmplIDs) . ")"; | |
} else { | |
$tmplID = wire("templates")->get($tmpl)->id; | |
$tmplq = " AND pages.templates_id=$tmplID"; | |
} | |
} else { | |
$tmplq = ''; | |
} | |
$limit = isset($event->arguments[4]) ? $event->arguments[4] : 100; | |
/* mysql plain query method, this way we can sort multiple rows | |
----------------------------------------------------------------- */ | |
if(count($tags) < 1) return $event->return = null; | |
foreach($tags as $tag) $tagIDs .= "$tag->id,"; | |
$tagIDs = substr($tagIDs,0,-1); | |
$query = " | |
SELECT data,pages_id,modified, COUNT(pages_id) as score | |
FROM field_$field LEFT JOIN pages ON (field_$field.pages_id=pages.id) | |
WHERE field_$field.data in($tagIDs) | |
AND field_$field.pages_id != $page->id AND pages.status < 2048 $tmplq | |
GROUP BY pages_id | |
ORDER BY score DESC, modified DESC | |
LIMIT $limit"; | |
$res = $this->db->query($query); | |
if(!$res->num_rows) return $event->return = null; | |
$pa = new PageArray(); | |
while($r = $res->fetch_object()){ | |
$pa->add(wire("pages")->get($r->pages_id)->set("score",$r->score)); | |
} | |
$event->return = $pa; | |
/* PW query method, this way we can only sort on one field | |
----------------------------------------------------------------- */ | |
/* | |
foreach($tags as $tag) { | |
$found = wire("pages")->find("$field=$tag,id!=$page->id,limit=$limit" . $tmplq); | |
foreach($found as $r) $rel[$r->id]++; | |
} | |
// if none found return | |
if(empty($rel)) return $event->return = null; | |
// build PageArray and add "score" property | |
$pa = new PageArray(); | |
foreach($rel as $key => $score) { | |
$pa->add( wire('pages')->get($key)->set("score",$score) ); | |
} | |
$event->return = $pa; | |
*/ | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment