Create a gist now

Instantly share code, notes, and snippets.

<?php
/**
* Plugin Name: T5 WP Load Order
* Description: Hooks into every action and creates a list of available variables, constants, functions, classes and files.
* Plugin URI:
* Version: 2012.11.05
* Author: Thomas Scholz
* Author URI: http://toscho.de
* Licence: MIT
* License URI: http://opensource.org/licenses/MIT
*/
/* Install as mu-plugin, UNCOMMENT the next line
* Be aware this will be slow, write actions on the log file will happen long
* after the request is finished, so be patient.
*/
#new T5_Track_Load;
class T5_Track_Load
{
/**
* Destination for log file. For each URL a new one.
*
* @type string
*/
protected $log_path = '';
/**
* Actions to ignore.
*
* @type array
*/
protected $do_not_track = array (
'gettext',
'gettext_with_context'
);
/**
* Already logged details.
*
* @type array
*/
protected $logged = array (
'files' => array (),
'globals' => array (),
'constants' => array (),
'classes' => array (),
'functions' => array (),
);
/**
* Constructor
*
* @since 2012.11.05
* @return object of this class
*/
public function __construct()
{
$this->set_log_file_path();
$this->track();
add_action( 'all', array ( $this, 'track' ), 100, 100 );
}
/**
* Collect and write data.
*
* @return void
*/
public function track()
{
static $called = FALSE;
$hook = $called ? current_filter() : 'Plugin called: ' . __FILE__;
$called = TRUE;
if ( in_array( $hook, $this->do_not_track ) )
return;
// Track each hooks just once.
$this->do_not_track[] = $hook;
// start tracking
$files = $this->track_files();
$globals = $this->track_globals();
$constants = $this->track_constants();
$classes = $this->track_classes();
$functions = $this->track_functions();
$empty_log = FALSE;
if ( '' === $files.$globals.$constants.$classes.$functions ) {
$empty_log = TRUE;
}
$log = ( $empty_log ? "\nHook: $hook" : "\n\nHook: $hook\n" )
. $files . $globals . $constants . $classes . $functions;
file_put_contents( $this->log_path, $log, FILE_APPEND );
}
/**
* Format logged data to log string.
*
* @param array $diff
* @param string $name
* @param string $before_item
* @param string $after_item
* @return string
*/
protected function diff_string(
array $diff,
$name,
$before_item = '',
$after_item = ''
)
{
$num = count( $diff );
if ( 0 === $num )
return '';
$list = join( "$after_item\n - $before_item", $diff );
return "\n$name: $num\n\n - $before_item$list$after_item\n";
}
/**
* Attempt to recreate the URL currently called.
*
* @return string
*/
protected function get_current_url()
{
$url = 'http';
is_ssl() && $url .= 's';
$url .= '://' . $_SERVER['HTTP_HOST'];
if ( ! empty ( $_SERVER['SERVER_PORT'] )
&& 80 !== (int) $_SERVER['SERVER_PORT']
)
{
$url .= $_SERVER['SERVER_PORT'];
}
// $_SERVER['REQUEST_URI'] is set in wp-includes/load.php
// before any plugin is activated.
$url .= $_SERVER['REQUEST_URI'];
return $url;
}
/**
* Create the directory and fill $this->log_path.
*
* @return void
*/
protected function set_log_file_path()
{
$this->log_path = $this->get_dir_name() . $this->get_log_file_name();
}
/**
* File name for the current log.
*
* @return string
*/
protected function get_log_file_name()
{
$base = $_SERVER['HTTP_HOST'] . '-' . $_SERVER['REQUEST_URI'];
return sanitize_title_with_dashes( $base ) . '.log';
}
/**
* Try to create the directory. Return it on success.
*
* @return string
*/
protected function get_dir_name()
{
$upload = wp_upload_dir();
empty ( $upload['error'] ) || die ( $upload['error'] );
$dir = $upload['basedir'] . '/t5-track-load-logs';
wp_mkdir_p( $dir ) || die ( "Could not create $dir." );
return "$dir/";
}
/**
* New files loaded.
*
* @return string
*/
protected function track_files()
{
$diff = $this->register_diff( get_included_files(), 'files' );
return $this->diff_string( (array) $diff, 'Files' );
}
/**
* New global variables
*
* @return string
*/
protected function track_globals()
{
$glob = array_keys( $GLOBALS );
$diff = $this->register_diff( $glob, 'globals' );
return $this->diff_string( (array) $diff, 'Globals', '$' );
}
/**
* New defined constants
*
* @return string
*/
protected function track_constants()
{
$constants = get_defined_constants( TRUE );
$names = array_keys( $constants['user'] );
$diff = $this->register_diff( $names, 'constants' );
return $this->diff_string( (array) $diff, 'Constants' );
}
/**
* Track new classes.
*
* Only classes and subclasses, no subsubclasses.
* That is a limitation of PHP.
*
* @return string
*/
protected function track_classes()
{
$classes = get_declared_classes();
$diff = $this->register_diff( $classes, 'classes' );
return $this->diff_string( (array) $diff, 'Classes' );
}
/**
* New defined functions.
*
* @return string
*/
protected function track_functions()
{
$functions = get_defined_functions();
$diff = $this->register_diff( $functions['user'], 'functions' );
return $this->diff_string( (array) $diff, 'Functions', '', '()' );
}
/**
* Sort new values, compare with already logged values and update log.
*
* @param array $new
* @param string $key
* @return array
*/
protected function register_diff( $new, $key )
{
sort( $new, SORT_NATURAL | SORT_FLAG_CASE );
$diff = array_diff( $new, $this->logged[ $key ] );
$this->logged[ $key ] = $new;
return $diff;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment