PluginProbe
Redirection / 3.0
Redirection v3.0
5.10.0 5.9.0 5.8.1 5.8.0 3.7.2 3.7.3 4.0 4.0.1 4.1 4.1.1 4.2 4.2.1 4.2.2 4.2.3 4.3 4.3.1 4.3.2 4.3.3 4.4 4.4.1 4.4.2 4.5 4.5.1 4.6.2 4.7.1 All 130 releases
redirection / redirection-admin.php

redirection-admin.php in Redirection 3.0, at redirection-admin.php

419 lines 13.6 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 include dirname( __FILE__ ).'/models/group.php';
4 include dirname( __FILE__ ).'/models/monitor.php';
5 include dirname( __FILE__ ).'/models/file-io.php';
6
7 define( 'RED_DEFAULT_PER_PAGE', 25 );
8 define( 'RED_MAX_PER_PAGE', 200 );
9
10 class Redirection_Admin {
11 private static $instance = null;
12 private $monitor;
13
14 static function init() {
15 if ( is_null( self::$instance ) ) {
16 self::$instance = new Redirection_Admin();
17
18 load_plugin_textdomain( 'redirection', false, dirname( plugin_basename( REDIRECTION_FILE ) ).'/locale/' );
19 }
20
21 return self::$instance;
22 }
23
24 function __construct() {
25 add_action( 'admin_menu', array( $this, 'admin_menu' ) );
26 add_action( 'plugin_action_links_'.basename( dirname( REDIRECTION_FILE ) ).'/'.basename( REDIRECTION_FILE ), array( $this, 'plugin_settings' ), 10, 4 );
27 add_filter( 'redirection_save_options', array( $this, 'flush_schedule' ) );
28 add_filter( 'set-screen-option', array( $this, 'set_per_page' ), 10, 3 );
29 add_action( 'redirection_redirect_updated', array( $this, 'set_default_group' ), 10, 2 );
30
31 if ( defined( 'REDIRECTION_FLYING_SOLO' ) && REDIRECTION_FLYING_SOLO ) {
32 add_filter( 'script_loader_src', array( $this, 'flying_solo' ), 10, 2 );
33 }
34
35 register_deactivation_hook( REDIRECTION_FILE, array( 'Redirection_Admin', 'plugin_deactivated' ) );
36 register_uninstall_hook( REDIRECTION_FILE, array( 'Redirection_Admin', 'plugin_uninstall' ) );
37
38 $this->monitor = new Red_Monitor( red_get_options() );
39 }
40
41 // These are only called on the single standard site, or in the network admin of the multisite - they run across all available sites
42 public static function plugin_activated() {
43 if ( is_network_admin() ) {
44 foreach ( get_sites() as $site ) {
45 switch_to_blog( $site->blog_id );
46
47 Redirection_Admin::update();
48 Red_Flusher::schedule();
49 red_set_options();
50
51 restore_current_blog();
52 }
53 } else {
54 Redirection_Admin::update();
55 Red_Flusher::schedule();
56 red_set_options();
57 }
58 }
59
60 // These are only called on the single standard site, or in the network admin of the multisite - they run across all available sites
61 public static function plugin_deactivated() {
62 if ( is_network_admin() ) {
63 foreach ( get_sites() as $site ) {
64 switch_to_blog( $site->blog_id );
65
66 Red_Flusher::clear();
67
68 restore_current_blog();
69 }
70 } else {
71 Red_Flusher::clear();
72 }
73 }
74
75 // These are only called on the single standard site, or in the network admin of the multisite - they run across all available sites
76 public static function plugin_uninstall() {
77 include_once dirname( REDIRECTION_FILE ).'/models/database.php';
78
79 $db = new RE_Database();
80
81 if ( is_network_admin() ) {
82 foreach ( get_sites() as $site ) {
83 switch_to_blog( $site->blog_id );
84
85 $db->remove( REDIRECTION_FILE );
86
87 restore_current_blog();
88 }
89 } else {
90 $db->remove( REDIRECTION_FILE );
91 }
92 }
93
94 private static function update() {
95 $version = get_option( 'redirection_version' );
96
97 Red_Flusher::schedule();
98
99 if ( $version !== REDIRECTION_DB_VERSION ) {
100 include_once dirname( REDIRECTION_FILE ).'/models/database.php';
101
102 $database = new RE_Database();
103
104 if ( $version === false ) {
105 $database->install();
106 }
107
108 $database->upgrade( $version, REDIRECTION_DB_VERSION );
109 }
110 }
111
112 // So it finally came to this... some plugins include their JS in all pages, whether they are needed or not. If there is an error
113 // then this can prevent Redirection running, it's a little sensitive about that. We use the nuclear option here to disable
114 // all other JS while viewing Redirection
115 public function flying_solo( $src, $handle ) {
116 if ( isset( $_SERVER['REQUEST_URI'] ) && strpos( $_SERVER['REQUEST_URI'], 'page=redirection.php' ) !== false ) {
117 if ( substr( $src, 0, 4 ) === 'http' && $handle !== 'redirection' && strpos( $src, 'plugins' ) !== false ) {
118 if ( $this->ignore_this_plugin( $src ) ) {
119 return false;
120 }
121 }
122 }
123
124 return $src;
125 }
126
127 private function ignore_this_plugin( $src ) {
128 if ( strpos( $src, 'mootools' ) !== false ) {
129 return true;
130 }
131
132 if ( strpos( $src, 'wp-seo-' ) !== false ) {
133 return true;
134 }
135
136 return false;
137 }
138
139 public function flush_schedule( $options ) {
140 Red_Flusher::schedule();
141 return $options;
142 }
143
144 function set_per_page( $status, $option, $value ) {
145 if ( $option === 'redirection_log_per_page' ) {
146 return max( 1, min( intval( $value, 10 ), RED_MAX_PER_PAGE ) );
147 }
148
149 return $status;
150 }
151
152 function plugin_settings( $links ) {
153 $settings_link = '<a href="tools.php?page='.basename( REDIRECTION_FILE ).'&amp;sub=options">'.__( 'Settings', 'redirection' ).'</a>';
154 array_unshift( $links, $settings_link );
155 return $links;
156 }
157
158 function redirection_head() {
159 global $wp_version;
160
161 $build = REDIRECTION_VERSION.'-'.REDIRECTION_BUILD;
162 $options = red_get_options();
163 $versions = array(
164 'Plugin: '.REDIRECTION_VERSION,
165 'WordPress: '.$wp_version,
166 'PHP: '.phpversion(),
167 'Browser: '.Redirection_Request::get_user_agent(),
168 );
169
170 $this->inject();
171
172 if ( ! isset( $_GET['sub'] ) || ( isset( $_GET['sub'] ) && ( in_array( $_GET['sub'], array( 'log', '404s', 'groups' ) ) ) ) ) {
173 add_screen_option( 'per_page', array( 'label' => sprintf( __( 'Log entries (%d max)', 'redirection' ), RED_MAX_PER_PAGE ), 'default' => RED_DEFAULT_PER_PAGE, 'option' => 'redirection_log_per_page' ) );
174 }
175
176 if ( defined( 'REDIRECTION_DEV_MODE' ) && REDIRECTION_DEV_MODE ) {
177 wp_enqueue_script( 'redirection', 'http://localhost:3312/redirection.js', array(), $build, true );
178 } else {
179 wp_enqueue_script( 'redirection', plugin_dir_url( REDIRECTION_FILE ).'redirection.js', array(), $build, true );
180 }
181
182 wp_enqueue_style( 'redirection', plugin_dir_url( REDIRECTION_FILE ).'redirection.css', array(), $build );
183
184 wp_localize_script( 'redirection', 'Redirectioni10n', array(
185 'WP_API_root' => esc_url_raw( get_rest_url() ),
186 'WP_API_nonce' => wp_create_nonce( 'wp_rest' ),
187 'pluginBaseUrl' => plugins_url( '', REDIRECTION_FILE ),
188 'pluginRoot' => admin_url( 'tools.php?page=redirection.php' ),
189 'per_page' => $this->get_per_page(),
190 'locale' => $this->get_i18n_data(),
191 'localeSlug' => get_locale(),
192 'token' => $options['token'],
193 'autoGenerate' => $options['auto_target'],
194 'versions' => implode( "\n", $versions ),
195 'version' => REDIRECTION_VERSION,
196 ) );
197
198 $this->add_help_tab();
199 }
200
201 private function add_help_tab() {
202 $title = __( 'Redirection Support', 'redirection' );
203 $content = sprintf( __( 'You can find full documentation about using Redirection on the <a href="%s" target="_blank">redirection.me</a> support site.', 'redirection' ), 'https://redirection.me/support/?utm_source=redirection&utm_medium=plugin&utm_campaign=context-help' );
204
205 $current_screen = get_current_screen();
206 $current_screen->add_help_tab( array(
207 'id' => 'redirection',
208 'title' => 'Redirection',
209 'content' => "<h2>$title</h2><p>$content</p>",
210 ) );
211 }
212
213 private function get_per_page() {
214 $per_page = intval( get_user_meta( get_current_user_id(), 'redirection_log_per_page', true ), 10 );
215
216 return $per_page > 0 ? $per_page : RED_DEFAULT_PER_PAGE;
217 }
218
219 private function get_i18n_data() {
220 $i18n_json = dirname( REDIRECTION_FILE ) . '/locale/json/redirection-' . get_locale() . '.json';
221
222 if ( is_file( $i18n_json ) && is_readable( $i18n_json ) ) {
223 $locale_data = @file_get_contents( $i18n_json );
224
225 if ( $locale_data ) {
226 return json_decode( $locale_data );
227 }
228 }
229
230 // Return empty if we have nothing to return so it doesn't fail when parsed in JS
231 return array();
232 }
233
234 function admin_menu() {
235 $hook = add_management_page( 'Redirection', 'Redirection', apply_filters( 'redirection_role', 'administrator' ), basename( REDIRECTION_FILE ), array( &$this, 'admin_screen' ) );
236 add_action( 'load-'.$hook, array( $this, 'redirection_head' ) );
237 }
238
239 private function check_minimum_wp() {
240 $wp_version = get_bloginfo( 'version' );
241
242 if ( version_compare( $wp_version, REDIRECTION_MIN_WP, '<' ) ) {
243 ?>
244 <div class="react-error">
245 <h1><?php _e( 'Unable to load Redirection', 'redirection' ); ?></h1>
246 <p style="text-align: left"><?php printf( __( 'Redirection requires WordPress v%1s, you are using v%2s - please update your WordPress', 'redirection' ), REDIRECTION_MIN_WP, $wp_version ); ?></p>
247 </div>
248 <?php
249 return false;
250 }
251
252 return true;
253 }
254
255 private function check_tables_exist() {
256 include_once dirname( REDIRECTION_FILE ).'/models/database.php';
257
258 $database = new RE_Database();
259 $status = $database->get_status();
260
261 if ( $status['status'] !== 'good' ) {
262 ?>
263 <div class="error">
264 <h3><?php _e( 'Redirection not installed properly', 'redirection' ); ?></h3>
265 <p style="text-align: left"><?php printf( __( 'Problems were detected with your database tables. Please visit the <a href="%s">support page</a> for more details.', 'redirection' ), 'tools.php?page=redirection.php&amp;sub=support' ); ?></p>
266 </div>
267 <?php
268
269 return false;
270 }
271
272 return true;
273 }
274
275 public function set_default_group( $id, $redirect ) {
276 red_set_options( array( 'last_group_id' => $redirect->get_group_id() ) );
277 }
278
279 function admin_screen() {
280 $version = get_plugin_data( REDIRECTION_FILE );
281 $version = $version['Version'];
282
283 Redirection_Admin::update();
284
285 if ( $this->check_minimum_wp() === false ) {
286 return;
287 }
288
289 if ( $this->check_tables_exist() === false && ( ! isset( $_GET['sub'] ) || $_GET['sub'] !== 'support' ) ) {
290 return false;
291 }
292 ?>
293 <div id="react-ui">
294 <div class="react-loading">
295 <h1><?php _e( 'Loading, please wait...', 'redirection' ); ?></h1>
296
297 <span class="react-loading-spinner"></span>
298 </div>
299 <noscript>Please enable JavaScript</noscript>
300
301 <div class="react-error" style="display: none">
302 <h1><?php _e( 'Unable to load Redirection', 'redirection' ); ?> v<?php echo esc_html( $version ); ?></h1>
303 <p><?php _e( "This may be caused by another plugin - look at your browser's error console for more details.", 'redirection' ); ?></p>
304 <p><?php _e( 'If you are using a page caching plugin or service (CloudFlare, OVH, etc) then you can also try clearing that cache.', 'redirection' ); ?></p>
305 <p><?php _e( 'Also check if your browser is able to load <code>redirection.js</code>:', 'redirection' ); ?></p>
306 <p><code><?php echo esc_html( plugin_dir_url( REDIRECTION_FILE ).'redirection.js?ver='.urlencode( REDIRECTION_VERSION ).'-'.urlencode( REDIRECTION_BUILD ) ); ?></code></p>
307 <p><?php _e( 'Please note that Redirection requires the WordPress REST API to be enabled. If you have disabled this then you won\'t be able to use Redirection', 'redirection' ); ?></p>
308 <p><?php _e( "If you think Redirection is at fault then create an issue.", 'redirection' ); ?></p>
309 <p class="versions"><?php _e( '<code>Redirectioni10n</code> is not defined. This usually means another plugin is blocking Redirection from loading. Please disable all plugins and try again.', 'redirection' ); ?></p>
310 <p>
311 <a class="button-primary" target="_blank" href="https://github.com/johngodley/redirection/issues/new?title=Problem%20starting%20Redirection%20<?php echo esc_attr( $version ) ?>">
312 <?php _e( 'Create Issue', 'redirection' ); ?>
313 </a>
314 </p>
315 </div>
316 </div>
317
318 <script>
319 var prevError = window.onerror;
320 var errors = [];
321 var timeout = 0;
322 var timer = setInterval( function() {
323 if ( isRedirectionLoaded() ) {
324 resetAll();
325 } else if ( errors.length > 0 || timeout++ === 5 ) {
326 showError();
327 }
328 }, 5000 );
329
330 function isRedirectionLoaded() {
331 return typeof redirection !== 'undefined';
332 }
333
334 function showError() {
335 var errorText = "";
336
337 if ( errors.length > 0 ) {
338 errorText = "```\n" + errors.join( ',' ) + "\n```\n\n";
339 }
340
341 resetAll();
342 document.querySelector( '.react-loading' ).style.display = 'none';
343 document.querySelector( '.react-error' ).style.display = 'block';
344
345 if ( typeof Redirectioni10n !== 'undefined' ) {
346 document.querySelector( '.versions' ).innerHTML = Redirectioni10n.versions.replace( /\n/g, '<br />' );
347 document.querySelector( '.react-error .button-primary' ).href += '&body=' + encodeURIComponent( errorText ) + encodeURIComponent( Redirectioni10n.versions );
348 }
349 }
350
351 function resetAll() {
352 clearInterval( timer );
353 window.onerror = prevError;
354 }
355
356 window.onerror = function( error, url, line ) {
357 console.error( error );
358 errors.push( error + ' ' + url + ' ' + line );
359 };
360 </script>
361 <?php
362 }
363
364 private function user_has_access() {
365 return current_user_can( apply_filters( 'redirection_role', 'administrator' ) );
366 }
367
368 function inject() {
369 if ( isset( $_GET['page'] ) && isset( $_GET['sub'] ) && $_GET['page'] === 'redirection.php' ) {
370 $this->tryExportLogs();
371 $this->tryExportRedirects();
372 $this->tryExportRSS();
373 }
374 }
375
376 function tryExportRSS() {
377 if ( isset( $_GET['token'] ) && $_GET['sub'] === 'rss' ) {
378 $options = red_get_options();
379
380 if ( $_GET['token'] === $options['token'] && !empty( $options['token'] ) ) {
381 $items = Red_Item::get_all_for_module( intval( $_GET['module'] ) );
382
383 $exporter = Red_FileIO::create( 'rss' );
384 $exporter->force_download();
385 echo $exporter->get_data( $items, array() );
386 die();
387 }
388 }
389 }
390
391 private function tryExportLogs() {
392 if ( $this->user_has_access() && isset( $_POST['export-csv'] ) && check_admin_referer( 'wp_rest' ) ) {
393 if ( isset( $_GET['sub'] ) && $_GET['sub'] === 'log' ) {
394 RE_Log::export_to_csv();
395 } else {
396 RE_404::export_to_csv();
397 }
398
399 die();
400 }
401 }
402
403 private function tryExportRedirects() {
404 if ( $this->user_has_access() && $_GET['sub'] === 'io' && isset( $_GET['exporter'] ) && isset( $_GET['export'] ) ) {
405 $export = Red_FileIO::export( $_GET['export'], $_GET['exporter'] );
406
407 if ( $export !== false ) {
408 $export['exporter']->force_download();
409 echo $export['data'];
410 die();
411 }
412 }
413 }
414 }
415
416 register_activation_hook( REDIRECTION_FILE, array( 'Redirection_Admin', 'plugin_activated' ) );
417
418 add_action( 'init', array( 'Redirection_Admin', 'init' ) );
419