本文目录导读:

我来为您详细介绍如何为PHP项目实现软删除功能。
数据库设计
在数据表中添加软删除相关字段:
ALTER TABLE users ADD COLUMN deleted_at TIMESTAMP NULL DEFAULT NULL, ADD COLUMN deleted_by INT NULL DEFAULT NULL;
或者创建表时直接包含:
CREATE TABLE users (
id INT PRIMARY KEY AUTO_INCREMENT,
name VARCHAR(100),
email VARCHAR(100),
deleted_at TIMESTAMP NULL DEFAULT NULL,
deleted_by INT NULL DEFAULT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP
);
PHP Trait实现(推荐方式)
创建可复用的Trait:
<?php
// SoftDeletable.php
trait SoftDeletable
{
/**
* 软删除记录
* @param int $deletedBy 删除者ID
* @return bool
*/
public function softDelete($deletedBy = null)
{
$this->deleted_at = date('Y-m-d H:i:s');
$this->deleted_by = $deletedBy;
return $this->save();
}
/**
* 恢复软删除的记录
* @return bool
*/
public function restore()
{
$this->deleted_at = null;
$this->deleted_by = null;
return $this->save();
}
/**
* 检查记录是否已删除
* @return bool
*/
public function isDeleted()
{
return $this->deleted_at !== null;
}
/**
* 强制删除记录
* @return bool
*/
public function forceDelete()
{
return parent::delete();
}
}
基础模型类实现
<?php
// BaseModel.php
class BaseModel
{
protected $table;
protected $primaryKey = 'id';
protected $fillable = [];
protected $db;
// 使用软删除Trait
use SoftDeletable;
/**
* 重写查询方法,自动过滤已删除记录
*/
public static function query()
{
$model = new static();
$model->where('deleted_at IS NULL');
return $model;
}
/**
* 查询包括已删除的记录
*/
public static function withTrashed()
{
return new static();
}
/**
* 只查询已删除的记录
*/
public static function onlyTrashed()
{
$model = new static();
$model->where('deleted_at IS NOT NULL');
return $model;
}
/**
* 删除方法重写
*/
public function delete()
{
return $this->softDelete();
}
}
具体模型类示例
<?php
// User.php
class User extends BaseModel
{
protected $table = 'users';
protected $fillable = ['name', 'email'];
// 业务方法
public function getActiveUsers()
{
return self::query()->get();
}
public function getDeletedUsers()
{
return self::onlyTrashed()->get();
}
}
使用示例
<?php
// 使用示例
// 1. 创建用户
$user = new User();
$user->name = '张三';
$user->email = 'zhangsan@example.com';
$user->save();
// 2. 软删除用户
$user->softDelete(1); // 参数为删除者ID
// 或者直接调用delete方法
$user->delete();
// 3. 查询活跃用户(自动过滤已删除)
$activeUsers = User::query()->get();
// 4. 查询所有用户(包括已删除)
$allUsers = User::withTrashed()->get();
// 5. 只查询已删除用户
$deletedUsers = User::onlyTrashed()->get();
// 6. 恢复用户
$user->restore();
// 7. 强制物理删除
$user->forceDelete();
// 8. 检查是否被删除
if ($user->isDeleted()) {
echo "该用户已被删除";
}
PDO数据库连接示例
<?php
// Database.php
class Database
{
protected static $instance = null;
protected $connection;
private function __construct()
{
$host = 'localhost';
$dbname = 'your_database';
$username = 'root';
$password = '';
try {
$this->connection = new PDO(
"mysql:host=$host;dbname=$dbname;charset=utf8mb4",
$username,
$password,
[
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_OBJ
]
);
} catch (PDOException $e) {
die("连接失败: " . $e->getMessage());
}
}
public static function getInstance()
{
if (self::$instance === null) {
self::$instance = new self();
}
return self::$instance;
}
public function getConnection()
{
return $this->connection;
}
}
完整示例的CRUD操作
<?php
// UserRepository.php
class UserRepository
{
private $db;
public function __construct()
{
$this->db = Database::getInstance()->getConnection();
}
/**
* 创建用户
*/
public function create($data)
{
$sql = "INSERT INTO users (name, email, created_at)
VALUES (:name, :email, NOW())";
$stmt = $this->db->prepare($sql);
$stmt->execute([
':name' => $data['name'],
':email' => $data['email']
]);
return $this->db->lastInsertId();
}
/**
* 软删除用户
*/
public function softDelete($id, $deletedBy = null)
{
$sql = "UPDATE users SET
deleted_at = NOW(),
deleted_by = :deleted_by
WHERE id = :id AND deleted_at IS NULL";
$stmt = $this->db->prepare($sql);
return $stmt->execute([
':id' => $id,
':deleted_by' => $deletedBy
]);
}
/**
* 恢复用户
*/
public function restore($id)
{
$sql = "UPDATE users SET
deleted_at = NULL,
deleted_by = NULL
WHERE id = :id";
$stmt = $this->db->prepare($sql);
return $stmt->execute([':id' => $id]);
}
/**
* 获取活跃用户
*/
public function getActiveUsers()
{
$sql = "SELECT * FROM users WHERE deleted_at IS NULL";
$stmt = $this->db->query($sql);
return $stmt->fetchAll();
}
/**
* 获取所有用户(包括已删除)
*/
public function getAllUsers()
{
$sql = "SELECT * FROM users ORDER BY created_at DESC";
$stmt = $this->db->query($sql);
return $stmt->fetchAll();
}
}
高级特性
1 自动软删除关联模型
<?php
trait CascadeSoftDeletes
{
protected $cascadeDeletes = [];
public function softDelete($deletedBy = null)
{
// 先删除关联模型
foreach ($this->cascadeDeletes as $relation) {
if (method_exists($this, $relation)) {
$relatedModels = $this->$relation()->get();
foreach ($relatedModels as $model) {
$model->softDelete($deletedBy);
}
}
}
return parent::softDelete($deletedBy);
}
}
2 软删除审计日志
<?php
trait SoftDeleteAudit
{
public function softDelete($deletedBy = null)
{
$result = parent::softDelete($deletedBy);
if ($result) {
// 记录审计日志
AuditLog::create([
'action' => 'soft_delete',
'model' => get_class($this),
'model_id' => $this->id,
'user_id' => $deletedBy,
'timestamp' => date('Y-m-d H:i:s')
]);
}
return $result;
}
}
注意事项
- 索引优化:为
deleted_at字段添加索引 - 唯一约束:注意软删除记录的唯一约束问题
- 查询性能:大量软删除记录可能影响查询性能
- 数据清理:定期清理物理删除过期数据
- 备份策略:软删除不应该替代数据备份
这就是一个完整的PHP软删除实现方案,可以根据项目需求进行适当调整和扩展。
版权声明:NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
NBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
CBA直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
足球直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播
英超直播