当前位置:首页 > PHP

php redis实现秒杀

2026-02-13 18:53:00PHP

PHP + Redis 实现秒杀功能

秒杀场景的核心在于解决高并发下的超卖问题和系统性能瓶颈。Redis 的高性能和原子操作特性非常适合实现秒杀系统。

使用 Redis 原子操作防止超卖

利用 Redis 的 DECRINCRBY 命令实现原子性库存扣减:

$redis = new Redis();
$redis->connect('127.0.0.1', 6379);

$productId = 'product_123';
$userId = uniqid(); // 模拟用户ID

// 预先设置库存
// $redis->set('stock_' . $productId, 100);

// 秒杀逻辑
$remaining = $redis->decr('stock_' . $productId);
if ($remaining >= 0) {
    // 扣减成功,记录用户购买信息
    $redis->sAdd('success_users_' . $productId, $userId);
    echo "秒杀成功";
} else {
    // 库存不足,恢复库存
    $redis->incr('stock_' . $productId);
    echo "秒杀失败";
}

Lua 脚本保证操作原子性

更推荐使用 Lua 脚本保证多个操作的原子性:

$lua = <<<LUA
local stock_key = KEYS[1]
local user_key = KEYS[2]
local user_id = ARGV[1]

local stock = tonumber(redis.call('GET', stock_key))
if stock and stock > 0 then
    redis.call('DECR', stock_key)
    redis.call('SADD', user_key, user_id)
    return 1
end
return 0
LUA;

$result = $redis->eval($lua, ['stock_' . $productId, 'success_users_' . $productId, $userId], 2);

使用 Redis 队列缓解压力

将请求先放入队列,异步处理:

// 用户请求入队
$redis->lPush('seckill_queue', json_encode(['user_id' => $userId, 'product_id' => $productId]));

// 后台 worker 处理
while(true) {
    $task = $redis->rPop('seckill_queue');
    if ($task) {
        $data = json_decode($task, true);
        // 处理秒杀逻辑
    }
    usleep(100000); // 0.1秒
}

限流措施

使用 Redis 实现简单限流:

$key = 'user_request_' . $userId;
$limit = 5; // 5次/秒

$current = $redis->incr($key);
if ($current == 1) {
    $redis->expire($key, 1);
}
if ($current > $limit) {
    echo "请求过于频繁";
    exit;
}

数据预热与库存分离

提前将库存加载到 Redis:

// 从数据库加载库存到Redis
$dbStock = 100; // 从数据库查询
$redis->set('stock_' . $productId, $dbStock);

注意事项

  • Redis 需要配置持久化,避免重启导致数据丢失
  • 考虑使用 Redis 集群提高可用性
  • 最终一致性:异步同步到数据库
  • 前端需要配合进行防重复提交处理
  • 监控 Redis 性能指标,及时扩容

以上方案结合了 Redis 的原子操作、队列和限流机制,能有效应对秒杀场景的高并发挑战。实际应用中可根据业务需求调整细节。

php redis实现秒杀

标签: 秒杀php
分享给朋友:

相关文章

php实现socket

php实现socket

PHP 实现 Socket 通信 PHP 可以通过 socket 扩展实现网络通信,支持 TCP/UDP 协议。以下是实现 Socket 通信的核心步骤和代码示例。 创建 TCP 服务器 //…

php实现接口

php实现接口

PHP 实现接口的方法 在 PHP 中,接口(Interface)用于定义一组方法的规范,而不实现具体功能。类可以实现一个或多个接口,并必须实现接口中定义的所有方法。 定义接口 接口使用 inter…

php实现的分页

php实现的分页

PHP 实现分页的方法 基本分页逻辑 分页的核心在于计算总页数、当前页码以及数据偏移量。假设每页显示 10 条数据: $current_page = isset($_GET['page']) ? (…

php 实现秒杀

php 实现秒杀

PHP 实现秒杀的关键技术 秒杀系统需要解决高并发、超卖、性能瓶颈等问题。以下是实现秒杀的核心方案: 使用 Redis 预减库存 将商品库存提前加载到 Redis 中,通过原子操作保证库存准确性:…

php变量的实现

php变量的实现

PHP变量的实现机制 PHP变量的实现基于Zend引擎的底层数据结构。核心结构体zval用于存储变量类型和值,其设计允许动态类型转换和高效内存管理。 zval结构体 PHP变量通过zval结构体实…

php 实现锁

php 实现锁

PHP 实现锁的常见方法 文件锁(flock) 利用 flock 函数对文件进行独占锁定,适用于单机环境。 $fp = fopen("lockfile.lock", "w+"); if (floc…