返回

WordPress 修订版本管理:从数据库优化到恢复可用性

mysql

如何将 WordPress 修订版本转移到自定义表并恢复

简介

WordPress 中的修订版本是跟踪帖子或页面随着时间的推移而发生更改的宝贵工具。然而,当修订版本数量众多时,它们可能会对数据库造成负担。本文将指导您如何将 WordPress 修订版本转移到自定义表中,并在编辑页面加载时将特定帖子的修订版本恢复回 wp_posts 表中。

步骤

1. 检查表格是否存在

使用 is_table_exist() 函数检查自定义表 posts_revisions 是否存在。

function is_table_exist($table_name) {
    global $wpdb;

    $sql = "SHOW TABLES LIKE '" . esc_sql($wpdb->prefix . $table_name) . "'";
    $table = $wpdb->get_var($sql);

    return $table == $wpdb->prefix . $table_name;
}

2. 处理修订版本

如果 wp_posts 表中存在修订版本:

使用 has_post_revisions() 函数检查 wp_posts 表中是否存在修订版本。

function has_post_revisions() {
    global $wpdb;

    $revision_count = $wpdb->get_var( "SELECT COUNT(*) FROM $wpdb->posts WHERE post_type = 'revision'" );

    return $revision_count > 0;
}

转移修订版本到自定义表:

使用 transfer_post_revisions_to_custom_table() 函数将修订版本转移到自定义表。

function transfer_post_revisions_to_custom_table() {
    global $wpdb;

    // 获取帖子表中的修订版本
    $revisions = $wpdb->get_results(
        "SELECT * FROM $wpdb->posts WHERE post_type = 'revision'"
    );

    if ($revisions) {
        foreach ($revisions as $revision) {
            // 检查自定义表中是否已存在修订版本
            $existing_revision = $wpdb->get_row(
                $wpdb->prepare(
                    "SELECT * FROM {$wpdb->prefix}posts_revisions WHERE id = %d",
                    $revision->ID
                )
            );

            // 如果修订版本不存在,则插入到自定义表中
            if (!$existing_revision) {
                $wpdb->insert(
                    $wpdb->prefix . 'posts_revisions',
                    array(
                        'id' => $revision->ID,
                        'post_author' => $revision->post_author,
                        'post_date' => $revision->post_date,
                        'post_date_gmt' => $revision->post_date_gmt,
                        'post_content' => $revision->post_content,
                        'post_title' => $revision->post_title,
                        'post_excerpt' => $revision->post_excerpt,
                        'post_status' => $revision->post_status,
                        'comment_status' => $revision->comment_status,
                        'ping_status' => $revision->ping_status,
                        'post_password' => $revision->post_password,
                        'post_name' => $revision->post_name,
                        'to_ping' => $revision->to_ping,
                        'pinged' => $revision->pinged,
                        'post_modified' => $revision->post_modified,
                        'post_modified_gmt' => $revision->post_modified_gmt,
                        'post_content_filtered' => $revision->post_content_filtered,
                        'post_parent' => $revision->post_parent,
                        'guid' => $revision->guid,
                        'menu_order' => $revision->menu_order,
                        'post_type' => $revision->post_type,
                        'post_mime_type' => $revision->post_mime_type,
                        'comment_count' => $revision->comment_count
                    )
                );
            }
        }

        // 从帖子表中删除修订版本
        $wpdb->query(
            $wpdb->prepare(
                "DELETE FROM $wpdb->posts WHERE post_type = 'revision'"
            )
        );
    }
}

3. 创建自定义表

如果自定义表不存在,使用 create_posts_revisions_table() 函数创建它。

function create_posts_revisions_table() {
    global $wpdb;

    $table_name = $wpdb->prefix . 'posts_revisions';
    $charset_collate = $wpdb->get_charset_collate();

    $sql = "CREATE TABLE $table_name (
        id bigint(20) NOT NULL AUTO_INCREMENT,
        post_author bigint(20) unsigned NOT NULL default '0',
        post_date datetime NOT NULL default '0000-00-00 00:00:00',
        post_date_gmt datetime NOT NULL default '0000-00-00 00:00:00',
        post_content longtext NOT NULL,
        post_title text NOT NULL,
        post_excerpt text NOT NULL,
        post_status varchar(20) NOT NULL default 'publish',
        comment_status varchar(20) NOT NULL default 'open',
        ping_status varchar(20) NOT NULL default 'open',
        post_password varchar(255) NOT NULL default '',
        post_name varchar(200) NOT NULL default '',
        to_ping text NOT NULL,
        pinged text NOT NULL,
        post_modified datetime NOT NULL default '0000-00-00 00:00:00',
        post_modified_gmt datetime NOT NULL default '0000-00-00 00:00:00',
        post_content_filtered longtext NOT NULL,
        post_parent bigint(20) unsigned NOT NULL default '0',
        guid varchar(255) NOT NULL default '',
        menu_order int(11) NOT NULL default '0',
        post_type varchar(20) NOT NULL default 'post',
        post_mime_type varchar(100) NOT NULL default '',
        comment_count bigint(20) NOT NULL default '0',
        PRIMARY KEY  (id),
        KEY post_name (post_name(191)),
        KEY type_status_date (post_type,post_status,post_date,ID),
        KEY post_parent (post_parent),
        KEY post_author (post_author)
    ) $charset_collate;";

    require_once( ABSPATH . 'wp-admin/includes/upgrade.php' );
    dbDelta( $sql );
}

4. 检查是否为编辑页面

使用 is_admin_post_edit_page() 函数检查是否为编辑页面。

function is_admin_post_edit_page() {
    if ( isset($_GET['action']) ) {
        if ($_GET['action'] == "edit" ) {
            return true;
        }
    }

    return false;
}

5. 恢复修订版本

如果为编辑页面,从自定义表中恢复特定帖子的修订版本。

$this_post_id = $_GET['post'];
global $wpdb;
$table_name = $wpdb->prefix . "posts_revisions";
$revisionArray = $wpdb->get_results("SELECT * FROM $table_name WHERE post_parent = '$this_post_id'");
foreach ($revisionArray as $revision) {
    $wpdb->insert(
        $wpdb->posts,
        array(
            'ID' => $revision->id,
            'post_author' => $revision->post_author,
            'post_date' => $revision->post_date,
            'post_date_gmt' => $revision->post_date_gmt,
            'post_content' => $revision->post_content,
            'post_title' => $revision->post_title,
            'post_excerpt' => $revision->post_excerpt,
            'post_status' => $revision->post_status,
            'comment_status' => $revision->comment_status,
            'ping_status' => $revision->ping_status,
            'post_password' => $revision->post_password,
            'post_name' => $revision->post_name,
            'to_ping' => $revision->to_ping,
            'pinged' => $revision->pinged,
            'post_modified' => $revision->post_modified,
            'post_modified_gmt' => $revision->post_modified_gmt,
            'post_content_filtered' => $revision