数据库设计

购物车表 (cart)

CREATE TABLE cart (
    cart_id INT AUTO_INCREMENT PRIMARY KEY,
    user_id INT NOT NULL,
    product_id INT NOT NULL,
    quantity INT NOT NULL DEFAULT 1,
    selected BOOLEAN DEFAULT TRUE,
    created_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_time TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    FOREIGN KEY (user_id) REFERENCES user(user_id),
    FOREIGN KEY (product_id) REFERENCES product(product_id),
    UNIQUE KEY (user_id, product_id)
);

商品表 (product)

CREATE TABLE product (
    product_id INT AUTO_INCREMENT PRIMARY KEY,
    name VARCHAR(100) NOT NULL,
    price DECIMAL(10,2) NOT NULL,
    stock INT NOT NULL,
    status TINYINT DEFAULT 1
);

用户表 (user)

CREATE TABLE user (
    user_id INT AUTO_INCREMENT PRIMARY KEY,
    username VARCHAR(50) NOT NULL UNIQUE
);

并发操作处理

乐观锁实现 在商品表中添加version字段:

ALTER TABLE product ADD COLUMN version INT DEFAULT 0;

Java代码示例:

public boolean addToCart(int userId, int productId, int quantity) {
    // 查询商品信息并检查库存
    Product product = productMapper.selectById(productId);
    if (product.getStock() < quantity) {
        return false;
    }
    
    // 更新商品库存(带乐观锁)
    int updated = productMapper.updateStockWithVersion(
        productId, 
        quantity, 
        product.getVersion()
    );
    
    if (updated == 0) {
        // 版本号不匹配,更新失败
        throw new OptimisticLockException("商品库存发生变化,请重试");
    }
    
    // 添加或更新购物车
    Cart cart = cartMapper.selectByUserAndProduct(userId, productId);
    if (cart == null) {
        cart = new Cart();
        cart.setUserId(userId);
        cart.setProductId(productId);
        cart.setQuantity(quantity);
        cartMapper.insert(cart);
    } else {
        cart.setQuantity(cart.getQuantity() + quantity);
        cartMapper.updateById(cart);
    }
    
    return true;
}

悲观锁实现 使用SELECT...FOR UPDATE锁定商品记录:

@Transactional
public boolean addToCartWithPessimisticLock(int userId, int productId, int quantity) {
    // 锁定商品记录
    Product product = productMapper.selectByIdForUpdate(productId);
    if (product.getStock() < quantity) {
        return false;
    }
    
    // 更新库存
    productMapper.updateStock(productId, quantity);
    
    // 更新购物车(同上)
    // ...
    
    return true;
}

购物车关键操作

获取用户购物车

public List<CartVO> getCartList(int userId) {
    return cartMapper.selectCartListWithProductInfo(userId);
}

更新购物车商品数量

@Transactional
public boolean updateCartQuantity(int cartId, int quantity) {
    Cart cart = cartMapper.selectById(cartId);
    if (cart == null) {
        return false;
    }
    
    Product product = productMapper.selectById(cart.getProductId());
    if (product.getStock() < quantity) {
        return false;
    }
    
    cart.setQuantity(quantity);
    cartMapper.updateById(cart);
    return true;
}

批量删除购物车商品

@Transactional
public int batchDeleteCartItems(int userId, List<Integer> cartIds) {
    return cartMapper.batchDelete(userId, cartIds);
}

性能优化建议

使用Redis缓存热门商品信息,减少数据库查询压力

对大流量场景,考虑使用Redis暂存购物车数据,定期同步到MySQL

为购物车表添加复合索引 (user_id, product_id) 提高查询效率

在高并发场景下,使用消息队列异步处理非核心操作

Logo

电商企业物流数字化转型必备!快递鸟 API 接口,72 小时快速完成物流系统集成。全流程实战1V1指导,营造开放的API技术生态圈。

更多推荐