WordPress Plugin Tutorial: How to Create a WordPress Plugin

WordPress Plugin Tutorial: How to Create a WordPress Plugin

In this WordPress plugin tutorial, you’ll learn how to create a complete WordPress plugin with its own admin page. The most important reason to create a plugin is that it allows you to separate your own code from the WordPress core code. If something goes wrong with your plugin, the rest of the site will generally continue to function.

Altering the core WP code can be catastrophic. With the more advanced plugin features provided by WordPress, you are even able to create plugins that change the way core functions work without actually altering their code.

What You’ll Need

To complete the steps in this WordPress plugin tutorial, you’ll need a text editor such as Notepad++ or NetBeans. You’ll also need FTP access to your hosting account and a working WordPress installation.

You can learn how to connect Notepad++ to your FTP server by reading the how to connect to FTP with Notepad++ tutorial. You can also use FTP software like FileZilla to upload your files, and the how to configure FileZilla client tutorial will teach you how.

This WordPress plugin tutorial is intended for people who already have basic knowledge of PHP. You will write a new function, call existing WordPress functions using parameters, and write PHP comments.

It’s also strongly recommended to create a backup of your website before proceeding further.

What Are WordPress Plugins?

A WordPress plugin is a standalone set of code that enhances and extends the functionality of WordPress. By using any combination of PHP, HTML, CSS, JavaScript/jQuery, or any other web programming language, a plugin can add new features to any part of your website, including the Admin Control Panel. You can modify the default behavior of WordPress, or remove unwanted behavior completely. Plugins allow you to easily customize and personalize WordPress to fit your needs.

Because WordPress plugins are standalone, they do not physically alter any of the WordPress core code. They can be copied and installed on any WordPress installation. An alternate (and strongly discouraged) way of making changes to WordPress is to write new functions in the WordPress functions.php file, which is stored in the /wp-includes/ folder, or the functions.php file that is part of a theme. This comes with a number of potential problems.

WordPress and its themes receive regular updates. And unless you are using WordPress child theme, when functions.php is overwritten by an update, your new code will be deleted and you’ll have to write it all over again. If you write a lot of functions and one of them has an error that you are unable to debug, you may have to replace the entire file with the original one, deleting all changes you have made. If your functions are removed from the file, your website may be covered in PHP errors where it tries to call the missing functions.

Plugins are never automatically overwritten or deleted when installing WordPress updates. If your plugin has coding errors, you can usually just deactivate it in the Admin Control Panel while you fix it. If your plugin has a serious error, WordPress will sometimes automatically deactivate it for you, allowing your site to continue functioning.

What are Hooks?

WordPress Plugins interact with core code using hooks. There are two different types of hooks.

  1. Action hooks (To add/remove functions)
  2. Filter hooks (To modify data that is produced by functions)

Actions and Action Hooks

When you visit any page of a WordPress website, a series of PHP functions (named actions) are called at various points, and they are attached to action hooks. Using the action hooks provided by WordPress, you can add your own functions to the list of actions that run when any action hook is called, and you can also remove pre-existing functions from any action hook. Action hooks dictate when the actions are called. Before the closing </head> tag of any page, the wp_head() action hook is called, and the actions that are hooked to wp_head() are run.

Action hooks are contextual – some are called on every page of your website, others are only called when viewing the Admin Control Panel, and so on. A full list of actions hooks and the context in which they are called can be found on the WordPress Plugin API/Action Reference page.

Adding Functions To An Action Hook Using add_action()

To add a function to any action hook, your plugin must call the WordPress function named add_action(), with at least two parameters.

  • The first required parameter is the name of the action hook that you want to attach to
  • The second required parameter is the name of the function that you want to run
  • The third parameter (optional) is the priority of the function you want to run. You can hook any number of different functions to the same action hook, and order them any way you like. The default priority is 10, putting your custom function after any of WordPress’ built-in functions. A function with a priority of 11 runs next, and so on.
  • The fourth parameter (optional) is the number of arguments, which means how many parameters your custom function is able to take. The default is 1.

Example plugin code to display text after the footer of every page

This plugin hooks the wp_footer() action hook, which is called right before the closing </body> tag of every page, and adds a new function named mfp_Add_Text(). Since this is part of a plugin and not a theme, it will continue to work if you activate an entirely different theme. You can save this example as a PHP file, upload it to the wp-content/plugins/ folder and activate it in the Admin Control Panel to see the change.

Final result:

WordPress Plugin Tutorial - Creating Simple Plugin

