Posts tagged ‘PHP’

When I go to WordCamps, I get this question a lot: “Why do you have the PHP Code Widget still in the directory?”

There’s a good answer for that, but first let me explain why I made the thing in the first place.

If you examine the history of that plugin, you’ll find that it was submitted almost 10 years ago. Back then, widgets were new. Most people using WordPress had hardcoded sidebars in their themes. Changing the sidebar meant changing the theme. Widgets aimed to replace that with draggable objects. The Widget plugin was still a plugin, and not in core, but headed there.

The PHP Code Widget was created to make it easy and simple and fast to migrate from a hardcoded sidebar to a widget based one. You could take your existing code in the sidebar file, paste it into the widget, and then you had a movable widget that you could easily use.

Obviously, this was not meant for long term usage. The goal was to get widget support rapidly in your theme, with the expectation that as new widgets came out, you could replace your old code with newer, shinier, well supported, widgets.

The reason the plugin is still in the directory is because it still fills a need for some people. If I removed it, then they would fulfill that need in worse ways. It does not take much searching to find snippets of code, with bad advice saying to just pop it into your theme’s functions.php file, and voila, now all your Text Widgets run PHP code. That snippet actually exists. It’s a terrible idea, for obvious reasons.

The PHP Code Widget is less terrible than the alternatives.

But it’s still terrible.

And yes, it bothers me that it is one of the top 150 plugins. Storing PHP code in your database and then running it is just dumb. Don’t do that. Code should live in the right place, and that place is not the database.

So, in an effort to reduce the usage of the PHP Code Widget, here’s one way to stop using it, if you still are.

Getting rid of the PHP Code Widget

Step 1:

Get the PHP Code that you are using from the Widget, copy it into a text editor, save it somewhere for safe keeping.

Step 2:

You’re going to make a new plugin. You can call it whatever you like, but I recommend naming it specific to the site you’re making it for. If I was making a plugin for this site to hold widgets, then I’d call it “Ottopress Widgets” or something to that effect.

How to make a new plugin:

(Note: You can use Pluginception for this instead, if you like. That one I’m not ashamed of, it’s a very handy tool.)

a. Make a directory in /wp-content/plugins named after your plugin, like /wp-content/plugins/ottopress-widgets

b. Make a PHP file in there named the same. Like ottopress-widgets.php.

c. Edit that file, and add this header to the top of it:

<?php
/* Plugin Name: Ottopress Widgets*/

Lovely. We’ve made a new plugin. It doesn’t do anything, yet, but here’s some more code to add to the plugin. This is largely copy-paste, and then you edit it to fit your specific circumstances

Step 3:

add_action( 'widgets_init', 'ottopress_widget_register' );
function ottopress_widget_register() {
	register_widget( 'Ottopress_Widget' );
}
class Ottopress_Widget extends WP_Widget {
	function __construct() {

		$class = 'widget_ottopress';
		$name = 'Ottopress Widget';

		$widget_ops = array('classname' => $class, 'description' => $name);
		$control_ops = array('width' => 400, 'height' => 350);
		parent::__construct('', $name, $widget_ops, $control_ops);
	}

	function widget( $args, $instance ) {
		extract($args);
		echo $before_widget;

		echo '<h2 class="widget-title">Ottopress Widget</h2>';
		echo "<div>Here's my custom stuff.</div>";

		echo $after_widget;
	}
}

I named this widget “Ottopress Widget” by way of example. In the first few lines of code, you’ll want to change these to your own naming scheme. It’s important that names be unique, which is why I recommend naming things using your site’s name. Unlikely for there to be interference that way.

The $class and $name variables you should also change. The class is used in the HTML that the widget produces, so you can refer to it via CSS. The name is simply used for display purposes on the widgets editing screens.

Step 4:

Finally, the meat of the code you want to edit is here. I’ll point it out specifically.

function widget( $args, $instance ) {
	extract($args);
	echo $before_widget;

	echo '<h2 class="widget-title">Ottopress Widget</h2>';
	echo "<div>Here's my custom stuff.</div>";

	echo $after_widget;
}

This is the code that shows the widget on your site itself. Now, this one is just hardcoded to show the normal before and after code (these are set by the theme, so these should always be there), and then it has a little hardcoded bit there where it echo’s out a title and a div that says “Here’s my Custom Stuff”.

