Amazon.co.uk Widgets

Log in

X
Creating a Joomla plugin and component with a little help from AI

Joomla is a powerful content management system but much of that power comes from the ability to add extensions without breaking the system. Extensions are opaque though and there is a lot to get to grips with to create them. There are many dependencies and knowledge points that you need to have to succeed. You might wisely choose to use a component creator to do this heavy lifting for you but I wondered what help there might be from AI. The answer is quite a bit and that I now have two working extensions - a plugin and a a component - but it wasn't exactly a straight out of the box experience. This article explores how to build a Joomla component using AI that dynamically generates meta descriptions from article content, thus enhancing SEO without manual input. You can learn more about Joomla development at the Joomla developer website.

Anyway, to the topic. I decided my meta descriptions were poor. I'm not sure how much they are relevant anymore in SEO so I didn't want to spend a lot of time curating them, but I want them to be useful. So I need to generate them automatically when an article is created and optionally need to regenerate them all if I change the logic for generation. We'll cover key aspects, including model creation, controller handling, and the UI for a "Regenerate All" button. By the end, you'll have a functional extension that automatically fills the metadesc field in Joomla articles.

TL:DR – The following guide walks through building Joomla extensions, a (component and a plugin) that automatically generate SEO-friendly meta descriptions. You'll create the necessary MVC files, ensure proper database updates, and add a button for bulk regeneration. The process automates a manual task in Joomla's content creation and should improve article visibility in search engines.

Getting your environment Setup - what you'll need to create and test a Joomla component

To create a Joomla content plugin and a component that automatically generate meta descriptions from the title and content of an article, you'll need the following:

  • Joomla installed (latest production version)
  • Access to Joomla’s filesystem and database
  • Basic understanding of Joomla and its extensions system

Generating the Plugin

I used AI to help generate the source code for the plugin.

AI prompt – Explain how to make a Plugin 
Explain what you need in order to make a content plugin for joomla to automatically generate meta descriptions from the title and content for an article.

Plugin structure

A Joomla content plugin resides in plugins/content/yourpluginname and typically includes:

  • yourpluginname.php (main plugin file)
  • yourpluginname.xml (plugin descriptor)

Plugin Event Hook

You should use Joomla’s onContentBeforeSave event to intercept and modify the article’s metadata before it's saved.

Generating the Meta Description

I want to generate a nice meta description, which can be safely up to 160 characters but vaguely google say it can sometimes be up to 300 characters. Sticking with 160 for now!

So the plugin needs to:

  • Extract text from $article->title and $article->introtext
  • Process content (strip tags, remove excessive whitespace, trim to ~150-160 characters)
    Assign generated description to $article->metadesc

And because it uses the event hook it is part of the save process. Nice. 

The AI generated some code, but it didn't work out of the box. It was very nearly right but also quite wrong about a few fundamentals. It tried to store the metadata as JSON encoded attributes. This didn't work. Telling the AI helped.

AI prompt – fixing the generated example
The description is just a string in the metadesc field.

So the Plugin directly modifies $article->metadesc, ensures that an existing meta description isn't overwritten if manually set, Cleans up the content by removing HTML tags and extra whitespace and Limits the generated meta description to 160 characters, the standard SEO length.

It saved me a massive amount of time though as all I neede to do was clean it up and heres the code I ended up with. The AI didn't add a licence or copyright, to its snippets so I added copyright since these are my edits to boilerplate code to create a finished working plugin, and I added the GNU/GPLv3 http://www.gnu.org/licenses/gpl-3.0.html which is Joomla's preferred licence for extensions. 

Plugin code (autometa.php)

autometa.php
<?php
/*
 * @package Plugin Autometa for Joomla! 
 * @version 1.1.0 autometa.php
 * @author Angus Fox
 * @copyright (C) 2025 - Multizone Limited
 * @license GNU/GPLv3 http://www.gnu.org/licenses/gpl-3.0.html
*/
defined('_JEXEC') or die;

use Joomla\CMS\Plugin\CMSPlugin;
use Joomla\CMS\Factory;

