代码之家  ›  专栏  ›  技术社区  ›  adardesign

php-mysql更新在本地主机上运行良好,但在活动时不起作用

  •  0
  • adardesign  · 技术社区  · 15 年前

    我有一个PHP页面,它更新了一个MySQL数据库,它在我的Mac(使用mamp的localhost)上工作正常。

    我检查了一下它的连接,但似乎有一个连接

     <?php require_once('connection.php'); ?>
    
     <?php  
      $id = $_GET['id'];
      $collumn = $_GET['collumn'];
      $val = $_GET['val'];
     // checking if there is a connection
     if(!$connection){
         echo "connectioned failed";
       }
      ?>
    
    
     <?php 
        $sqlUpdate = 'UPDATE plProducts.allPens SET '. "{$collumn}".' = '."'{$val}'".' WHERE allPens.prodId = '."'{$id}'".' LIMIT 1';
        mysql_query($sqlUpdate);
        // testing for errors
       if ($sqlUpdate === false) {
          // Checked this and echos NO errors.
         echo "Query failed: " . mysql_error();
        }
    
    if (mysql_affected_rows() == 1) {
      echo "updated";
    } else {
      echo "failed";
    }?>
    

    在URL中,我传递参数,它如下所示: http://pathToSite.com/updateDB.php?id=17&collumn=prodid&val=4

    也许这和主机有关?这不是简单的php-mysql数据库更新吗?这里可能有什么问题?

    为什么在本地主机上有效?

    为什么在Live服务器上没有呢?

    3 回复  |  直到 15 年前
        1
  •  1
  •   Charles    15 年前

    让我们从解决您的确切问题开始。您的查询由于某种原因失败。我们可以通过检查返回的信息来找出问题所在。 mysql_query 如果是布尔值错误,则询问 mysql_error 出了什么问题:

    $sh = mysql_query($sqlUpdate);
    if($sh === false) {
        echo "Query failed: " . mysql_error();
        exit;
    }
    

    你还有其他问题。最大的问题是您的代码 an SQL Injection vulnerability . 假设你的剧本被称为 foo.php . 如果我要求:

    foo.php?collumn=prodId = NULL -- 
    

    然后您的SQL将显示如下:

    UPDATE plProducts.allPens SET prodId = NULL -- = "" WHERE allPens.prodId = "" LIMIT 1
    

    -- 是SQL注释。

    我刚刚成功地在你的表中插入了所有的产品ID。

    这个 最有效 停止SQL注入的方法是使用 准备的报表 占位符 . PHP中的“mysql”扩展不支持它们,因此您还需要切换到 mysqli 扩展,或 PDO 延伸。

    让我们使用一个PDO准备好的语句来保证查询的安全。

    // Placeholders only work for *data*.  We'll need to validate 
    // the column name another way.  A list of columns that can be
    // updated is very safe.
    $safe_columns = array('a', 'b', 'c', 'd');
    if(!in_array($collumn, $safe_columns))
        die "Invalid column";
    // Those question marks are the placeholders.
    $sqlUpdate = "UPDATE plProducts.allPens SET $column = ? WHERE allPens.prodId = ? LIMIT 1";
    $sh = $db->prepare($sqlUpdate);
    // The entries in the array you pass to execute() are substituted
    // into the query, replacing the placeholders.
    $success = $sh->execute(array( $val, $id ));
    // If PDO is configured to use warnings instead of exceptions, this will work.
    // Otherwise, you'll need to worry about handling the exception...
    if(!$success)
        die "Oh no, it failed!  MySQL says: " . join(' ', $db->errorInfo());
    
        2
  •  1
  •   Bill Karwin    15 年前

    如果遇到错误,大多数mysql函数都返回false。您应该检查错误情况,如果出现错误,则输出错误消息。这将使您更好地了解问题发生的位置以及问题的性质。

    令人惊讶的是,尽管php文档中有许多示例,但有多少程序员从不检查错误状态。

    $link = mysql_connect(...);
    if ($link === false) {
        die(mysql_error());
    }
    
    $selected = mysql_select_db(...);
    if ($selected === false) {
        die(mysql_error());
    }
    
    $result = mysql_query(...);
    if ($result === false) {
        die(mysql_error());
    }
    
        3
  •  1
  •   staticsan    15 年前

    你的电话 mysql_query() 是错误的;您正在检查正在传入的变量的内容,但函数调用不能这样工作。它返回一个您应该检查的值。如果查询失败,则返回 false . 如果它返回数据(例如 SELECT )它返回一个资源句柄。如果成功但不返回数据(如 INSERT )它返回真。

    构建SQL时也会遇到一些问题。@Charles提到了SQL注入并建议准备好的语句。如果仍要构造查询字符串,则需要使用 mysql_real_escape_string() . (但是我建议你读一下 mysqli 扩展并使用这些函数。)

    其次,将字符串与嵌入替换连接起来。这太愚蠢了。改为这样做:

     $sqlUpdate = 'UPDATE plProducts.allPens SET '.$collumn.' = \''.$val.'\' 
            WHERE allPens.prodId = '.intval($id).' LIMIT 1';
    

    如果您必须在querystring中接受它,您还应该检查 $collumn 在使用前设置为有效值。如果不是,则发送并出错页面。同样,检查一下 $id 将变为数字(使用 is_numeric() )所有这些都叫做 防御性程序设计 .