If you’re migrating from the PHP code widget, well, here’s where you migrate it to. You can drop your code from the PHP Code widget here and, you know, do whatever you were doing in the widget before, just now in an actual custom widget, in your own custom plugin. No more storing the code in the database. Just activate the plugin and replace the PHP Code widget with this one.

If you need more widgets because you were using it in multiple places, then simply repeat the process. Paste that whole class in there, only give it a different class name and other info, then put in your other code. You can have as many widgets as you like, they just have to all be named differently. Simple.

Note that this widget has no settings screen of any kind. Why would it? You’re controlling the code directly, no need for settings, presumably. If you want to go on and make your widget smarter and more complex and have settings, well, there’s other tutorials for that.

If this reduces the usage of the PHP Code Widget, well, I’ll be a happier person.

Shortlink:

Been a while since I wrote something. Let’s talk about some of the new stuff available in the Customizer.

Forget about some of part two

First, back in part two, I had a bit about Surfacing the Customizer. That bit is outdated now, WordPress does this for you in later versions. So, yeah, skip that.

Shiny new thing: Panels

Okay, so Panels aren’t that new. They were added in WordPress 4.0. Basically, they’re sliding containers for sections. Having trouble fitting all your settings on the screen? Group the various sections up into Panels. Panels show up as an item in the main list, and when you click the arrow next to them, the whole list glides off screen to show only those sections.

So, now we have four things: Panels, Sections, Controls, and Settings.

  • Panels group Sections together
  • Sections contain Controls
  • Controls are what the user changes
  • Settings define what the Controls change

Creating a panel is easy:

$wp_customize->add_panel( 'some_panel', array(
   'title' => 'Panel 1',
   'description' => 'This is a description of this panel',
   'priority' => 10,
) );

Adding a section to that panel is just as easy:

$wp_customize->add_section( 'themedemo_panel_settings', array(
 'title' => 'More Stuff',
 'priority' => 10,
 'panel' => 'some_panel',
) );

All that’s new is a panel setting to tell the section to go into that panel. Simple.

Active Callbacks

One of the problems with the Customizer was that it displayed settings and showed them changing on the site to your right, but the site being displayed is the actual site. Meaning that you can navigate on it. Sometimes, the controls being shown don’t necessarily apply to the actual site that you’re seeing.

Example: If you have a control to change the color of something in the sidebar, but then are looking at a page which has no sidebar, then you have no visual feedback to tell you what the change looks like.

To fix this, “active callbacks” are used.

The active_callback is simply a new parameter that you can pass into Panels, Sections, or Controls. It can contain the name of a function, and that function will be called when the page changes. The function should return true or false (or equivalent) to indicate whether or not the element of the customizer should be shown for that page.

So, if you have a whole Panel that only make sense when the user is looking at Front Page of the site (and not an individual post), then you can do this:

$wp_customize->add_panel( 'front_page_panel', array(
   'title' => 'Front Page Stuff',
   'description' => 'Stuff that you can change about the Front Page',
   'priority' => 10,
   'active_callback' => 'is_front_page',
) );

And voila, when the user is not looking at the front page, the panel simply disappears.

You can use any of the normal WordPress Template Tags for this, or write your own function if you want to be more specific about it.

Edit: As pointed out in the comments, this will not work with ALL of the Template Tags. In particular, is_single won’t work because of the optional parameter it can take. You can define a wrapper for these methods instead, to get the same effect. Example:

function callback_single() { return is_single(); }
...
   'active_callback'=>'callback_single'
...

Fun with Active Callbacks

If you do need to write your own callback function, note that the function receives the object in question when it’s called. So, if you attach an active_callback to a Panel, your function will get a argument of the WP_Customize_Panel object in question passed to it. Sections get WP_Customize_Section and such. You can use the information in these to decide whether the panel (or whatever) should be shown for that page.

So, how do we use that object? Well, you can use this to make whether certain controls show or not dependent on the values of other settings. All the various items you can use this on have a link back to the main WP_Customize_Manager. That class has a get_setting function, which you can use to determine what to do.

So, let’s make a control that causes other controls to appear, dependent on a setting.

First, let’s make a simple radio selection control:

$wp_customize->add_setting( 'demo_radio_control', array(
   'default'        => 'a',
) );

$wp_customize->add_control( 'demo_radio_control', array(
   'label'      => 'radio_control',
   'section'    => 'themedemo_panel_settings',
   'settings'   => 'demo_radio_control',
   'type'       => 'radio',
   'choices'    => array(
   'a' => 'Choice A',
   'b' => 'Choice B',
   ),
) );

