Skip to content

Instantly share code, notes, and snippets.

@PatelUtkarsh
Last active June 28, 2018 13:05
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save PatelUtkarsh/58f5f283780f6dbe58690dac13b46a08 to your computer and use it in GitHub Desktop.
Save PatelUtkarsh/58f5f283780f6dbe58690dac13b46a08 to your computer and use it in GitHub Desktop.
Custom table to WordPress schema migration base class proof of concept. NOT TESTED.
<?php
/**
* Migration Abstract class.
*
* Should inherit this class and all documented class variable must overwrite in child class for this to work.
*
* @package rtCamp
*/
namespace rtCamp\TableMigrate;
abstract class Migrate {
/**
* Table to migrate.
*
* @type string
*/
const TABLE_NAME = '';
public $total_records;
public $limit = 100;
public $migrated_records = 0;
public $current_row;
/**
* Post type name.
*
* @var string
*/
public $post_type;
/**
* Taxonomy name.
*
* @var string
*/
public $tax;
/**
* Mapping should have wp_insert / wp_term key and mapping value from table column.
*
* example:
* [
* 'post_title' => 'column_name',
* 'post_status' => ['name' => 'column_name', 'callback' => {callback function}]
* 'meta_input' => [
* 'meta_key' => 'column_name',
* 'meta_key2' => ['name' => 'col_name', 'callback' => {callback function} ]
* ] ]
*
* @var array
*/
public $mapping = [];
/**
* Is CPT migration.
*
* @var bool
*/
public $is_cpt;
/**
* Is taxonomy migration.
*
* @var bool
*/
public $is_tax;
public function __construct() {
if ( $this->is_mapping_exists() ) {
echo 'Mapping can\'t be empty in' . get_class( $this );
die;
}
$this->total_records = intval( $this->get_total_records() );
}
protected function is_mapping_exists() {
return ! empty( $this->mapping );
}
public function start() {
if ( $this->migrated_records === $this->total_records ) { // Migration complete.
return true;
}
while ( $this->migrated_records !== $this->total_records ) {
$data = $this->get_next_records();
foreach ( $data as $row ) {
$this->current_row = $row;
$wp_data = $this->map_columns( $this->mapping, $row );
// Insert data.
if ( $this->is_cpt ) {
$wp_data['post_type'] = $this->post_type;
wp_insert_post( $wp_data );
} elseif ( $this->is_tax ) {
$term = $wp_data['term'];
$term_meta = $wp_data['term_meta'];
unset( $wp_data['term'], $wp_data['term_meta'] );
$term_id = wp_insert_term( $term, $this->tax, $wp_data );
foreach ( $term_meta as $key => $val ) {
add_term_meta( $term_id['term_id'], $key, $val );
}
}
$this->migrated_records ++;
}
}
$this->current_row = null;
}
public function map_columns( $mapping, $row ) {
$wp_data = [];
foreach ( $mapping as $wp_col => $mapping_table_col ) {
if ( is_array( $mapping_table_col )
&&
array_key_exists( 'name', $mapping_table_col )
&&
array_key_exists( 'callback', $mapping_table_col )
&&
is_callable( $mapping_table_col['callback'] ) ) {
$wp_data[ $wp_col ] = call_user_func( $mapping_table_col['callback'], $row[ $mapping_table_col['name'] ], $mapping_table_col['name'], $row, $this );
} else if ( is_array( $mapping_table_col ) ) {
// In case of array of array for post_meta and term_meta.
$wp_data[ $wp_col ] = $this->map_columns( $mapping_table_col, $row );
} else {
$wp_data[ $wp_col ] = $row[ $mapping_table_col ];
}
}
return $wp_data;
}
public function get_query() {
return sprintf( 'SELECT * FROM %s LIMIT %u, %u', static::TABLE_NAME, $this->migrated_records, $this->limit );
}
public function get_total_records() {
global $wpdb;
$sql = sprintf( 'SELECT COUNT(*) FROM %s', static::TABLE_NAME );
return $wpdb->get_var( $sql );
}
public function get_next_records() {
global $wpdb;
$sql = $this->get_query();
return $wpdb->get_results( $sql, ARRAY_A ); // Returns array.
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment