0

オプションで url クエリ文字列パラメーターを介してフィルター処理されたレポートの配列を返す FlightPHP と PHPActiveRecord を使用した API に取り組んでいます。

$allowed = ['author' => 'author_id', 'owner' => 'owner_id'];
$options = build_options(Flight::request(), $allowed);
$reports = Report::all($options);

メソッド build_options は、すべてのクエリ オプションを含む配列を作成します。この場合、これらの列を削除する WHERE 句は許可されておらず、渡されなかったパラメーターは無視されます。

function build_options($request, $allowed) {
  $clauses = array_map(function($column, $value) {
    return "($column = :$value OR :$value IS NULL)";
  }, $allowed, array_keys($allowed));
  $where = implode($clauses, ' AND ');
  $params = array_intersect_key($request->query->getData(), $allowed);
  return ['conditions' => [$where, $params]];
}

この関数は、次のような WHERE 句を作成します。

(author_id = :author OR :author IS NULL) AND (owner_id = :owner OR :owner IS NULL)

しかし、PHPActiveRecord は名前付きプレースホルダーを受け入れないようです。これについて尋ねる GitHub の唯一の問題は 2010 年のものであり、クローズされました。

オプションのパラメーターを使用してクエリをエレガントにフィルター処理する他の方法はありますか?

- 編集 -

名前付きプレースホルダーなしで機能する位置プレースホルダーを使用した回避策に取り組みました。名前付きのプレースホルダーを使用したバージョンは、よりクリーンで理解しやすいと思います。

function build_options($request, $allowed) {
  $params = array_intersect_key($request->query->getData(), $allowed);
  $clauses = array_map(function($param) use ($allowed) {
    return "$allowed[$param] = ?";
  }, array_keys($params));
  $where = implode($clauses, ' AND ');
  return ['conditions' => array_merge([$where], array_values($params))];
}
4

0 に答える 0