Now, we need to make two other controls, one for each choice. You can actually make as many as you like, we’ll keep it simple.

First, the control for choice A. Let’s make it a simple text control.

$wp_customize->add_setting( 'choice_a_text', array(
   'default' => '',
) );

$wp_customize->add_control( 'choice_a_text', array(
   'label'      => 'Choice A: ',
   'section'    => 'themedemo_panel_settings',
   'type'       => 'text',
   'active_callback' => 'choice_a_callback',
) );

We’ll need that callback function to detect if choice A is selected in the radio control, and return true if it is, and false otherwise. Like so:

function choice_a_callback( $control ) {
   if ( $control->manager->get_setting('demo_radio_control')->value() == 'a' ) {
      return true;
   } else {
      return false;
   }
}

You can simplify that if you like, I spelled it out with an if statement so as to be clear as to what is happening.

panel1

Now for choice B, let’s make it display a color control instead:

$wp_customize->add_setting( 'choice_b_color', array(
   'default' => '#123456',
) );

$wp_customize->add_control( new WP_Customize_Color_Control( $wp_customize, 'choice_b_color', array(
   'label'   => 'Choice B',
   'section' => 'themedemo_panel_settings',
   'settings'   => 'choice_b_color',
   'active_callback' => 'choice_b_callback',
) ) );

And its callback:

function choice_b_callback( $control ) {
   if ( $control->manager->get_setting('demo_radio_control')->value() == 'b' ) {
      return true;
   } else {
      return false;
   }
}
panel1-b

Now, note that the callbacks are very similar. Seems like repeated code, doesn’t it? Well, it is, but remember that the $control here is the whole WP_Customize_Control object. We can use the same callback and simply check which control is calling it here instead.

function choice_callback( $control ) {
   $radio_setting = $control->manager->get_setting('demo_radio_control')->value();
   $control_id = $control->id;

   if ( $control_id == 'choice_a_text'  && $radio_setting == 'a' ) return true;
   if ( $control_id == 'choice_b_color' && $radio_setting == 'b' ) return true;

   return false;
}

So, instead of using two different callbacks, we just point our controls to this callback, which figures out what should show up for which setting. I’m sure you can simplify this further, depending on your particular needs.

One more thing: Customizing the Customizer

Not everybody likes the style of the Customizer. Maybe it clashes with your theme. Maybe you just want to tweak it a bit. Maybe you dislike that gray background color, and a more soothing blue would go better for your theme.

add_action( 'customize_controls_enqueue_scripts', 'themedemo_customizer_style');
function themedemo_customizer_style() {
   wp_add_inline_style( 'customize-controls', '.wp-full-overlay-sidebar { background: #abcdef }');
}

Or maybe you don’t think the Customizer area is wide enough… be careful with this one though, consider mobile users as well.

add_action( 'customize_controls_enqueue_scripts', 'themedemo_customizer_style');
function themedemo_customizer_style() {
   wp_add_inline_style( 'customize-controls', '.wp-full-overlay-sidebar { width: 400px } .wp-full-overlay.expanded { margin-left: 400px } ');
}

You can enqueue whole extra CSS files instead, if you like. Or, if you have special needs for javascript in some of your controls, and there’s libraries necessary to implement them, then you can enqueue those libraries here as well.

Shortlink:


So in my last post about Internationalization, I covered some non-obvious things that you should consider when adding translation capabilities to your code.

Today, let’s add to that by covering some non-obvious translation functions. You’re probably not using these, since they don’t get talked about as much. But there’s probably places where you should be using them, so knowing about them is the first step. And knowing is half the battle.

Basic functions, again

Last time I talked about these functions:

  • __()
  • _e()
  • _x()
  • _ex()
  • _n()

Let’s cover the ones I didn’t talk about.

Escaping output

In practice, you tend to use these mostly when outputting things onto the main page or in the admin. But, one thing you also use a lot when outputting text is the standard escaping functions. These are things like esc_html(), which outputs text in a way that makes it “safe” to go onto a webpage, without being interpreted as HTML. If the text comes from user input, then this is a good idea.

Now, if you think about it, then the text you have may be translated in some other file, which you don’t control either. So escaping that text might be a good idea too. If somebody snuck bad code into a translation file, a user might get bad things displayed without being able to easily find it.