NOTE: you can call add_action() before defining your own function because PHP evaluates the entire script before executing it. Writing add_action() calls at the top of the file in the order that they are executed, then defining your functions in the same order below, makes the file easier to read.

Removing Functions From an Action Hook Using remove_action()

To remove an action from an action hook, you must write a new function that calls remove_action(), then call the function you have written using add_action(). The example below will make this clearer.

You must give remove_action() at least two pieces of information as parameters.

  • The first required parameter is the name of the action hook the function is hooked to
  • The second required parameter is the name of the function that you want to remove
  • The third parameter (optional) is the priority of the original function. This parameter must be identical to the priority that was originally defined when adding the action to the action hook. If you didn’t define a priority in your custom function, don’t include the parameter.

Example: imagine you don’t want the text added to the footer in the previous example to appear on a Monday. One way of doing this is by using the PHP date function to get the current day, followed by an if…then… conditional statement to test whether the current day is Monday, then calling remove_action() if it is a Monday. You call the function using add_action(), hooking any action hook that occurs before the action hook you want to affect. If you try to hook an action hook that occurs after wp_footer in this example, the action will not be removed from the hook as it has already run.

Filters and Filter Hooks

A filter function allows you to modify the resulting data that is returned by existing functions and must be hooked to one of the filter hooks. The available filter hooks are different to the action hooks. They behave similarly to action hooks in that they are called at various points in the script and are contextual. A full list of filter hooks and the context in which they are called can be found on the WordPress Plugin API/Filter Reference page.

Adding Filters Using add_filter()

To add a filter function to any filter hook, your plugin must call the WordPress function named add_filter(), with at least two parameters.

  • The first required parameter is the name of the filter hook that you want to hook
  • The second required parameter is the name of the filter function that you want to run
  • The third parameter (optional) is the priority of the function you want to run. You can attach any number of different filter functions to a filter hook. The default priority is 10, putting your custom function after any built-in functions. A function with a priority of 11 runs next, and so on.
  • The fourth parameter (optional) is the number of arguments, which means how many parameters your custom filter function is able to take. The default is 1.

Example plugin to alter the excerpt of a post

WordPress has a function that retrieves the excerpt of a post named get_the_excerpt(), which is also a filter hook. The function to actually display the excerpt calls get_the_excerpt() to retrieve it, that’s where the filter is applied and the excerpt is altered before being displayed. This plugin defines a filter function that takes the excerpt as its only input parameter, adds some text before it, and returns the new value every time the get_the_excerpt() is called. As the return value of the get_the_excerpt() function is the actual excerpt text, it is automatically entered as the functions parameter $old_Excerpt when called using  add_filter(). The function you define must return the new value.

Final result:
Created WordPress Plugin in Action
Removing Filters Using remove_filter()

Removing a filter is much simpler than removing an action because you can call the remove_filter() function without defining a new function. For this example, we’ll once again add a very simple conditional situation and remove the text if the current day is a Thursday.

Now that you have a basic understanding of hooks and filters, let’s create a simple WordPress plugin that adds a new link and page to the Admin Control Panel.

Step 1 – Storing Your Plugin

The first step to creating your WordPress plugin is making a folder to store all your files. Plugins are saved in the following folder: /wp-content/plugins/. The folder you create needs a unique and descriptive name to ensure it doesn’t clash with any other plugin. Connect to your hosting account with an FTP client. From the main WordPress directory, navigate to wp-content, then to plugins. Inside the plugins folder, create a new folder named my-first-plugin.WordPress Plugin Tutorial - Creating WordPress Plugin Folder with FTPTo make things significantly easier for yourself in the future, it is best to separate the various files that make up your WordPress plugin and give them their own subfolders, rather than having all your plugin’s files in the main folder. When a plugin grows and becomes complex, it’s a lot easier to find a specific file when everything has its own place. If your plugin uses some custom CSS, you create a CSS folder and save all CSS files in there. If your plugin uses custom JavaScript, you create a JavaScript folder.

Step 2 – Creating the First File

The first file in your plugin is an important one. It contains all the information WordPress needs to display your plugin in the plugin list, which allows you to actually activate the plugin.

In your my-first-plugin folder, create a new PHP file named my-first-plugin.php. It’s good practice to give this first file a similar name to the one you gave your folder, but it can have any name you like. Add the opening PHP tag <?php to the first line. You don’t need to add a closing tag to the end of the file (to understand why, read the note on this page of the PHP manual). This file will primarily hold ‘header comments’ with various pieces of information that will be read/displayed by WordPress. Header comments go in a multi-line PHP comment, one per line and each line starts with a specific piece of text to define what the line refers to. These should only go in this first file and do not need to be in any other file.

