首页 > 解决方案 > 不能使用 mysqli_stmt_bind_param 将标量值用作数组

问题描述

我在博客中使用 php 和 mysqli 创建博客我可以在特定主题下显示帖子

以下是在主题下显示帖子的代码:

/* * * * * * * * * * * * * * * *
* Returns all posts under a topic
* * * * * * * * * * * * * * * * */
function getPublishedPostsByTopic($topic_id) {
    global $conn;
    $sql = "SELECT * FROM posts ps WHERE ps.id IN (SELECT pt.post_id FROM post_topic pt WHERE pt.topic_id=? GROUP BY pt.post_id HAVING COUNT(1) = 1)";
    $stmt= mysqli_stmt_init($conn);
    mysqli_stmt_prepare($stmt,$sql);
    mysqli_stmt_bind_param($stmt,"i",$topic_id);
    mysqli_stmt_execute($stmt);
    $result=mysqli_stmt_get_result($stmt);
    $posts=mysqli_fetch_assoc($result);

    $final_posts = array();
    foreach ($posts as $post) {
        $post['topic'] = getPostTopic($post['id']); 
        array_push($final_posts, $post);
    }
    return $final_posts;
}

但是当我运行它时,我得到了这些错误:

Warning: Cannot use a scalar value as an array
Warning: Illegal string offset 'id' 
Warning: Cannot assign an empty string to a string offset 

我用来避免 MySQL 注入的要点是mysqli_stmt_bind_param 当我使用以下代码而不是上面提到的代码时发生 SQL INJECTION:

function getPublishedPostsByTopic($topic_id) {
    global $conn;
    $sql = "SELECT * FROM posts ps WHERE ps.id IN (SELECT pt.post_id FROM post_topic pt WHERE pt.topic_id=$topic_id GROUP BY pt.post_id     HAVING COUNT(1) = 1)";
    $result = mysqli_query($conn, $sql);
    // fetch all posts as an associative array called $posts
    $posts = mysqli_fetch_all($result, MYSQLI_ASSOC);

    $final_posts = array();
    foreach ($posts as $post) {
        $post['topic'] = getPostTopic($post['id']); 
        array_push($final_posts, $post);
    }
    return $final_posts;
}

我是 PHP 的初学者,希望有人向我解释如何解决这个问题

谢谢你

标签: phpmysqli

解决方案


没有必要使代码如此复杂。坚持使用面向对象的风格并get_result()直接在结果上循环。

function getPublishedPostsByTopic($topic_id) {
    global $conn;
    // prepare/bind/execute
    $sql = "SELECT * FROM posts ps WHERE ps.id IN (SELECT pt.post_id FROM post_topic pt WHERE pt.topic_id=? GROUP BY pt.post_id HAVING COUNT(1) = 1)";
    $stmt = $conn->prepare($sql);
    $stmt->bind_param('i', $topic_id);
    $stmt->execute();

    $final_posts = array();
    // get result and iterate over it
    foreach ($stmt->get_result() as $post) {
        $post['topic'] = getPostTopic($post['id']);
        $final_posts[] = $post;
    }
    return $final_posts;
}

推荐阅读