我开发了一个web服务(PHP / MySQL),只需通过JSON字符串输出优惠券代码。
工作原理:应用程序收到1个参数(email),然后向数据库表发出请求以获取尚未分配的优惠券代码。然后,请求更新此优惠券代码的行并将“1”放入指定的列中。 (SELECT / UPDATE例程)
之后,JSON就像这样输出:
echo '{"couponCode": "'. $coupon_code . '"}';
就是这样。
问题是webservice在大约1分钟内收到10000个请求。这种情况一天只发生一次。如果我查看apache的原始日志,我可以看到它每次都收到了10000个请求,但在我的表中只有984行已经更新(即:984个优惠券代码)。我多次测试它,每次都在980到986之间变化。 Web服务创建的日志文件不会显示任何错误,并且确切反映了数据库中已更新的内容,每次都在980到986个新行之间。
我的问题是:缺少的请求发生了什么?是服务器没有足够的内存来在这么短的时间内处理这样的多个请求吗? (当我使用5000个请求进行测试时,它可以正常工作)
如果它可以提供帮助,这里是获取新优惠券代码的功能:
function getNewCouponCode($email){
$stmt = $this->connector->prepare("SELECT * FROM coupon_code WHERE email = '' ORDER BY id ASC LIMIT 1");
$stmt2 = $this->connector->prepare("UPDATE coupon_code SET email = :email WHERE id = :id");
try{
$this->connector->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$this->connector->beginTransaction();
$this->connector->exec("LOCK TABLES coupon_code WRITE");
/*TRANSACTION 1*/
$stmt->execute();
$result["select"] = $stmt->fetch(PDO::FETCH_ASSOC);
/*TRANSACTION 1*/
/*TRANSACTION 2*/
$stmt2->bindParam(":email", $email);
$stmt2->bindParam(":id", $result["select"]["id"]);
$result["update"] = $stmt2->execute();
/*TRANSACTION 2*/
$this->connector->commit();
$this->connector->exec('UNLOCK TABLES');
return $result;
}catch(Exception $e) {
$this->connector->rollBack();
$this->connector->exec('UNLOCK TABLES');
$result["error"] = $e->getMessage();
return $result;
}
}
提前致谢。
答案 0 :(得分:3)
每分钟986个请求对于PHP应用程序来说是一个非常重要的负载,就像你设计的那样,以及一个Apache Web服务器。听起来你在一台服务器上运行这一切。
首先,无论你每分钟猛击10k次,都应该知道如果失败就重新尝试。为什么不发生这种情况?如果您的远程系统在您的控制之下,请查看是否可以解决此问题。
接下来,你会发现Nginx的线程模型比Apache的效率要高得多。
现在,您的应用程序......看起来您实际上不需要SELECT
然后UPDATE
。为什么不只是更新,并检查结果?然后它本身是原子的,你不必做这个表锁定的东西(这真的会让你慢下来)。