So you could write something like echo esc_html(__('text','text-domain')), but that’s a bit wordy. Let’s talk about some shortcuts.

The esc_html__() function is the equivalent of esc_html(__(...)). It does the escaped html and the double-underscore translation all in one go. Similarly, the esc_html_e() function does the same thing, but it echoes the result, just like the _e() function would. And there’s also esc_html_x(), which is the equivalent of combining esc_html() and _x().

Along with those three are the three identical equivalents for attributes: esc_attr__(), esc_attr_e(), and esc_attr_x(). As the name implies, these combine the translation functions with esc_attr(), which is the escape function specifically intended when you’re outputting text into html attributes.

Also note there’s no shortcut for the equivalent of _ex(). It’s just not used that much, or at least not enough to need something special for it. Use an echo esc_html_x() instead.

There are no shortcuts for the other escaping functions as yet, but these can save a few keystrokes and make your code that much more readable.

The Numerical No-op

So we’ve got some shortcuts for escaping with those three functions, but where’s the love for _n()?

One of the problems with _n() is that it tends to require the strings to be in the same place that the PHP variable is. For all the other functions, you could have a big file of strings in an array, and then reference those strings by name or something elsewhere because they don’t require any PHP variables. Nothing about them is computed at the time of the output.

But not so with _n(), that $number to decide which string to use means that the strings have to be right there, they can’t be translated separately and referenced.

This is where _n_noop() comes in. The _n_noop() function basically takes the singular and plural strings for something, along with the text domain, and stores them in an array so that they can be referenced later by a function named translate_nooped_plural().

Perhaps an example is in order. Let’s go back to the tacos:

$string = sprintf( _n('You have %d taco.', 'You have %d tacos.', $number, 'plugin-domain'), $number );

What if we wanted those strings somewhere else? Like in a big file with all of our strings. Here’s a way to separate the strings from the _n() call:

$taco_plural = _n_noop('You have %d taco.', 'You have %d tacos.', 'plugin-domain');
$string = sprintf( translate_nooped_plural( $taco_plural, $number) , $number );

Now, that $taco_plural can be defined anywhere. Note that it contains no references to PHP variables. It’s basically static and unchanging. This allows us to separate it, then reference it elsewhere for the actual translation. The translate_nooped_plural() function performs the same job as _n() does, choosing which string to use based on the $number of tacos. The sprintf then pushes the $number into the chosen string, replacing the %d with the number.

Thus, that lets us extract the translatable strings out and put them anywhere we choose.

Also of note: The _nx_noop() function is a cross between _n_noop() and _x(). It takes a context for the translators as the third argument, and the domain becomes the fourth argument. Useful if you need to explain to the translators the context surrounding the pluralization choice.

Numbers and Dates

The number_format_i18n() function is functionally equivalent to the PHP number_format function. It lets you format numbers with commas at the thousands mark and so forth, except that it also takes localization into account. Not everybody uses commas for thousands and periods for decimals. This function will do the translation appropriately for that aspect.

The date_i18n() function is functionally equivalent to the PHP date function. It will handle all the same string formatting parameters as date() will, but it will cause output to be translated for month names, day-of-week names, and so forth. Of note is that it doesn’t change the format requested. If some places put days before months, for example, it won’t handle that. But it will output the month name in the native language (if the translation pack has the right month name in it). So you may want to run the date formatting string through __() as well, to let translators adjust the date format accordingly.

Wrap up

And that’s pretty much all the rest of the translation functions that I didn’t cover before. I may have forgotten a few useful ones here or there. Feel free to comment about anything I missed, or what you see most often, especially if you’re doing translations yourself.

Shortlink:

My post about how to customize WordPress images with tricks like greyscale and such got me lots of feedback, so I figured I might as well turn it into a plugin.

The ImageFX plugin allows you to customize the image sizes from WordPress or custom ones for your theme, by applying filters to them.

The way it works is basically identical to my original post on the topic, only it allows the filters to be defined on a per-image-size level. It also allows the addition of a “slug” to be appended to the image filename, which is useful for cases where you want to have two images at the same size, but with different filters.

Since it was easy to do, I went ahead and created several other simple image filters that you can use for your images:

  • Greyscale (black and white)
  • Sepia tone (old-timey!)
  • Colorize with red, yellow, green, blue, or purple
  • Photonegative
  • Emboss
  • Brighten
  • Greyscale except red, green, or blue (classy!)