The first comment you must add to my-first-plugin.php is the name of your plugin. Start by writing the PHP multi-line comment opener /* on the second line of the file, right below the opening PHP tag. On the third line, write Plugin Name: My First Plugin. On the fourth line, close the comment section with */. Your file will now look like this:

Save the file and upload it to the my-first-plugin folder. Navigate to the Plugins page of the WordPress Admin Control Panel. You’ll now see a plugin in the list named My First Plugin with links to Activate, Edit and Delete the plugin. There are a few different pieces of information you can add at this point, such as a description of the plugin, your own name, a link to your website, the current version of your plugin etc. For now, we will only add a description and your name.

Edit my-first-plugin.php so it looks like the example below, upload it, and overwrite the old file when asked:

Once it’s uploaded, refresh the WordPress admin area Plugins page and you should now see your plugin with its new description and By Your Name.WordPress Plugin We Just Created in Admin Area

Step 3 – Writing Your Plugin’s Functions

As mentioned earlier, the best practice when developing a plugin is to neatly separate your code into appropriate files and folders. Since the primary job of the first file is to hold the comment headers, it makes sense to place the rest of the plugin’s code in separate files in their own subfolder, using PHP’s ‘include’ functions to access them. Any files stored in subfolders are called directly by our code and only by our code, so subfolder names don’t need a prefix. However, it is highly recommended that you give all your files, functions, and variables a unique prefix in their name to avoid any conflicts with other plugins. In this case, we are using mfp as a prefix, which is short for ‘My First Plugin’.

In your plugin’s main folder, create a new folder named includes. Any file that is ‘included’ by another file will go in this folder. Create a new PHP file in the includes folder and save it as mfp-functions.php. Give it the opening <?php tag on the first line. This new file is where all your plugin’s functions will be stored.

Now go back to my-first-plugin.php in your plugin’s main folder. We need to make it include the mfp-functions.php file so we can actually use the new functions. Since this is the main plugin file, including mfp-functions.php here makes the functions available to any other file in your plugin. Use require_once to ensure the plugin only works if the functions file is available. The easiest way to include files from your plugin folder is by using the WordPress function plugin_dir_path(__FILE__), which gives the full path to the directory where our plugin is stored, then use a . (period) to append the name of the subfolder we created earlier (includes), followed by the name of the file we created (mfp-functions.php).

Edit my-first-plugin.php as shown below then save and upload it once again, overwriting the previous version when asked.

Return to mfp-functions.php in the includes subfolder.

It’s a great idea to group similar functions together and write a multi-line comment above each group describing the group, followed by a short single-line comment above each function briefly describing it. That way you don’t have to read through the entire code to find a function and figure out what it does. We’ll name the function mfp_Add_My_Admin_Link(). The function will add a new top-level link to the Admin Control Panel’s navigation menu.

To recap – writing a new function involves the following steps:

  • Write a comment describing the function
  • Name the function
  • Write the function

In mfp-functions.php, write the following:

Inside our function, we need to use the built-in WordPress function add_menu_page() to give our menu a name, a title and dictate who is allowed to see it. Then we tell it what to display when you go to the page. You can also give the menu link an icon and set its position in the admin control panel navigation menu – these are both optional, so we will leave them out for this tutorial. The default cog icon will be shown on the link to our page. Our link will appear at the bottom of the admin control panel navigation menu. All this information is entered as parameters of  add_menu_page().

The four required parameters of add_menu_page() all appear on their own line to improve readability, in this order:

  1. The title of the page you see after clicking the link (displayed in the tab in your browser)
  2. Text to show as the menu link (displayed in the admin control panel navigation list), this should be the name of your plugin
  3. User capability requirement to view the menu, in this example only users with the ‘manage_options’ capability can access the page (don’t worry about this for now)
  4. The file to use when displaying the actual page (we’ll create this next), which will be stored in the includes subfolder and named mfp-first-acp-page.php. The URL entered here is known as a ‘slug’.

Before continuing, it’s important to note that there is an alternate way to use this function. The fourth parameter can simply be a string of text that is displayed in the url after ‘wp-admin/admin.php?page=’. If you enter ‘my-plugin-page’, the URL becomes ‘wp-admin/admin.php?page=my-plugin-page’. The fifth parameter must then be the name of a function that outputs something. You could write a function that just echoes ‘Welcome to page 1’ for instance. It is significantly easier to create a PHP file to hold your page.

