php如何实现取消订单?

php实现取消订单的方法:首先【order_status】为1时代表客户下单确定;然后为2时代表客户已付款;最后为0时代表订单已取消,运用swoole的异步毫秒定时器。

php如何实现取消订单?

php实现取消订单的方法:

一、业务场景:当客户下单在指定的时间内如果没有付款,那我们需要将这笔订单取消掉,比如好的处理方法是运用延时取消,这里我们用到了swoole,运用swoole的异步毫秒定时器不会影响到当前程序的运行。

二、说明,order_status为1时代表客户下单确定,为2时代表客户已付款,为0时代表订单已取消(正是swoole来做的),下面的代表我没有用框架,比较纯的PHP代表方便理解和应用

三、举例说明,库存表csdn_product_stock产品ID为1的产品库存数量为20,产品ID为2的库存数量为40,然后客户下单一笔产品ID1减10,产品ID2减20,所以库存表只够2次下单,例子中10秒后自动还原库存,如下图:

立即学习“PHP免费学习笔记(深入)”;

图解:

1、第一次下完单产品ID1库存从20减到了10,产品ID2库存从40减到了20;

2、第二次下完单产品ID的库存为0了,产品ID2的库存也为0了;

3、第三次下单时,程序提示Out of stock;

4、过了10秒钟(每个订单下单后往后推10秒),客户两次下单,由于没有付款(csdn_order表的order_status为1),产品1和产品2的库存被还原了(csdn_order表的order_status变为0),客户又可以继续下单了

6e424672db924cb7090206a9f1838d9.png

1、所需要sql数据库表

DROP TABLE IF EXISTS `csdn_order`;CREATE TABLE `csdn_order` (  `order_id` int(10) unsigned NOT NULL AUTO_INCREMENT,  `order_amount` float(10,2) unsigned NOT NULL DEFAULT '0.00',  `user_name` varchar(64) CHARACTER SET latin1 NOT NULL DEFAULT '',  `order_status` tinyint(2) unsigned NOT NULL DEFAULT '0',  `date_created` datetime NOT NULL,  PRIMARY KEY (`order_id`)) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8; DROP TABLE IF EXISTS `csdn_order_detail`;CREATE TABLE `csdn_order_detail` (  `detail_id` int(10) unsigned NOT NULL AUTO_INCREMENT,  `order_id` int(10) unsigned NOT NULL,  `product_id` int(10) NOT NULL,  `product_price` float(10,2) NOT NULL,  `product_number` smallint(4) unsigned NOT NULL DEFAULT '0',  `date_created` datetime NOT NULL,  PRIMARY KEY (`detail_id`),  KEY `idx_order_id` (`order_id`)) ENGINE=InnoDB AUTO_INCREMENT=0 DEFAULT CHARSET=utf8; DROP TABLE IF EXISTS `csdn_product_stock`;CREATE TABLE `csdn_product_stock` (  `auto_id` int(10) unsigned NOT NULL AUTO_INCREMENT,  `product_id` int(10) NOT NULL,  `product_stock_number` int(10) unsigned NOT NULL,  `date_modified` datetime NOT NULL,  PRIMARY KEY (`auto_id`),  KEY `idx_product_id` (`product_id`)) ENGINE=InnoDB AUTO_INCREMENT=3 DEFAULT CHARSET=utf8; INSERT INTO `csdn_product_stock` VALUES ('1', '1', '20', '2018-09-13 19:36:19');INSERT INTO `csdn_product_stock` VALUES ('2', '2', '40', '2018-09-13 19:36:19');

登录后复制

2、config.php


登录后复制

 