Here’s some examples. This a pic of me, Nacin, Rose, and Matt at WordCamp San Francisco. I ran it through the sepia, blue colorize, and grey-except-red filters.



These are some of the default filters included, but since I could, I went ahead and made it easily expandable too. All you have to do to define a filter is to create a function to do the image filtering you want, then call the imagefx_register_filter() function to add it.

To implement your own custom filter, you can do it like this:

imagefx_register_filter('custom-name','my_custom_filter');
function my_custom_filter(&$image) {
 // modify the $image here as you see fit
}

Note that the $image is passed by reference, so you don’t have to return it. This is because the $image resource takes up a lot of memory, so to save on memory usage, you are manipulating it in place, sort of thing.

You can use any of the image functions in PHP to change the image however you like. The filters I’ve implemented are mostly pretty simple. You can see them all in the filters.php file, in the plugin.

Caveats: The plugin will only filter JPG images, to avoid the overhead of recompressing PNGs and to avoid breaking animated GIF files. Also note that I haven’t tested these filters extensively. They’re only a starting point, sort of thing. I spent all of about 20 minutes writing them, so don’t expect miracles. 🙂

You can download version 0.1 of the plugin from the WordPress plugin directory: http://wordpress.org/extend/plugins/imagefx/

Enjoy!

Shortlink:

First, WordPress plugin authors: Please don’t do this.

if ( isset($_GET['resource']) && !empty($_GET['resource']) ) {
	$resources = array(
		'icon1.png' => '... base 64 encoded code ...',
		'icon2.png' => '... base 64 encoded code ...',
		);

	if ( array_key_exists($_GET['resource'], $resources) ) {
		$content = base64_decode($resources[ $_GET['resource'] ]);
                header('Content-Length: '.strlen($content));
                header('Content-Type: image/png');
            	echo $content;
		exit;
	}
}

I’ve seen a few different versions of this, and while the idea is nice, this is really the wrong way to go about it.

The idea is to include small icons or images in the plugin file itself, instead of as separate files. This sort of code then lets you reference them by calling a URL of ?resource=icon1.png or whatever. When that resource variable is detected, the plugin kicks in and serves up the image instead of the site.

Advantages to this sort of thing:

  • No need for extra icon files

Disadvantages to this sort of thing:

  • Now every http request to get an icon file on your admin page results in loading up the WordPress code, causing extra CPU usage.

Here’s a better way. It’s called the Data URI.

<img src="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAAUAAAAFCAYAAACNbyblAAAAHElEQVQI12P4//8/w38GIAXDIBKE0DHxgljNBAAO9TXL0Y4OHwAAAABJRU5ErkJggg==" alt="Red dot" />

Here’s that code in action, right here: Red dot

Why this is better:

  • Same benefits as before, no need for extra icon files
  • No extra CPU load from loading WordPress to get that icon file
  • No extra HTTP requests at all, in fact, since the data for the tiny icon is contained right there in the code

Disadvantage:

  • Doesn’t work in IE7. You can work around this by detecting IE7 and serving up the image separately, if you really want. Or you can just ignore it like most people do. Seriously. IE7 is insecure (link, link) and nobody should be using it, anywhere. WordPress itself will probably drop IE7 support in the admin in the next couple of versions.

So use Data URIs for small images (under 32KB in size). They’re fast and easy. They’re an idea whose time has come.

Shortlink:

While looking at my backlinks today, I noticed a site in French had linked to my post about making photo galleries. He mentioned that the Google Translate wasn’t great. I took a look, and while I don’t know how good the text translation was, I did notice that Google strangely tried to translate the code as well, thus screwing it all up.

A quick search revealed that all one had to do was to add the “notranslate” class to any wrapping object to prevent its contents from being translated.

Now, I use the Syntax Highligher Evolved plugin to display code on my site (although I use an older version because I like the look and functionality of it better than the latest version). So I edited the plugin and found where it inserts the PRE tag, and added the notranslate class to it. And voila, now my code doesn’t get translated anymore.

Just a helpful tip for anybody who posts code on their sites.

Shortlink:

Saw this post about Chrome voice searching in HTML forms on Google’s blog today. Very cool, so I had to give it a try. If you check the “Search” box in the upper right corner of the page, you’ll see a little icon (if you’re using a dev version of Chrome). Click it to do a search-by-voice.

What I didn’t expect was how totally easy it is to implement. Seriously, it’s less than a line of code.

Example. Say your search box (possibly in your theme’s searchform.php file) looks like this:

