修改配置信息,并保存为任意名字的php文件,然后上传到根目录运行



<?php
/**

  • Typecho 域名批量更新工具
  • 功能:批量更新文章内容中的域名链接
  • 使用方法:
    1. 修改下面的数据库路径和域名
    1. 访问此脚本
    1. 删除此文件
      */

// 🔧 配置信息
$db_path = DIR . '/usr/XXX.db'; // SQLite数据库文件路径
$old_domain = 'https://www.hivps.cn'; // 旧域名
$new_domain = 'https://blog.hivps.cn'; // 新域名

echo "

Typecho 域名批量更新工具

";
echo "

数据库路径:" . htmlspecialchars($db_path) . "

";
echo "

旧域名:" . htmlspecialchars($old_domain) . "

";
echo "

新域名:" . htmlspecialchars($new_domain) . "

";

if (!file_exists($db_path)) {

echo "<p style='color: red;'>❌ 数据库文件不存在</p>";
exit;

}

try {

$db = new SQLite3($db_path);

// 备份函数
function backupTable($db, $table_name) {
    $backup_table = $table_name . '_backup_' . date('Ymd_His');
    $db->exec("CREATE TABLE $backup_table AS SELECT * FROM $table_name");
    echo "<p style='color: blue;'>📋 已备份表: $backup_table</p>";
    return $backup_table;
}

echo "<h3>🔄 开始更新...</h3>";

// 1. 更新文章内容 (table.contents)
echo "<p>📝 更新文章内容...</p>";
backupTable($db, 'typecho_contents');

$sql1 = "UPDATE typecho_contents SET text = REPLACE(text, ?, ?) WHERE text LIKE ?";
$stmt1 = $db->prepare($sql1);
$stmt1->bindValue(1, $old_domain, SQLITE3_TEXT);
$stmt1->bindValue(2, $new_domain, SQLITE3_TEXT);
$stmt1->bindValue(3, '%' . $old_domain . '%', SQLITE3_TEXT);
$result1 = $stmt1->execute();
$changes1 = $db->changes();
echo "<p style='color: green;'>✅ 文章内容更新了 {$changes1} 条记录</p>";

// 2. 更新文章字段中的链接 (table.contents.text)
echo "<p>📝 更新文章字段链接...</p>";
$sql2 = "UPDATE typecho_contents SET 
            title = REPLACE(title, ?, ?),
            slug = REPLACE(slug, ?, ?)
          WHERE (title LIKE ? OR slug LIKE ?)";
$stmt2 = $db->prepare($sql2);
$stmt2->bindValue(1, $old_domain, SQLITE3_TEXT);
$stmt2->bindValue(2, $new_domain, SQLITE3_TEXT);
$stmt2->bindValue(3, $old_domain, SQLITE3_TEXT);
$stmt2->bindValue(4, $new_domain, SQLITE3_TEXT);
$stmt2->bindValue(5, '%' . $old_domain . '%', SQLITE3_TEXT);
$stmt2->bindValue(6, '%' . $old_domain . '%', SQLITE3_TEXT);
$result2 = $stmt2->execute();
$changes2 = $db->changes();
echo "<p style='color: green;'>✅ 文章字段更新了 {$changes2} 条记录</p>";

// 3. 更新配置中的网站地址
echo "<p>⚙️ 更新网站配置...</p>";
$config_updates = [
    'siteUrl' => $new_domain,
    'themeUrl' => $new_domain . '/usr/themes',
    'pluginUrl' => $new_domain . '/usr/plugins',
    'attachmentUrl' => $new_domain . '/usr/uploads'
];

foreach ($config_updates as $key => $value) {
    $sql3 = "UPDATE typecho_options SET value = ? WHERE name = ?";
    $stmt3 = $db->prepare($sql3);
    $stmt3->bindValue(1, $value, SQLITE3_TEXT);
    $stmt3->bindValue(2, $key, SQLITE3_TEXT);
    $stmt3->execute();
    echo "<p style='color: blue;'>🔧 更新配置 {$key}: {$value}</p>";
}

// 4. 更新评论中的链接
echo "<p>💬 更新评论内容...</p>";
$sql4 = "UPDATE typecho_comments SET text = REPLACE(text, ?, ?), url = REPLACE(url, ?, ?) WHERE text LIKE ? OR url LIKE ?";
$stmt4 = $db->prepare($sql4);
$stmt4->bindValue(1, $old_domain, SQLITE3_TEXT);
$stmt4->bindValue(2, $new_domain, SQLITE3_TEXT);
$stmt4->bindValue(3, $old_domain, SQLITE3_TEXT);
$stmt4->bindValue(4, $new_domain, SQLITE3_TEXT);
$stmt4->bindValue(5, '%' . $old_domain . '%', SQLITE3_TEXT);
$stmt4->bindValue(6, '%' . $old_domain . '%', SQLITE3_TEXT);
$result4 = $stmt4->execute();
$changes4 = $db->changes();
echo "<p style='color: green;'>✅ 评论内容更新了 {$changes4} 条记录</p>";

// 5. 更新附件表(如果存在)
$table_check = "SELECT name FROM sqlite_master WHERE type='table' AND name='typecho_attachments'";
$check_result = $db->querySingle($table_check);

if ($check_result) {
    echo "<p>📎 更新附件信息...</p>";
    $sql5 = "UPDATE typecho_attachments SET 
                path = REPLACE(path, ?, ?),
                url = REPLACE(url, ?, ?),
                thumbnail = REPLACE(thumbnail, ?, ?)
              WHERE url LIKE ? OR thumbnail LIKE ?";
    $stmt5 = $db->prepare($sql5);
    $stmt5->bindValue(1, $old_domain, SQLITE3_TEXT);
    $stmt5->bindValue(2, $new_domain, SQLITE3_TEXT);
    $stmt5->bindValue(3, $old_domain, SQLITE3_TEXT);
    $stmt5->bindValue(4, $new_domain, SQLITE3_TEXT);
    $stmt5->bindValue(5, $old_domain, SQLITE3_TEXT);
    $stmt5->bindValue(6, $new_domain, SQLITE3_TEXT);
    $stmt5->bindValue(7, '%' . $old_domain . '%', SQLITE3_TEXT);
    $stmt5->bindValue(8, '%' . $old_domain . '%', SQLITE3_TEXT);
    $result5 = $stmt5->execute();
    $changes5 = $db->changes();
    echo "<p style='color: green;'>✅ 附件信息更新了 {$changes5} 条记录</p>";
}

// 验证更新结果
echo "<h3>🔍 验证更新结果</h3>";
$verify_sql = "SELECT COUNT(*) as count FROM typecho_contents WHERE text LIKE ?";
$verify_stmt = $db->prepare($verify_sql);
$verify_stmt->bindValue(1, '%' . $old_domain . '%', SQLITE3_TEXT);
$verify_result = $verify_stmt->execute();
$verify_count = $verify_result->fetchArray();

if ($verify_count['count'] > 0) {
    echo "<p style='color: orange;'>⚠️ 仍有 {$verify_count['count']} 条记录包含旧域名,请检查</p>";
} else {
    echo "<p style='color: green; font-weight: bold;'>✅ 验证通过!所有旧域名链接已更新</p>";
}

$db->close();

echo "<hr>";
echo "<h3 style='color: green;'>🎉 域名更新完成!</h3>";
echo "<p>更新内容:</p>";
echo "<ul>";
echo "<li>文章内容:{$changes1} 条</li>";
echo "<li>文章字段:{$changes2} 条</li>";
echo "<li>评论内容:{$changes4} 条</li>";
if (isset($changes5)) {
    echo "<li>附件信息:{$changes5} 条</li>";
}
echo "</ul>";
echo "<p>✅ 网站配置已更新</p>";
echo "<p>📋 已创建数据备份</p>";
echo "<hr>";
echo "<h4>🔄 后续操作:</h4>";
echo "<ol>";
echo "<li>检查网站首页显示是否正常</li>";
echo "<li>测试文章内容中的链接是否正确</li>";
echo "<li>验证附件是否能正常访问</li>";
echo "<li>更新CDN或静态文件服务(如果有)</li>";
echo "</ol>";
echo "<p style='color: red; font-size: 1.2em; font-weight: bold;'>⚠️ 请立即删除此更新脚本文件!</p>";

} catch (Exception $e) {

echo "<h3 style='color: red;'>❌ 更新失败</h3>";
echo "<p><strong>错误信息:</strong>" . htmlspecialchars($e->getMessage()) . "</p>";
echo "<p><strong>建议:</strong>请备份数据库后重试</p>";

}
?>

最后修改:2025 年 12 月 04 日
如果觉得我的文章对你有用,请随意赞赏