3、order_submit.php

 true));$pdo->setAttribute(PDO::ATTR_AUTOCOMMIT, 1);$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); $orderInfo = array('order_amount' => 10.92,'user_name' => 'yusan','order_status' => 1,'date_created' => 'now()','product_lit' => array(0 => array('product_id' => 1,'product_price' => 5.00,'product_number' => 10,'date_created' => 'now()'),1 => array('product_id' => 2,'product_price' => 5.92,'product_number' => 20,'date_created' => 'now()'))); try{$pdo->beginTransaction();//开启事务处理 $sql = 'insert into csdn_order (order_amount, user_name, order_status, date_created) values (:orderAmount, :userName, :orderStatus, now())';$stmt = $pdo->prepare($sql);  $affectedRows = $stmt->execute(array(':orderAmount' => $orderInfo['order_amount'], ':userName' => $orderInfo['user_name'], ':orderStatus' => $orderInfo['order_status']));$orderId = $pdo->lastInsertId();if(!$affectedRows) {throw new PDOException("Failure to submit order!");}foreach($orderInfo['product_lit'] as $productInfo) { $sqlProductDetail = 'insert into csdn_order_detail (order_id, product_id, product_price, product_number, date_created) values (:orderId, :productId, :productPrice, :productNumber, now())';$stmtProductDetail = $pdo->prepare($sqlProductDetail);  $stmtProductDetail->execute(array(':orderId' => $orderId, ':productId' =>  $productInfo['product_id'], ':productPrice' => $productInfo['product_price'], ':productNumber' => $productInfo['product_number'])); $sqlCheck = "select product_stock_number from csdn_product_stock where product_id=:productId";  $stmtCheck = $pdo->prepare($sqlCheck);  $stmtCheck->execute(array(':productId' => $productInfo['product_id']));  $rowCheck = $stmtCheck->fetch(PDO::FETCH_ASSOC);if($rowCheck['product_stock_number'] prepare($sqlProductStock);  $stmtProductStock->execute(array(':productNumber' => $productInfo['product_number'], ':productId' => $productInfo['product_id']));$affectedRowsProductStock = $stmtProductStock->rowCount(); //库存没有正常扣除,失败,库存表里的product_stock_number设置了为非负数//如果库存不足时,sql异常:SQLSTATE[22003]: Numeric value out of range: 1690 BIGINT UNSIGNED value is out of range in '(`test`.`csdn_product_stock`.`product_stock_number` - 20)'if($affectedRowsProductStock commit();//提交事务//exec("php order_cancel.php -a" . $orderId . " &");pclose(popen('php order_cancel.php -a ' . $orderId . ' &', 'w'));//system("php order_cancel.php -a" . $orderId . " &", $phpResult);//echo $phpResult;}catch(PDOException $e){echo $e->getMessage();$pdo->rollback();}$pdo = null;} catch (PDOException $e) {    echo $e->getMessage();}?>

登录后复制

4、order_cancel.php

 true));$pdo->setAttribute(PDO::ATTR_AUTOCOMMIT, 0);$pdo->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION); swoole_timer_after(10000, function ($queryString) {global $queryString, $pdo; try{$pdo->beginTransaction();//开启事务处理 $orderId = $queryString['a'];  $sql = "select order_status from csdn_order where order_id=:orderId";  $stmt = $pdo->prepare($sql);  $stmt->execute(array(':orderId' => $orderId));  $row = $stmt->fetch(PDO::FETCH_ASSOC);//$row['order_status'] === "1"代表已下单,但未付款,我们还原库存只针对未付款的订单if(isset($row['order_status']) && $row['order_status'] === "1") {$sqlOrderDetail = "select product_id, product_number from csdn_order_detail where order_id=:orderId";  $stmtOrderDetail = $pdo->prepare($sqlOrderDetail);  $stmtOrderDetail->execute(array(':orderId' => $orderId));  while($rowOrderDetail = $stmtOrderDetail->fetch(PDO::FETCH_ASSOC)) {$sqlRestoreStock = "update csdn_product_stock set product_stock_number=product_stock_number + :productNumber, date_modified=now() where product_id=:productId";  $stmtRestoreStock = $pdo->prepare($sqlRestoreStock);$stmtRestoreStock->execute(array(':productNumber' => $rowOrderDetail['product_number'], ':productId' => $rowOrderDetail['product_id']));} $sqlRestoreOrder = "update csdn_order set order_status=:orderStatus where order_id=:orderId";  $stmtRestoreOrder = $pdo->prepare($sqlRestoreOrder);$stmtRestoreOrder->execute(array(':orderStatus' => 0, ':orderId' => $orderId));} $pdo->commit();//提交事务}catch(PDOException $e){echo $e->getMessage();$pdo->rollback();}$pdo = null; appendLog(date("Y-m-d H:i:s") . "" . $queryString['a'] . "" . "end" . json_encode($queryString));}, $pdo); } catch (PDOException $e) {echo $e->getMessage();}function appendLog($str) {$dir = 'log.txt';$fh = fopen($dir, "a");fwrite($fh, $str . "");fclose($fh);}?>

登录后复制

相关学习推荐:PHP编程从入门到精通

以上就是php如何实现取消订单?的详细内容,更多请关注【创想鸟】其它相关文章!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至253000106@qq.com举报,一经查实,本站将立刻删除。

发布者:PHP中文网,转转请注明出处:https://www.chuangxiangniao.com/p/2135782.html

(0)
上一篇 2025年2月25日 00:28:44
下一篇 2025年2月25日 00:29:00

AD推荐 黄金广告位招租... 更多推荐

相关推荐

  • ubuntu下php如何安装curl

    ubuntu下php安装curl的方法:可以通过执行apt-get命令安装。具体方法是:1、执行【sudo apt-get install curl  libcurl3-dev php7.0-curl】命令安装;2、重启apache服务器。…

    2025年2月25日
    000
  • php读取txt乱码怎么办

    php读取txt乱码的解决办法:首先下载并安装Editplus软件;然后把要读取的txt文本重新进行编码;最后使用php读取指定txt文本随机一行内容即可。 PHP读取txt文本内容乱码问题解决方法 首先要说txt文件的编码格式ANSI、U…

    2025年2月25日
    200
  • 关于ubuntu php环境设置详解

    ubuntu php设置方法:首先更新源列表;然后打开“终端窗口”,输入命令“sudo apt-get install php5”来安装php;接着安装配置好apache环境,并安装php5-gd模块;最后创建“info.php”文件即可。…

    2025年2月25日 编程技术
    200
  • php如何将日期转换成字符串

    php将日期转换成字符串的方法是:我们可以通过date()函数来实现。date()函数用于格式化本地日期和时间,如果成功则返回格式化的日期字符串,如果失败则报E_WARNING错并返回FALSE。 要将日期时间戳转换成时间字符串,可以通过d…

    2025年2月25日
    200
  • php如何删除文件中任意一行?

    php删除文件中任意一行的方法:首先将文件逐行读入数组;然后遍历数组并把数组各元素的值添加到要保存的字符串中;接着当处理到对应于要删除的行的数组元素时不读入它;最后保存文件即可。 php删除文件中任意一行的方法: 实现思路:     将文件…

    2025年2月25日
    200
  • 如何用php实现unicode和utf8的转换?

    用php实现unicode和utf8转换的方法:首先对于【4-6】字节编码的情况不必考虑;然后出现四字节以上的【utf-8】字符,可以直接视为乱码忽略掉或转为unicode实体形式即可,代码为【$utf8char = “{$c}…

    2025年2月25日
    200
  • php连接mysql数据库报错了怎么办

    php连接mysql数据库报错了的解决方法是:1、打开环境变量设置,在Path变量后添加php的安装目录;2、重启计算机;3、将libmysql.dll文件拷贝到apache服务器中的bin目录下;4、重启apache服务器。 错误描述: …

    2025年2月25日
    200
  • cmd运行php文件输出乱码怎么办

    cmd运行php文件输出乱码的解决方法是:1、设置编码,具体代码为【header(“Content-type: text/html; charset=utf-8”)】;2、执行【chcp 65001】命令;3、重新执…

    2025年2月25日
    200
  • php中while循环语句如何使用

    php中while循环语句的使用方法是:while循环语句在指定条件为true时执行代码块。while循环语句语法:【while(条件为真){要执行的代码;}】,具体代码如:【while($x 我们在编写代码时,经常需要反复运行同一代码块。…

    2025年2月25日
    200
  • php token验证失败怎么办?

    php token验证失败的解决办法:1、保障添加的服务器是联通,并且url是能够访问;2、token不能重复;3、服务器上的token要改时,要和配置表单上的一致。 php token验证失败的解决办法: 这里附上配置表单,token验证…

    2025年2月25日
    200

发表回复

登录后才能评论