class PlgContentAutoMeta extends CMSPlugin
{
    public function onContentBeforeSave($context, $article, $isNew)
    {
        // Ensure it's a Joomla article
        if ($context !== 'com_content.article') {
            return true;
        }

        // Skip if a meta description already exists
        if (!empty($article->metadesc)) {
            return true;
        }

        // Generate a meta description using the title and introtext
        $article->metadesc = $this->generateMetaDescription($article->title, $article->introtext);

        return true;
    }

    private function generateMetaDescription($title, $introtext)
    {
        $summary = $this->extractText($introtext);
        $metaDesc = trim($title);

        if (!empty($summary)) {
            $metaDesc .= ' - ' . $summary;
        }

        return mb_substr($metaDesc, 0, 160); // Trim to 160 characters
    }

    private function extractText($text)
    {
        // Remove HTML tags, decode special characters, and clean up spaces
        $cleanText = trim(strip_tags(html_entity_decode($text, ENT_QUOTES | ENT_HTML5, 'UTF-8')));

        return $cleanText;
    }
}

Plugin Manifest  (autometa.xml)

This defines the plugin metadata and installation parameters.

autometa.xml
<?xml version="1.0" encoding="utf-8"?>
<extension type="plugin" version="5.0" group="content" method="upgrade">
    <name>PLG_CONTENT_AUTOMETA</name>
    <version>1.1.0</version>
    <creationDate>19 February 2025</creationDate>
	<author>Angus Fox</author>
	<copyright>(C) 2025 Multizone Limited. All rights reserved.</copyright>
	<authorEmail>This email address is being protected from spambots. You need JavaScript enabled to view it.</authorEmail>
	<authorUrl>https://www.multizone.co.uk</authorUrl>
	<license>GNU/GPLv3 http://www.gnu.org/licenses/gpl-3.0.html</license>
	<description>PLG_CONTENT_AUTOMETA_XML_DESCRIPTION</description>
    <files>
        <filename plugin="autometa">autometa.php</filename>
        <folder>language</folder>
    </files>
</extension>

Installation and activation

  • Zip the yourpluginname.php and yourpluginname.xml into a package
  • Add the licence as a text file from the GPL website.
  • Install via Joomla Extensions Manager
  • Enable the plugin in Joomla's Plugin Manager

This will ensure every new article gets a meta description if one isn’t provided manually.

Testing the plugin

The AI even listed the example scenarios, which I've rewritten to take account of my changes to the original logic.

  • Case 1, Article with introtext
  • Case 2, Article without introtext
  • Case 3 No text at all
Case 1 Article with introtext
<p class="lead">AI is changing the world.</p>
<p>New developments in machine learning...</p>

Generated Meta Description

Article Title - AI is changing the world.

Example outputs

The AI gave me some helpful output examples too.

Example article Data
TitleIntrotextGenerated Meta Description
"Exciting Tech News" "AI is transforming the industry..." "Exciting Tech News - AI is transforming the industry..."
"Future of Space" "<p>NASA plans new Mars missions...</p>" "Future of Space - NASA plans new Mars missions..."

Generating the component

To update meta descriptions for all articles as a maintenance task as opposed to individually, we need to:

  • Create a Joomla administrator component with a button in the backend.
  • When clicked, it will regenerate all articles meta descriptions.

Again AI can be used to help generate the source code for the component.

AI Prompt – making a component to do the task on all articles rather than one at a time
What if I want it to run on all my articles, as a maintence task from a button, as well as on save?

Setting up the component structure

Joomla components require a structured directory layout. this isn't the most advanced MVC layout for Joomla but it works.

It provides a separation of concerns. The Meta description logic is in a helper, making it reusable.
It provides good readability. The model focuses on database operations.
It provides easier maintenance it is easy to edit the logic without disturbing the rest.

The extension folder layout looks like this:

Folder structure
    /com_autometa/
    │── autometa.php         # Main entry file
    │── controller.php       # Handles actions
    │── manifest.xml       # an XML file detailing information about the component
    │── models/              # Model logic
    │   ├── autometa.php     # Processes meta descriptions
    │── views/
    │   ├── autometa/
    │   │   ├── view.html.php
    │   │   ├── tmpl/
    │   │   │   ├── default.php (UI for regenerating metadata)

Creating the model

The model processes each article and regenerates metadata. It fetches articles, extracts a summary, and updates the database.

models/autometa.php
<?php
defined('_JEXEC') or die;

