• 欢迎访问搞代码网站,推荐使用最新版火狐浏览器和Chrome浏览器访问本网站!
  • 如果您觉得本站非常有看点,那么赶紧使用Ctrl+D 收藏搞代码吧

PHP+redis实现的限制抢购防止商品超发功能详解

php 搞代码 4年前 (2022-01-21) 23次浏览 已收录 0个评论

本文实例讲述了PHP+redis实现的限制抢购防止商品超发功能。分享给大家供大家参考,具体如下:

  • redis不仅仅是单纯的缓存,它还有一些特殊的功能,在一些特殊场景上很好用。redis中key的原子自增incrby和判断key不存在再写入的setnx方法,可以有效的防止超发。
  • 下面使用两个不同的方式来说明利用redis做商品购买库存数量限制。
  • 业务场景很简单,就是限制抢购5个商品,模拟并发请求抢购商品,每抢购一次对应redis中的key值增加一次,通过判断限购的数量来限制抢购,抢购成功写入成功日志,失败写入失败的信息记录,通过记录的数量来判断是否超发。

文件index.php

<?php
require_once './myRedis.php';
require_once './function.php';
class sendAward{
  public $conf = [];
  const V1 = 'way1';//版本一
  const V2 = 'way2';//版本二
  const AMOUNTLIMIT = 5;//抢购数量限制
  const INCRAMOUNT = 1;//redis递增数量值
  //初始化调用对应方法执行商品发放
  public function __construct($conf,$type){
    $this->conf = $conf;
    if(empty($type))
      return '';
    if($type==self::V1){
      $this->way1(self::V1);
    }elseif($type==self::V2){
      $this->way2(self::V2);
    }else{
      return '';
    }
  }
  //抢购商品方式一
  protected function way1($v){
    $redis = new myRedis($this->conf);   
    $keyNmae = getKeyName($v);
    if(!$redis->exists($keyNmae)){
      $redis->set($keyNmae,0);
    }
    $currAmount = $redis->get($keyNmae);
    if(($currAmount+self::INCRAMOUNT)>self::AMOUNTLIMIT){
      writeLog("没有抢到商品",$v);
      return;
    }
    $redis->incrby($keyNmae,self::INCRAMOUNT);
    writeLog("抢到商品",$v);
  }
  //抢购商品方式二
  protected function way2($v){
    $redis = new myRedis($this->conf);
    $keyNmae = getKeyName($v);
    if(!$redis->exists($keyNmae)){
      $redis->setnx($keyNmae,0);
    }
    if($redis->incrby($keyNmae,self::INCRAMOUNT) > self::AMOUNTLIMIT){
      writeLog("没有抢到商品",$v);
      return;
    }
    writeLog("抢到商品",$v);
  }
}
//实例化调用对应执行方法
$type = isset($_GET['v'])?$_GET['v']:'way1';
$conf = [
  'host'=>'192.168.0.214','port'=>'6379',
  'auth'=&<strong style="color:transparent">本文来源gao@daima#com搞(%代@#码@网&</strong><strong>搞gaodaima代码</strong>gt;'test','db'=>2,
];
new sendAward($conf,$type);

文件myRedis.php

<?php
/**
 * @desc 自定义redis操作类
 * **/
class myRedis{
  public $handler = NULL;
  public function __construct($conf){
    $this->handler = new Redis();
    $this->handler->connect($conf['host'], $conf['port']); //连接Redis
    //设置密码
    if(isset($conf['auth'])){
      $this->handler->auth($conf['auth']); //密码验证
    }
    //选择数据库
    if(isset($conf['db'])){
      $this->handler->select($conf['db']);//选择数据库2
    }else{
      $this->handler->select(0);//默认选择0库
    }
  }
  //获取key的值
  public function get($name){
    return $this->handler->get($name);
  }
  //设置key的值
  public function set($name,$value){
    return $this->handler->set($name,$value);
  }
  //判断key是否存在
  public function exists($key){
    if($this->handler->exists($key)){
      return true;
    }
    return false;
  }
  //当key不存在的设置key的值,存在则不设置
  public function setnx($key,$value){
    return $this->handler->setnx($key,$value);
  }
  //将key的数值增加指定数值
  public function incrby($key,$value){
    return $this->handler->incrBy($key,$value);
  }
}

文件function.php

<?php
//获取商品key名称
function getKeyName($v)
{
  return "send_goods_".$v;
}
//日志写入方法
function writeLog($msg,$v)
{
  $log = $msg.PHP_EOL;
  file_put_contents("log/$v.log",$log,FILE_APPEND);
}


搞代码网(gaodaima.com)提供的所有资源部分来自互联网,如果有侵犯您的版权或其他权益,请说明详细缘由并提供版权或权益证明然后发送到邮箱[email protected],我们会在看到邮件的第一时间内为您处理,或直接联系QQ:872152909。本网站采用BY-NC-SA协议进行授权
转载请注明原文链接:PHP+redis实现的限制抢购防止商品超发功能详解
喜欢 (0)
[搞代码]
分享 (0)
发表我的评论
取消评论

表情 贴图 加粗 删除线 居中 斜体 签到

Hi,您需要填写昵称和邮箱!

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址