audit_water_tables.php 2.1 KB

12345678910111213141516171819202122232425262728293031
  1. <?php
  2. /** 只读表清理盘点:仅输出结构统计、代码引用路径及外键,不输出业务数据或凭据。 */
  3. require dirname(__DIR__).'/vendor/autoload.php';
  4. \Dotenv\Dotenv::createUnsafeMutable(dirname(__DIR__))->load();
  5. \support\App::loadAllConfig(['route']);
  6. \Webman\ThinkOrm\ThinkOrm::start(null);
  7. use support\think\Db;
  8. $root = dirname(__DIR__);
  9. $sources = [];
  10. foreach (['app','config','plugin/saiadmin/app','plugin/saiadmin/config','plugin/saipackage/app','plugin/saipackage/config'] as $directory) {
  11. if (!is_dir($root.'/'.$directory)) continue;
  12. foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator($root.'/'.$directory,FilesystemIterator::SKIP_DOTS)) as $file) {
  13. if ($file->getExtension() === 'php') $sources[str_replace('\\','/',substr($file->getPathname(),strlen($root)+1))] = file_get_contents($file->getPathname());
  14. }
  15. }
  16. $tables = Db::query('SELECT TABLE_NAME AS name,TABLE_ROWS AS estimated_rows,DATA_LENGTH+INDEX_LENGTH AS bytes FROM information_schema.TABLES WHERE TABLE_SCHEMA=DATABASE() ORDER BY TABLE_NAME');
  17. foreach ($tables as &$table) {
  18. $full = $table['name'];
  19. $short = preg_replace('/^sa_/','',$full);
  20. $pattern = '/(?<![a-zA-Z0-9_])(?:'.preg_quote($full,'/').'|'.preg_quote($short,'/').')(?![a-zA-Z0-9_])/i';
  21. $table['reference_files'] = [];
  22. foreach ($sources as $file=>$content) if (preg_match($pattern,$content)) $table['reference_files'][] = $file;
  23. $table['water_dynamic_tables'] = str_starts_with($full,'sa_water_');
  24. if (!$table['reference_files'] && !$table['water_dynamic_tables']) $table['exact_rows'] = Db::table($full)->count();
  25. }
  26. unset($table);
  27. echo json_encode(['database'=>Db::query('SELECT DATABASE() AS name')[0]['name'],
  28. 'note'=>'静态字面引用仅供筛选线索,无引用不等于无使用;需检查动态ORM、外部项目及历史数据。',
  29. 'tables'=>$tables,
  30. 'foreign_keys'=>Db::query('SELECT TABLE_NAME,COLUMN_NAME,REFERENCED_TABLE_NAME,REFERENCED_COLUMN_NAME FROM information_schema.KEY_COLUMN_USAGE WHERE TABLE_SCHEMA=DATABASE() AND REFERENCED_TABLE_NAME IS NOT NULL'),
  31. ],JSON_PRETTY_PRINT|JSON_UNESCAPED_UNICODE).PHP_EOL;