Custom Fields may be useful in many Joomla extensions. They can be added by calling a custom script file upon an extension install or uninstall. The script will use Joomla’s database driver to manually insert new custom field records.
I created this code to go along with my guide on loading custom article fields within layout files, however, it could apply to any type of extension.
Setup
Begin by navigating to your extension’s XML manifest file and defining a scriptfile element if one does not exist already. We usually use “script.php” as the filename.
In my “joomStarter” template, the top of the manifest file looks like this now:
<extension type="template" client="site" method="upgrade">
<name>joomstarter</name>
<version>1.30</version>
<creationDate>June 2023</creationDate>
<author>Your Name</author>
<authorEmail>Your Email</authorEmail>
<copyright>(C) 2023 KG</copyright>
<description>TPL_J4STARTER_XML_DESCRIPTION</description>
<inheritable>1</inheritable>
<scriptfile>script.php</scriptfile>
-- continued --
Code language: HTML, XML (xml)
Then create your script.php file if one does not exist. It must contain a class named “yourextensionInstallerScript” – this is required or it won’t load on install/update/uninstall.
The InstallerScript class can use 3 functions on install, uninstall, and update. Other functions are available but I’m not covering them here.
<?php
defined ( '_JEXEC' ) or die;
class myextensionInstallerScript
{
public function install($parent)
{
echo '<p>Extension installed/p>';
}
public function uninstall($parent)
{
echo '<p>Extension uninstalled</p>';
}
public function update($parent)
{
echo '<p>Extension Updated</p>';
}
}
Code language: HTML, XML (xml)
Copy/paste the above code and remember to change the class name to reflect whatever the extension’s name is.
Load/Remove Custom Fields
Now we just need to add some script to define and insert the custom fields we need into the database. I would suggest manually creating the field yourself within Joomla’s admin panel, and then copying the field information directly from phpMyAdmin or whatever database explorer you use. Some of the fields are formatted with JSON so this will make it easier to ensure everything is correct.
In this example, I create a pretty generic text field for the articles fields. If you are using fields outside articles, such as a custom user field, you’ll need to change the context field accordingly.
You should provide a value for every property of the field listed below even if you don’t think it’s important for your use case – there are no default values for some of the required columns in the database table structure.
<?php
defined ( '_JEXEC' ) or die;
use Joomla\CMS\Factory;
//if using a template, you must prefix this with the template's name as defined in templateDetails.xml
//if running from a component, you must prefix this with the component's name as defined in the component's manifest file, usually com_componentname
//same applies to any other type of extension... myextensionInstallerScript, etc
class joomstarterInstallerScript
{
public function install($parent)
{
//get id of current user
$userid = Factory::getApplication()->getIdentity()->id;
// Create a new custom field
$field = new stdClass();
$field->context = 'com_content.article'; //change this to the context needed
$field->group_id = 0; //change this to the group id if needed. if you want to create a custom group you'll have to do that first and look up the new group id
$field->title = 'Your Field Title';
$field->name = 'your_field_name';
$field->label = 'Your Field Label';
$field->description = 'Fields Description Here';
$field->type = 'text';
$field->default_value = '';
$field->state = 1;
$field->required = 0;
$field->params=''; //in json format
$field->fieldparams=''; // in json format
//you'll probably be okay leaving the rest of the params alone
$field->access = 1;
$field->created_user_id = $userid;
$field->created_time = date('Y-m-d H:i:s');
$field->modified_user_id = $userid;
$field->modified_time = date('Y-m-d H:i:s');
$field->language = '*';
// Insert the new field in the database
$db = Factory::getContainer()->get('DatabaseDriver');
$db->insertObject('#__fields', $field, 'id');
echo '<p>Custom field created</p>';
}
public function uninstall($parent)
{
//remove custom field from database
$db = Factory::getContainer()->get('DatabaseDriver');
$query = $db->getQuery(true)
->delete($db->quoteName('#__fields'))
->where($db->quoteName('name') . ' = ' . $db->quote('your_field_name'));
$db->setQuery($query);
$db->execute();
echo '<p>Custom field removed</p>';
}
public function update($parent)
{
//You would need to do a version check here to see if the you need to create a custom field or not, or check if the custom field exists and change accordingly
}
}
Code language: PHP (php)
Now that the field’s been created, I can see it under the article fields, and the option is available for each article.
You can learn how I access the values of my custom fields from within articles by reading the snippet on that.