PluginProbe ʕ •ᴥ•ʔ
Blocks Animation: CSS Animations for Gutenberg Blocks / 3.2.0
Blocks Animation: CSS Animations for Gutenberg Blocks v3.2.0
3.2.0 3.1.11 3.1.10 2.2.5 2.2.6 2.2.7 2.3.0 2.3.1 2.3.2 2.3.3 2.3.4 2.4.0 2.4.1 2.5.0 2.5.1 2.5.2 2.6.0 2.6.1 2.6.10 2.6.11 2.6.12 2.6.13 2.6.2 2.6.3 2.6.4 2.6.5 2.6.6 2.6.7 2.6.8 2.6.9 3.0.0 3.0.1 3.0.10 3.0.11 3.0.12 3.0.2 3.0.3 3.0.4 3.0.5 3.0.6 3.0.7 3.0.8 3.0.9 3.1.0 3.1.1 3.1.2 3.1.3 3.1.4 3.1.5 3.1.6 3.1.7 3.1.8 3.1.9 trunk 1.0.0 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.1.0 1.7.1 1.7.2 1.7.3 1.7.4 1.7.5 2.0.0 2.0.1 2.0.10 2.0.11 2.0.12 2.0.13 2.0.14 2.0.15 2.0.16 2.0.2 2.0.3 2.0.4 2.0.5 2.0.6 2.0.7 2.0.8 2.0.9 2.1.0 2.1.1 2.1.2 2.1.3 2.1.4 2.1.5 2.1.6 2.2.0 2.2.1 2.2.2 2.2.3 2.2.4
blocks-animation / vendor / codeinwp / themeisle-sdk / src / Modules / Migrator.php
blocks-animation / vendor / codeinwp / themeisle-sdk / src / Modules Last commit date
About_us.php 1 week ago Abstract_Migration.php 2 months ago Announcements.php 2 months ago Compatibilities.php 1 year ago Dashboard_widget.php 1 week ago Featured_plugins.php 2 months ago Float_widget.php 1 year ago Licenser.php 2 months ago Logger.php 8 months ago Migrator.php 2 months ago Notification.php 1 year ago Promotions.php 1 week ago Recommendation.php 1 year ago Review.php 8 months ago Rollback.php 1 year ago Script_loader.php 8 months ago Translate.php 1 year ago Translations.php 8 months ago Uninstall_feedback.php 1 week ago Welcome.php 1 year ago
Migrator.php
178 lines
1 <?php
2 /**
3 * The migrator module for ThemeIsle SDK.
4 *
5 * @package ThemeIsleSDK
6 * @subpackage Modules
7 * @copyright Copyright (c) 2024, Themeisle
8 * @license http://opensource.org/licenses/gpl-3.0.php GNU Public License
9 * @since 3.3.50
10 */
11
12 namespace ThemeisleSDK\Modules;
13
14 use ThemeisleSDK\Common\Abstract_Module;
15 use ThemeisleSDK\Product;
16
17 // Exit if accessed directly.
18 if ( ! defined( 'ABSPATH' ) ) {
19 exit;
20 }
21
22 /**
23 * Migrator module for ThemeIsle SDK.
24 *
25 * Allows products to ship PHP migration files that run automatically on
26 * admin page loads. Each product opts in by registering its migrations
27 * directory via the `{product_slug}_sdk_migrations_path` filter.
28 */
29 class Migrator extends Abstract_Module {
30 /**
31 * Option key suffix used to store the list of ran migrations.
32 */
33 const OPTION_SUFFIX = '_ran_migrations';
34
35 /**
36 * Check if we should load the module for this product.
37 *
38 * Always returns true — the actual path check happens lazily at admin_init.
39 *
40 * @param Product $product Product to load the module for.
41 *
42 * @return bool
43 */
44 public function can_load( $product ) {
45 return apply_filters( $product->get_slug() . '_sdk_enable_migrator', true );
46 }
47
48 /**
49 * Load module logic.
50 *
51 * @param Product $product Product to load.
52 *
53 * @return Migrator
54 */
55 public function load( $product ) {
56 $this->product = $product;
57 add_action( 'admin_init', array( $this, 'run_pending' ) );
58 add_action( 'themeisle_sdk_rollback_migration_' . $product->get_slug(), array( $this, 'rollback' ) );
59 return $this;
60 }
61
62 /**
63 * Discover and run any pending migrations for the product.
64 *
65 * Only runs when a version upgrade was detected during this request, indicated
66 * by the themeisle_sdk_update_{slug} action having fired.
67 *
68 * @return void
69 */
70 public function run_pending() {
71 if ( ! did_action( 'themeisle_sdk_update_' . $this->product->get_slug() ) ) {
72 return;
73 }
74
75 $path = $this->get_migrations_path();
76
77 if ( empty( $path ) || ! is_dir( $path ) ) {
78 return;
79 }
80
81 $files = glob( trailingslashit( $path ) . '*.php' );
82
83 if ( empty( $files ) ) {
84 return;
85 }
86
87 sort( $files ); // Alphabetical order = chronological order given timestamp naming.
88
89 $option_key = $this->product->get_key() . self::OPTION_SUFFIX;
90 $ran = get_option( $option_key, array() );
91
92 foreach ( $files as $file ) {
93 $name = basename( $file, '.php' );
94
95 if ( in_array( $name, $ran, true ) ) {
96 continue;
97 }
98
99 try {
100 $migration = require $file; // Migration files return an anonymous class instance.
101
102 if ( ! ( $migration instanceof Abstract_Migration ) ) {
103 continue;
104 }
105
106 if ( ! $migration->should_run() ) {
107 continue;
108 }
109
110 $migration->up();
111 $ran[] = $name;
112 update_option( $option_key, $ran );
113 } catch ( \Throwable $e ) {
114 // Log and stop — leave the migration unrecorded so it retries next load.
115 // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
116 error_log( 'ThemeIsle SDK Migrator: failed to run ' . $name . ': ' . $e->getMessage() );
117 break;
118 }
119 }
120 }
121
122 /**
123 * Roll back a single migration by name.
124 *
125 * Calls down() on the migration and removes it from the ran list so it will
126 * be picked up again on the next upgrade. This method is never called
127 * automatically — products invoke it explicitly when needed.
128 *
129 * @param string $migration_name Migration basename without .php extension.
130 *
131 * @return bool True if rolled back successfully, false if not found or not previously run.
132 */
133 public function rollback( $migration_name ) {
134 $option_key = $this->product->get_key() . self::OPTION_SUFFIX;
135 $ran = get_option( $option_key, array() );
136
137 if ( ! in_array( $migration_name, $ran, true ) ) {
138 return false;
139 }
140
141 $path = $this->get_migrations_path();
142 $file = trailingslashit( $path ) . $migration_name . '.php';
143
144 if ( ! is_file( $file ) ) {
145 return false;
146 }
147
148 try {
149 $migration = require $file;
150
151 if ( ! ( $migration instanceof Abstract_Migration ) ) {
152 return false;
153 }
154
155 $migration->down();
156 update_option( $option_key, array_values( array_diff( $ran, array( $migration_name ) ) ) );
157
158 return true;
159 } catch ( \Throwable $e ) {
160 // phpcs:ignore WordPress.PHP.DevelopmentFunctions.error_log_error_log
161 error_log( 'ThemeIsle SDK Migrator: failed to roll back ' . $migration_name . ': ' . $e->getMessage() );
162
163 return false;
164 }
165 }
166
167 /**
168 * Get the migrations directory path for the current product.
169 *
170 * Products register their path via the `{slug}_sdk_migrations_path` filter.
171 *
172 * @return string Absolute path to the migrations directory, or empty string.
173 */
174 private function get_migrations_path() {
175 return (string) apply_filters( $this->product->get_slug() . '_sdk_migrations_path', '' );
176 }
177 }
178