use Joomla\CMS\MVC\Model\BaseDatabaseModel;
use Joomla\CMS\Factory;

class AutometaModelAutometa extends BaseDatabaseModel
{
    public function regenerateAllMetaDescriptions()
    {
        $db = Factory::getDbo();

        // Select all articles
        $query = $db->getQuery(true)
            ->select(['id', 'title', 'introtext'])
            ->from('#__content');
        $db->setQuery($query);
        $articles = $db->loadObjectList();

        // Loop through each article and update meta description
        foreach ($articles as $article) {
            $metaDesc = $this->generateMetaDescription($article->title, $article->introtext);

            // Update query
            $updateQuery = $db->getQuery(true)
                ->update('#__content')
                ->set($db->quoteName('metadesc') . ' = ' . $db->quote($metaDesc))
                ->where($db->quoteName('id') . ' = ' . (int) $article->id);
            $db->setQuery($updateQuery);
            $db->execute();
        }
    }

    // Generate a meta description from title + introtext
    private function generateMetaDescription($title, $introtext)
    {
        // Remove HTML tags and trim
        $cleanIntro = strip_tags($introtext);
        $cleanIntro = trim($cleanIntro);

        // Limit intro text to 150 characters
        $summary = mb_substr($cleanIntro, 0, 150);

        return $title . ' - ' . $summary;
    }
}

Adding the controller logic

The controller handles user interactions, such as clicking the "Regenerate All" button. It ensures the model executes properly.

controller.php
<?php
defined('_JEXEC') or die;

use Joomla\CMS\MVC\Controller\BaseController;
use Joomla\CMS\Factory;

class AutometaController extends BaseController
{
    public function regenerateAll()
    {
        $model = $this->getModel('Autometa', 'AutometaModel', ['ignore_request' => true]);

        if ($model) {
            $model->regenerateAllMetaDescriptions();
            Factory::getApplication()->enqueueMessage('All meta descriptions regenerated.', 'message');
        } else {
            Factory::getApplication()->enqueueMessage('Error: Could not load model.', 'error');
        }

        $this->setRedirect('index.php?option=com_autometa');
    }
}

Building the user interface

The UI provides a button to regenerate meta descriptions. This form submits a request to trigger the controller action.

views/autometa/tmpl/default.php
<?php
defined('_JEXEC') or die;
use Joomla\CMS\Router\Route;
?>

<form action="<?php echo Route::_('index.php?option=com_autometa&task=regenerateAll'); ?>" method="post">
    <button type="submit" class="btn btn-primary">Regenerate All Meta Descriptions</button>
</form>
views/autometa/view.html.php
<?php
defined('_JEXEC') or die;

use Joomla\CMS\MVC\View\HtmlView;

class AutometaViewAutometa extends HtmlView
{
    public function display($tpl = null)
    {
        parent::display($tpl);
    }
}

Creating a manifest and installing and testing the component

The final step is ensuring the Joomla manifest correctly installs all files. The manifest.xml must reference all essential components. Pay careful attention here, as the AI essed up the hierarchy of the XML so it needed to be manually reordered in line with Joomla standards.

manifest.xml
<?xml version="1.0" encoding="utf-8"?>
<extension type="component" version="5.0" method="upgrade">
    <name>com_autometa</name>
    <version>1.0.0</version>
    <creationDate>2025-02-20</creationDate>
    <author>Angus Fox</author>
    <description>Automatically generates meta descriptions for Joomla articles.</description>
    <administration>
        <menu link="index.php?option=com_autometa">AutoMeta</menu>
        <files folder="admin">
            <filename>autometa.php</filename>
            <filename>controller.php</filename>
            <folder>models</folder>
            <folder>views</folder>  
        </files>
    </administration>
</extension>

Conclusion

This process provided a structured way for me to develop a working Joomla plugin and corresponding maintenance component that dynamically generates meta descriptions. By implementing a proper MVC pattern, leveraging Joomla's database API, and integrating a user-friendly interface, it can help streamline the content management workflow and enhance SEO. AI is like having a coach helping. It doesn't really know all these answers but can find them if you ask it the right questions. I wouldn't have been able to achieve this on my own in anywhere near the time it took - less than a day - I guess in the future it is the prompt writers who will inherit the Earth.