<form id="searchform" action="<?php bloginfo('home'); ?>/" method="get">
<input id="s" name="s" size="20" type="text" value="<?php _e('Search') ?>..." />
</form>

All you have to do is to add some bits to the input element box. Specifically, you add x-webkit-speech speech onwebkitspeechchange=”this.form.submit();”. That’s it. Seriously:

<form id="searchform" action="<?php bloginfo('home'); ?>/" method="get">
<input id="s" name="s" size="20" type="text" value="<?php _e('Search') ?>..." x-webkit-speech speech onwebkitspeechchange="this.form.submit();" />
</form>

Note that this won’t validate, if you care about that sort of thing. Works fine though.

You can do a whole lot more with Javascript and events and translations and multiple choices and such, if you’re thinking of developing something cool with it. I’m just shocked and amazed that this is already in my browser and I had no idea it was there. Very cool.

Shortlink:

A while back, I wrote a post detailing why it was a bad idea to generate Javascripts using PHP in WordPress plugins. In that post, I mentioned a couple of better ways to do it.

At the time, I didn’t know about the third, and best way, to accomplish this. Mike’s comment over there reminded me of it. WordPress has it built in.

If you already know about wp_localize_script, you can stop reading now.

The wp_localize_script function was made in order to allow for WordPress translations to be able to also translate some of the JS files inside WordPress. Thus the name “localize”. The way it works is to load up the translated versions of text from the translation files and then include them into the resulting HTML output as a Javascript object. The scripts then use that object to produce any text output they need to produce.

Turns out that’s really similar to our goal of sending arbitrary parameters from WordPress to be used by Javascript code.

How to do it:

1. Make your script static (instead of generated) and enqueue your script as per normal. Example:

wp_enqueue_script('my-script','/path/to/whatever.js',…);

No real changes there. You’ll have to come back and modify your script to use these parameters it’s getting passed, but we’ll get to that in a minute.

2. Build an array of your parameters that you want to send to the script.

$params = array(
  'foo' => 'bar',
  'setting' => 123,
);

Note that my parameters are simple examples, but this is PHP code. You can get your parameters however you like. Such as get_option to pull them from the database, perhaps.

3. Call wp_localize_script and give your parameters a unique name.

wp_localize_script( 'my-script', 'MyScriptParams', $params );

What this will do is make WordPress output an inline script with your parameters (properly encoded) just before the enqueue outputs the script tag that loads your script in the first place. So then those parameters will be available to your script as an instance of an object with “MyScriptParams” (from my example).

This means that Javascript code can now reference them as attributes of the name you gave.

So, step 4. Modify your script to use those parameters. In my example, I used “MyScriptParams” and the parameter names are “foo” and “setting”. In my Javascript code I can use them as “MyScriptParams.foo” and “MyScriptParams.setting”.

Much cleaner. One static and unchanging JS file to cache. Parameters get put into your HTML itself as a one-liner. You can deal with the parameters using a normal PHP array before passing them over. No need to screw around with generating Javascript from PHP or looking for wp-load or even messing with tricky actions.

Perfect.

Shortlink:

Originally published here: http://ottodestruct.com/blog/2010/dont-include-wp-load-please/

Note: There is a followup post to this one, which details an even better way than the two given below: http://ottopress.com/2010/passing-parameters-from-php-to-javascripts-in-plugins/

Time for Otto’s general griping: WordPress plugin programming edition.

Here’s a practice I see in plugins far too often:

  1. Plugin.php file adds something like this to the wp_head:
    <script src='http://example.com/wp-content/plugins/my-plugin/script.js.php'>
  2. Script.js.php has code like the following:
    <?php
    include "../../../wp-load.php";
    ?>
    ... javascript code ...
    

The reason for this sort of thing is that there’s some option or code or something that the javascript needs from the database or from WordPress or whatever. This PHP file is, basically, generating the javascript on the fly.

Usually, the case for this turns out to be something minor. The code needs the value from an option, or some flag to turn it on or off. Or whatever.

Problem is that finding wp-load.php can be a bit of a chore. I’ve seen extreme efforts to find and load that file in plugins before, including searching for it, examining the directory structure to make decent guesses, etc. This sort of thing has existed even before wp-load.php came around, with people trying to load wp-config.php themselves and such.

But the real problem is simpler: This is always the wrong way to do it.
Continue reading ‘Don’t include wp-load, please.’ »

Shortlink: