intro
Zend_Search_Luceneを利用した単純な検索処理の実装例です。
デモサイトより動作を確認できます。
ただし、日本語では動作確認していません。日本語でのLuceneの利用についてはこちらのブログが参考になります。
デモサイトより動作を確認できます。
ただし、日本語では動作確認していません。日本語でのLuceneの利用についてはこちらのブログが参考になります。
1.検索処理実行クラスの作成
以下のように
Webに公開されているローカルファイルから検索を行うためのクラスです。
library/My/Search/Lucene.php
ファイルを作成します。Webに公開されているローカルファイルから検索を行うためのクラスです。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 |
<?php require_once 'Zend/Search/Lucene.php'; class My_Search_Lucene { private $__baseUrl = null; private $__path = null; private $__pattern = null; private $__indexPath = null; public function __construct($baseUrl, $path, $pattern, $indexPath) { $this->__baseUrl = $baseUrl; $this->__path = $path; $this->__pattern = $pattern; $this->__indexPath = $indexPath; } public function getBaseUrl() { return $this->__baseUrl; } public function getPath() { return $this->__path; } public function getPattern() { return $this->__pattern; } public function getIndexPath() { return $this->__indexPath; } public function createIndex() { $path = rtrim(str_replace('\\', '/', realpath($this->getPath())), '/'); $files = $this->__glob($path, $this->getPattern()); $baseUrl = rtrim($this->getBaseUrl(), '/'); $index = Zend_Search_Lucene::create($this->getIndexPath()); foreach ($files as $file) { /* For html documents. */ $docUrl = $baseUrl . str_replace('\\', '/', substr($file, strlen($path))); $doc = Zend_Search_Lucene_Document_Html::loadHTMLFile($file); $doc->addField(Zend_Search_Lucene_Field::Text('url', $docUrl)); /* For general documents, use the following code instead of the above. $docContent = file_get_contents($file); $docUrl = $baseUrl . str_replace('\\', '/', substr($file, strlen($path))); $doc = new Zend_Search_Lucene_Document(); $doc->addField(Zend_Search_Lucene_Field::Text('url', $docUrl)); $doc->addField(Zend_Search_Lucene_Field::Text('title', $docUrl)); $doc->addField(Zend_Search_Lucene_Field::Text('body', $docContent)); */ $index->addDocument($doc); } } public function search($query) { if (!file_exists($this->getIndexPath())) { $this->createIndex(); } $index = Zend_Search_Lucene::open($this->getIndexPath()); $args = func_get_args(); $results = call_user_func_array(array($index, 'find'), $args); return $results; } private function __glob($path, $pattern) { // see http://jp.php.net/glob $paths=glob($path.'/*', GLOB_MARK|GLOB_ONLYDIR|GLOB_NOSORT); $files=glob($path.'/'.$pattern); if ($files === FALSE) { $files = array(); } foreach ($paths as $path) { $path = rtrim(str_replace('\\', '/', $path), '/'); $files=array_merge($files, $this->__glob($path, $pattern)); } return $files; } } |
2.コントローラの作成
以下のように
定数を環境に応じて変更してください。
application/constorllers/Lucene.php
ファイルを作成します。定数を環境に応じて変更してください。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 |
<?php require_once 'Zend/Controller/Action.php'; require_once 'Zend/Form.php'; require_once 'My/Search/Lucene.php'; class LuceneController extends Zend_Controller_Action { const DOC_DIR = 'c:/temp/lucene/'; const BASE_URL = '/doc/'; const INDEX_PATH = 'c:/temp/index'; const PATTERN = '*.html'; public function indexAction() { $form = $this->_getSearchForm(); $this->view->form = $form; } public function createAction() { $lucene = new My_Search_Lucene( LuceneController::BASE_URL, LuceneController::DOC_DIR, LuceneController::PATTERN, LuceneController::INDEX_PATH ); $lucene->createIndex(); } public function searchAction() { $form = $this->_getSearchForm(); if ($form->isValid($_POST)) { $values = $form->getValues(); $lucene = new My_Search_Lucene( LuceneController::BASE_URL, LuceneController::DOC_DIR, LuceneController::PATTERN, LuceneController::INDEX_PATH ); $query = Zend_Search_Lucene_Search_QueryParser::parse($values['query']); $this->view->results = $lucene->search($query); $this->view->query = $query; } else { $this->view->results = array(); } $this->view->form = $form; } protected function _getSearchForm() { $form = new Zend_Form(array( 'method' => 'post', 'action' => $this->_helper->url->url(array('action'=>'search')), 'elements' => array( 'query' => array('text', array( 'required' => true, 'label' => 'Query', )), 'submit' => array('submit', array( 'label' => 'Search', )) ), )); return $form; } } |
3.ビューの作成
以下のように
application/views/scripts/lucene/index.phtml
ファイルを作成します。
1 2 3 4 |
<div><?php echo '<a href="' . $this->url(array('action'=>'create')) . '">Create Index</a>'; ?></div> <div><?php echo $this->form; ?></div> |
以下のようにapplication/views/scripts/lucene/create.phtml
ファイルを作成します。
1 |
<div>Index file has been created.</div> |
以下のようにapplication/views/scripts/lucene/search.phtml
ファイルを作成します。
1 2 3 4 5 6 7 8 9 10 11 12 |
<div><?php echo $this->form; ?></div> <div> <ul> <?php foreach ($this->results as $result) { echo '<li><a href="' . $result->url . '">' . $result->title . '</a>'; echo '(' . $result->score . ')</li>'; } ?> </ul> </div> |
5.確認
Webサーバにアクセスし、インデックスの作成や検索処理が行えることを確認してください。
履歴
日付 | 内容 |
---|---|
2009/1/15 | 公開 |