New Bookstore! Save 20% on books with discount code: LAUNCH
Web Dev + WordPress + Security

WordPress Error Fix: “Call to undefined function get_header()”

[ Call to undefined function ] I’m seeing a big increase in bot attacks targeting theme files directly. First they get the URL to your theme directory. There are numerous ways for a bot to get this information. For example most themes include assets like CSS and JavaScript files, and the link includes the full URL. So then once they have the theme URL, bad bots will make direct requests for well-known theme template files, like index.php and header.php. Requesting template files directly may reveal possible security vulnerabilities, which apparently is an increasingly popular attack vector. It also triggers the “Call to undefined function get_header()” (and similar) errors. Fortunately there is an easy fix.

Is your site targeted?

To find out if your site is getting hit with direct requests for theme files, you can check your site’s access/error logs. Here are some examples from my own logs that should help show what to look for:

Note: In the following log entries, all file paths are changed to example URLs to prevent Google from crawling and reporting errors. In the actual log files, errors contain file paths, not URLs. P.S., it is most ridiculous that Googlebot crawls plain-text path information, inside of <pre> tags no less.
2018-12-30 17:54:07 Error
AH01071: Got error 'PHP message: PHP Fatal error: 
Uncaught Error: Call to undefined function get_header() in https://example.com/wp-content/themes/digwp/index.php:1
Stack trace: #0 {main} thrown in https://example.com/wp-content/themes/digwp/index.php on line 1'

2018-12-30 12:53:55 Error
AH01071: Got error 'PHP message: PHP Fatal error: 
Uncaught Error: Call to undefined function get_header() in https://example.com/wp-content/themes/digwp/404.php:1
Stack trace: #0 {main} thrown in https://example.com/wp-content/themes/digwp/404.php on line 1'

2018-12-30 12:53:55 Error
AH01071: Got error 'PHP message: PHP Fatal error: 
Uncaught Error: Call to undefined function esc_url() in https://example.com/wp-content/themes/digwp/header.php:8
Stack trace: #0 {main} thrown in https://example.com/wp-content/themes/digwp/header.php on line 8'

So if your site is targeted with direct-template attacks, you’ll see LOTS of these types of errors. In these examples, the requests are for index.php, 404.php, and header.php. From my analyses, most of the template requests are for these three files, but you may also find them scanning for other well-known WordPress files, such as:

/archive.php
/wp-includes/rss-functions.php 
..various theme template files
..various files in the WP Media Library

Basically, any direct request for a WordPress core, theme, or plugin file most likely will trigger an error, unless proper measures are taken beforehand. For example, later we’ll look at an easy way to stop the “undefined function” error, which in turn will help conserve precious server resources and improve overall site security.

Understanding the error

So what’s with the “call to undefined function” fatal errors? They happen because WordPress core is not loaded for directly loaded template files.

For example, if you request header.php directly, any core functions such as esc_url() are not available because the file is requested outside of WordPress.

What happens if you do nothing? Well, your theme may already have implemented a similar technique, or maybe not. What’s the risk? Depending on how your theme is coded, it may be possible for bad actors to execute code out of context, which may expose potential attack vectors.

How to fix

The easiest way to prevent this type of error is to simply exit the script if WordPress is not available. This is an ancient yet effective PHP technique used to prevent direct file access:

<?php if (!defined('ABSPATH')) exit; ?>

It simply says: If the ABSPATH constant is not defined, then exit the script. This works because ABSPATH is only defined when WordPress is loaded. So when a bad bot comes along and starts requesting your theme templates, it will simply get a blank page (empty response) from the server.

You may have seen similar code during your WordPress travels. Preventing direct script access is an important part of PHP security. You don’t want attackers/bots running scripts out of context, when not authorized, and so forth.

Example

To implement this technique, open any theme files that are targeted, and include the line at the top of the file. For example, many theme templates include the header before any other code, looks like this:

<?php get_header(); ?>

After adding the “no direct access” snippet, you’ll have something like:

<?php 
	if (!defined('ABSPATH')) exit;
	get_header(); 
?>

However you decide to format the code is fine, the point is to include the ABSPATH line before any other functions are called.

Pro Tip: Want to stop more bad bots? Check out my free WordPress plugin, Blackhole for Bad Bots, available at the WP Plugin Directory.

Bonus

To go further, you can protect sensitive file information by disabling directory views. For example, if you visit your theme parent directory in a browser, what do you see? If directory views are enabled, you’ll get a linked list of all the files. Not good. What you should see is either a blank white screen or some other server response. You know, to help keep your file information safe and secure.

There are numerous ways to disable directory views. The WordPress way is to create a new (empty) index.php file in whichever directory you want to protect.

Important! Only create a new index.php file if one does NOT already exist in the directory. That is, don’t overwrite any existing index files.

Then in index.php, add the following code:

<?php 
// Silence is golden.

WordPress core uses this technique in various directories. By disabling open directory views, we prevent attackers from obtaining information about which files exist on the server. So it benefits security and is recommended practice for all public directories, unless you’ve got it covered with .htaccess, or maybe have reason to do otherwise and leave views enabled for a specific directory.

Closing thoughts

The simple techniques described in this article are proven security measures that will prevent unsafe code execution and stop errors from filling up your logs. That means better performance and security for your site. Even if you’re not experiencing the type of errors described in this article, protecting your theme and plugin files from direct access is good for security.

Jeff Starr
About the Author
Jeff Starr = Creative thinker. Passionate about free and open Web.
Blackhole Pro: Trap bad bots in a virtual black hole.
Welcome
Perishable Press is operated by Jeff Starr, a professional web developer and book author with two decades of experience. Here you will find posts about web development, WordPress, security, and more »
The Tao of WordPress: Master the art of WordPress.
Thoughts
Take a screenshot with Firefox (no extension required). Open Developer Tools Settings and enable the “Take a screenshot” button. Then click the button :)
Take a screenshot with Chrome (no extension required). Open DevTools, type Cmd + Shift + P, then type screenshot.
After 10 years working on my 2010 iMac, my upgrade finally arrived. Shiny new iMac shipped from Ireland :)
Too much caffeine weirds me out. But I love the taste of coffee. So once in a while I enjoy a small cup of decaf. Hits the spot.
Chris Coyier is a truly awesome person. One of the finest people I've ever worked with. Just #gottasayit
Excel won't open CSV file because SYLK format? Open it with text editor and add an apostrophe ' at the beginning of the file, save changes, done.
Displaying too many social media buttons and links all over the place imho makes you look desperate and frankly kinda sad.
Newsletter
Get news, updates, deals & tips via email.
Email kept private. Easy unsubscribe anytime.