CleanupSqlBackup.php 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170
  1. <?php
  2. namespace App\Module\Cleanup\Models;
  3. use UCore\ModelCore;
  4. use Illuminate\Database\Eloquent\Relations\BelongsTo;
  5. /**
  6. * SQL备份记录模型
  7. *
  8. * 存储INSERT语句到数据库表中
  9. */
  10. class CleanupSqlBackup extends ModelCore
  11. {
  12. /**
  13. * 数据表名
  14. */
  15. protected $table = 'cleanup_sql_backups';
  16. // field start
  17. /**
  18. * @property int $id 主键ID
  19. * @property int $backup_id 备份记录ID
  20. * @property string $table_name 表名
  21. * @property string $sql_content INSERT语句内容
  22. * @property int $records_count 记录数量
  23. * @property int $content_size 内容大小(字节)
  24. * @property string $content_hash 内容SHA256哈希
  25. * @property array $backup_conditions 备份条件
  26. * @property \Carbon\Carbon $created_at 创建时间
  27. */
  28. // field end
  29. /**
  30. * 字段类型转换
  31. */
  32. protected $casts = [
  33. 'backup_conditions' => 'array',
  34. 'records_count' => 'integer',
  35. 'content_size' => 'integer',
  36. ];
  37. /**
  38. * 隐藏字段
  39. */
  40. protected $hidden = [
  41. 'sql_content', // 默认隐藏SQL内容,避免大量数据传输
  42. ];
  43. /**
  44. * 关联备份记录
  45. */
  46. public function backup(): BelongsTo
  47. {
  48. return $this->belongsTo(CleanupBackup::class, 'backup_id');
  49. }
  50. /**
  51. * 获取格式化的内容大小
  52. */
  53. public function getFormattedSizeAttribute(): string
  54. {
  55. $size = $this->content_size;
  56. if ($size < 1024) {
  57. return $size . ' B';
  58. } elseif ($size < 1024 * 1024) {
  59. return round($size / 1024, 2) . ' KB';
  60. } elseif ($size < 1024 * 1024 * 1024) {
  61. return round($size / (1024 * 1024), 2) . ' MB';
  62. } else {
  63. return round($size / (1024 * 1024 * 1024), 2) . ' GB';
  64. }
  65. }
  66. /**
  67. * 获取SQL内容预览(前100个字符)
  68. */
  69. public function getSqlPreviewAttribute(): string
  70. {
  71. if (empty($this->sql_content)) {
  72. return '';
  73. }
  74. $preview = substr($this->sql_content, 0, 100);
  75. if (strlen($this->sql_content) > 100) {
  76. $preview .= '...';
  77. }
  78. return $preview;
  79. }
  80. /**
  81. * 验证内容哈希
  82. */
  83. public function verifyContentHash(): bool
  84. {
  85. if (empty($this->sql_content) || empty($this->content_hash)) {
  86. return false;
  87. }
  88. $currentHash = hash('sha256', $this->sql_content);
  89. return $currentHash === $this->content_hash;
  90. }
  91. /**
  92. * 作用域:按备份ID筛选
  93. */
  94. public function scopeByBackup($query, int $backupId)
  95. {
  96. return $query->where('backup_id', $backupId);
  97. }
  98. /**
  99. * 作用域:按表名筛选
  100. */
  101. public function scopeByTable($query, string $tableName)
  102. {
  103. return $query->where('table_name', $tableName);
  104. }
  105. /**
  106. * 作用域:按记录数量排序
  107. */
  108. public function scopeOrderByRecords($query, string $direction = 'desc')
  109. {
  110. return $query->orderBy('records_count', $direction);
  111. }
  112. /**
  113. * 作用域:按内容大小排序
  114. */
  115. public function scopeOrderBySize($query, string $direction = 'desc')
  116. {
  117. return $query->orderBy('content_size', $direction);
  118. }
  119. /**
  120. * 获取统计信息
  121. */
  122. public static function getStats(): array
  123. {
  124. return [
  125. 'total_count' => static::count(),
  126. 'total_records' => static::sum('records_count'),
  127. 'total_size' => static::sum('content_size'),
  128. 'avg_records_per_backup' => static::avg('records_count'),
  129. 'avg_size_per_backup' => static::avg('content_size'),
  130. ];
  131. }
  132. /**
  133. * 获取按表名分组的统计
  134. */
  135. public static function getTableStats(): array
  136. {
  137. return static::selectRaw('
  138. table_name,
  139. COUNT(*) as backup_count,
  140. SUM(records_count) as total_records,
  141. SUM(content_size) as total_size,
  142. AVG(records_count) as avg_records,
  143. AVG(content_size) as avg_size
  144. ')
  145. ->groupBy('table_name')
  146. ->orderBy('total_size', 'desc')
  147. ->get()
  148. ->toArray();
  149. }
  150. }