2

PDO で実行して印刷するクエリを正常に取得しましたが、ここで何か間違ったことをしています。この質問のコードの重要な部分は、コードの最後の数ブロックにあります。わかりやすくするために、最初の部分を含めています。

このコードは、複数の入力フィールドを持つ HTML フォームに接続します。PHP は、WHERE ステートメントで各フィールドのデータに AND を追加して、クエリを作成します。

これは私をスローするものです: $query 変数をエコーし​​、クエリが適切に形成されていることを確認できますが、クエリ結果を印刷しようとすると、結果が印刷されません。

ここではプリペアド ステートメントの使用に取り組み、さまざまな数のパラメーターを使用してプリペアド ステートメントを作成できなかったため、最初にそれらを使用せずにコードを動作させることを試みることにしました。この投稿の助けを借りて、試してみました: PDO 準備済みステートメントを使用して、検索フィールドから複数のキーワードを使用する LIKE クエリ

それで、今のところ準備された声明を脇に置いて、誰かが私がここで間違っていることを教えてもらえますか? どんな助けでも大歓迎です。

<?php
if(isset($_POST['submit'])) {

// define the list of fields
$fields = array('titleSearch', 'keywordSearch', 'fullSearch', 'fromYear', 'toYear', 
    'fromSeconds', 'toSeconds', 'withSound', 'withColor');
$conditions = array();

// loop through the defined fields
foreach($fields as $field){
    // if the field is set and not empty
    if(isset($_POST[$field]) && $_POST[$field] != '') {
        // create a new condition, using a prepared statement
        $conditions[] = "$field LIKE CONCAT ('%', $_POST[$field], '%')";
    }
}

// build the query
$query = "SELECT keyframeurl, videoid, title, creationyear, sound, color, 
     duration, genre FROM openvideo ";

// if there are conditions defined, append them to the query
if(count($conditions) > 0) {
    $query .= "WHERE " . implode(' AND ', $conditions);
}

//confirm that query formed correctly
echo $query; 

//print query results
foreach ($dbh->query($query) as $row){
   print $row['videoid'].' - '.$row['title'].'<br />';
}
}
?>
4

4 に答える 4

1

クエリを投稿する代わりに、それを実行する必要があります。
それが問題を解決する唯一の方法です

  • スタック オーバーフローの通行人は、クエリを実行するためのデータベース サーバーを頭の中に持っていません。
  • スタック オーバーフローの通行人は、クエリを実行するための特定のデータベース サーバーを頭の中に持っていません。

したがって、データベースに対してクエリを実行し、何が問題なのかを尋ねることができるのは、あなただけです。

  1. エラー報告をオンにします。エラーが発生したことを確認できることを確認してください。意図的なエラーを追加して、それが機能するかどうかを確認してください。
  2. 必要な値が実際に含まれているかどうか、データベース データを再確認してください。
  3. データベースの値と本当に一致する場合は、入力データを再確認してください。
  4. コンソールまたはphpadminでデータベースに対して組み立てられたクエリを実行します。

特定の問題を掘り下げます。ただ座って待ってはいけません。「動作しないコードがあります」という質問をすることはほとんど意味がありません。コードをじっと見つめるのではなく、実行する必要があります。

于 2013-04-09T19:54:31.507 に答える
1

クエリに直接挿入している $_POST 値を囲む引用符を忘れました。

$conditions[] = "$field LIKE CONCAT ('%', '$_POST[$field]', '%')";
                                          ^--            ^--

したがって、これで当面の問題は解決されますが、SQL インジェクション攻撃に対しては依然として無防備です。

于 2013-04-09T18:54:21.120 に答える
-1

組み込み関数さえ必要ありません。CONCAT文字列全体を としてモデル化できます$conditions[] = "{$field} LIKE '%{$_POST[$field]}%'"。ただし、短期的に深刻な SQL インジェクション攻撃に直面したくない場合は、準備済みステートメントを使用する必要があります。

このようなことを試してみませんか?(例として PDO を使用):

if ($pdo = new \PDO("mysql:host=localhost;dbname=testdb;charset=utf8", "user", "password")) {
    $fields = ["titleSearch","keywordSearch","fullSearch","fromYear","toYear","fromSeconds","toSeconds","withSound","withColor"];
    $parameters = array_map(function ($input) { return filter_var($input, FILTER_SANITIZE_STRING); }, $fields)
    $conditions = array_map(function ($input) { return (!empty($_POST[$input]) ? "{$input} LIKE ?" : null); }, $fields);
    $query = "SELECT `keyframeurl`,`videoid`,`title`,`creationyear`,`sound`,`color`,`duration`,`genre` FROM `openvideo`" . (sizeof($conditions) > 0 ? " " . implode(" AND ", $conditions) : null);

    if ($statement = $pdo->prepare($query, [\PDO::ATTR_CURSOR => \PDO::CURSOR_FWDONLY])) {
        if ($statement->execute((!empty($parameters) ? $parameters : null))) {
            $result = $statement->fetchAll(\PDO::FETCH_ASSOC);
        }
    }
}

テストしていませんが(今思いついたばかりです)、PDOを設定し、探していると思われる条件に基づいてステートメントを準備し、execute()メソッドにパラメーターを追加する必要があります(事前にフィルタリングされていますが、 FARの方が優れていますフィルタリング手法) を使用して、クエリに関連付けられたすべての結果を返します。

これを使用しないことにした場合でも、少なくとも考えてみてください... PDO の良い出発点であり、もちろん、GET/POST 変数フィルタリングに関する優れたチュートリアルを取得します (または、HTML などのサードパーティ ツールを使用します)。浄水器、それについて)。

それが役立つことを願っています;)

于 2013-04-09T20:11:15.273 に答える