環境
サーバー:AWS(Amazon Linux)
PHPバージョン:5.4.28
フレームワーク:CakePHP(v2.8)
前提・実現したいこと
Searchプラグインを使って検索機能を実装したい。
ただしテーブル名とモデル名とでは名前が異なる。
(モデル名がTicket、テーブル名がQuestions)
詳細
Questionsテーブルのtitleという列に対して部分一致検索をしたいと考えております。
以下のURLでアクセスされた際に、title列に"foo"という文字列が含まれるレコードを取得したいです。
https://example.com/tickets?title=foo
TicketのController/Model/Viewを新規に作成し、TicketモデルをQUESTIONSテーブルに紐付けられればと考えています。
上記の実装をする理由
上記のURLの通りTicketという名前のモデルとして検索したいのですが、既存のシステムではこれをQuestionというモデルで実装しています。
DB上の物理テーブル名もQUESTIONSというテーブルに実装されており、今からQuestion→Ticketとモデル名を変更するのは工数の関係からも
不可能と見ています。
また既存のサイトにはすでに以下のURLがあり、今回作成する機能とは別の機能として存在します。
https://example.com/questions?title=foo
発生している問題・エラーメッセージ
作成した検索フォームに"foo"と打ち込むと、以下のURLにリダイレクトされます。
https://example.com/tickets?title=foo
しかし検索結果には"foo"を含まないレコードも表示されます。
色々変更してみたのですが、どうしても解決方法が分かりません。
該当のソースコード
php:
1<?php 2App::uses('View', 'View'); 3class TicketsController extends AppController{ 4 5 public $uses = array("Question","Ticket"); 6 public $components = array("Paginator","Search.Prg"); 7 public $autoRender = true; 8 public $layout = "main"; 9 public $presetVars = true; 10 11 public function index(){ 12 /* ...全ページ共通の処理... */ 13 14 //検索条件をパース 15 $this->Prg->commonProcess("Ticket"); 16 $condition = $this->Ticket->parseCriteria($this->Prg->parsedParams()); 17 18 //上記検索条件に「公開」の状態になっていることを追加 19 $condition = array_merge($condition, array("open" => true)); 20 21 /* この時点の$conditionをdebug表示させると、GETパラメータが 22 * ?title=fooとなっている場合でもarray("open"=>true)しか格納されていない 23 * 従ってGETパラメータtitleが認識されていないのではないかと思われる。 24 * 25 * しかし、$this->request->queryにはtitle=>fooが格納されている。 26 */ 27 28 /* ... 以降、Ticketに固有の処理... */ 29 30 //ページネーションの設定 31 $this->Paginator->settings = array( 32 "limit" => 10, 33 "order" => array("Question.created"=>"desc"), 34 "conditions" => $condition, 35 "paramType" => "querystring", 36 ); 37 38 //画面に表示 39 $this->set(array( 40 "Tickets" => $this->Paginator->paginate("Question"), 41 "me" => $me, 42 "canonical_url" => LINE_BASE_URL."/tickets/", 43 "queryparams" => $this->request->query, 44 )); 45 } 46}
php:Ticket.php
1<?php 2class Ticket extends AppModel{ 3 public $name = "Question"; 4 public $actsAs = array('Search.Searchable'); 5 6 public $filterArgs = array( 7 "title" => array( 8 "type"=>"like", 9 "field"=>array("Question.title"), 10 ), 11 ); 12}
php:index.ctp
1<!-- フォーム部分を抜粋 --> 2<div class="search"> 3 <?= $this->Form->create("POST", array("url"=>"index")) ?> 4 <table> 5 <tr> 6 <th>チケット名で検索</th> 7 <td><?= $this->Form->input("Ticket.title", array("label"=>false, "div"=>false)) ?></td> 8 </tr> 9 </table> 10 <?= $this->Form->end("検索") ?> 11</div> 12 13<!-- ページネーション部分を抜粋 --> 14<div class="pagenation"> 15 <?php 16 $this->paginator->options(array( 17 "url" => array( 18 "?" => $queryparams // 設定しないとページ遷移した時に検索条件がなくなる 19 ) 20 )); 21 ?> 22 <?= $this->paginator->numbers(array( 23 "first" => 1, // 「最初のページへ戻る」のリンクの数 24 "last" => 1, // 「最後のページへ行く」のリンクの数 25 "ellipsis" => " ... ", // 省略していることを表すための文字列 26 "separator" => " | ", // ページングリンクを分割する際に表示されるもの 27 "modulus" => 5, // ページングとして表示する数 28 "tag" => "", // リンクを囲むタグ 29 )); ?> 30</div>
あなたの回答
tips
プレビュー