Edit mfp-functions.php, remove // My code goes here, replace it with add_menu_page() and give it parameters as shown below:

To make this function actually run, we need to use the WordPress function named add_action() with two parameters, as described in the ‘Adding Functions To An Action Hook’ section of this tutorial. You may want to read over that section again before continuing.

  • The first parameter is the action hook you want to target. In our case the action hook is admin_menu – this means our function is run when the Admin Menu is being generated.
  • The second parameter is just the name of the function to run. The function we wrote is named mfp_Add_My_Admin_Link. Note that the parentheses are NOT used here. Remember that PHP evaluates the entire script before running it, allowing you to use add_action() before defining the function named in parameter 2.

Our final file looks like this:

Upload mfp-functions.php to the includes folder and overwrite the old one.

Step 4 – Creating The New Admin Page

Now we can create the page to be displayed when you click on your admin control panel link. Go back to the includes subfolder and create a new PHP file named mfp-first-acp-page.php. PHP opening tags aren’t required in this file as we are only using HTML. Write the HTML below, and upload the file.

When creating admin pages, WordPress recommends enclosing your own HTML with a div and giving it the “wrap” class, as shown above. This ensures that all your content appears in the correct place, just like any other admin page. If you don’t wrap it like this, the page can become very messy.

Go back to your plugin list in the WordPress Admin Control Panel and activate the plugin. Once the page loads, look at the bottom of the admin control panel navigation menu. There is the brand-new link named ‘My First Plugin’. Click it, and you have your very own admin control panel page!

WordPress Plugin Tutorial - Plugin Created


Congratulations, you have just created your first WordPress plugin, added a new link to the admin menu, and displayed a whole new page in the Admin Control Panel! It doesn’t do much just yet, but this is the first step after all. From here, you can build upon what you’ve learned and extend WordPress any way you like. For more tutorials, check out our WordPress tutorials section.

The Author


Liam Carberry / @liamcarb

Liam is a WordPress fanatic that loves to write about web development and coding. When he's not working, he likes to help people create websites and applications. In short, his job is also a hobby!


Hoargarth Reply

November 25 2017

Pretty nice and simple tutorial, helped me a lot to get fast into WP plugin creation. There's just one thing that didn't work for me: I did everything just like you did but my WordPress couln't find my admin page. For me the problem was in step 3 at the "add_menu_page()" function. The problem was the 4th parameter 'includes/mfp-first-acp-page.php', I changed it to 'my-first-plugin/includes/mfp-first-acp-page.php' and it worked like it should. I don't know if it's caused by a WP-Update or something else. And thanks again for your tutorial.



    Replied on August 22 2018

    Thanks for adding this comment. I had the same problem, easy fix!



    Replied on January 07 2019

    Thanks, I had the same issue and I was continuously checking where I had made the mistake, but after looking at your comment, I had to change the root directory to my-first-plugin/includes/mfp-first-acp-page.php. I think they should change the code because when I didn't get the output I was disappointed that I made some mistake. You are a life saver Thanks a lot.



    Replied on January 07 2019

    You are a life saver


Pegues Reply

December 21 2017

Nice tutorial. Like @Hoargarth mentioned, I had to add the name of the plugin in the 4th parameter value for add_menu_page in order for it to work. In your current example it was trying to display the page in the frontend. Great tutorial overall. Simple and to the point.


Alex Swarte Reply

September 12 2018

Great first start in building a plugin !!


Sunny Chawla Reply

March 11 2019

I have read the article and it was very helpful for me, thank you for this wonderful article. Also, I would like to add that my favorite plugin "Woocommerce", it's my favorite because here there are various types of customization like we can add discount coupons, select color attributes, we can add a variable product etc. It's a very useful plugin for new developers who are targeting E-commerce development.


RajJes Reply

February 20 2020

We are getting the 404 error. After click on created menu.



    Replied on March 12 2020

    Hi RajJes, Try these 404 error fixes to get rid of the error :)


Steve Reply

April 21 2020

This is really good. Now that I have my plugin I would like to create a premium version. How about a tutorial on how to create a paid version that is different and updates automatically, keeping it separate from the free version. There doesn't seem to be any information about how to do this on the web. Thanks


    Andrius S.

    Replied on April 23 2020

    Hey, Steve, glad you liked the article, and thanks for the suggestion!


chernenko Reply

May 30 2020

Very good tutorials guard. Thank you very much

Leave a reply




This site uses Akismet to reduce spam. Learn how your comment data is processed.

Become a part of Hostinger now!

More in WordPress