AEM: Custom metadata forms for Assets

How to create your own metadata form and apply custom field validation

Theo Pendle
7 min readNov 10, 2019

This post article was inspired by user davidm28404065’s question on the AEM Experience League forums, which is the basis for the use case described below.

The use case

Business users want to make use of AEM Asset’s metadata system and have the following requirements:

  1. All assets under the your site directory (I will use the wknd directory from the AEM WKND Tutorial) should have mandatory Title and Description fields.
  2. The Title field should contain only alphabetic characters and start with a capital letter.

Now let’s dive in and make all their dreams come true!

Understanding metadata schema forms

You won’t have to open CRXDE for this part as AEM has made a metadata schema editor available through the Touch UI (documented here).

A metadata schema defines which metadata can be associated with an asset and is associated to a form design.

Note: I am creating this article on an AEM 6.5.1 instance. The steps below are applicable if you are on AEM 6.3 or 6.4 but the Touch UI will be slightly different.

Go to Tools > Assets > Metadata Schemas to find the list of OOTB schemas. Among them you should find a schema called default:

OOTB metadata schemas

The default metadata schema applies to all assets for which another schema is not specified. Click on the checkbox and then on Edit in the top toolbar to view the schema form:

Metadata schema form editor

If you are familiar with AEM Assets you will recognize this as the form that is accessed by visiting an asset’s Properties page. On the left you have the viewer and on the right a number of form components.

Do not change anything in the default schema as we will want to preserve the original OOTB behavior. Exit the editor and return to the list of schemas.

Click on default (not the checkbox, but the actual name) and you will see that schemas are organised on a hierarchical manner. The default schema is the parent of a number of other schemas, such as image which itself has two children tiff and jpeg. Although it does not seem to be mentioned in the documentation, the child schemas inherit form elements from their parents. We will prove this now (if you prefer to get straight to the action, you can skip to the section below).

Open the editor for the default > image schema and the default > image > jpeg schema and compare the two. The first thing you might notice is the lock icon on certain sections of the form:

Locked section of the form

This section is locked because it is inherited from default.

If you look at the bottom of the jpeg schema form you will see a Location field which is not present on the image schema form.

Now open the Properties page of a JPEG and a PNG asset and compare those. You will see that the PNG (which is an image, but not a jpeg) does not contain the Location field whereas the JPEG does.

This principle of inheritance can also be confirmed by looking at the JCR (sorry I know I said no CRXDE… yet) by looking at the node structure of the schemas:

From this we can see that the image schema inherits the default schema and adds width and height fields. The jpeg schema then inherits image and adds a location field.

Creating a custom metadata form

Return to Tools > Assets > Metadata Schemas and click the checkbox by default. Select Copy from the top toolbar and name your schema [your-site-name]-default (wknd-default in my case). Open the editor for the schema you just created.

Click on the Title field and you will see a number of options in the Settings and Rules tabs on the right (on AEM 6.3 these two tabs are merged into one single Settings tab). One option in particular is relevant to our use case: the Required option in the Rules tab.

Select Required to make the Title field mandatory and do the same for Description. Click on Save.

As described above, the inheritance principle means that all schemas under wknd-default will now have mandatory Title and Description fields.

If you were to rush over to an asset Properties page now you would not see any change. That is because metadata schemas need to be associated with folders in the DAM. To do this, select your schema and click on Apply to Folder(s) in the top toolbar:

Applying a schema to a DAM folder

Select your site directory from the path selector and click on Apply.

Now if we navigate to our site directory in the DAM we will see that any assets that do not have the required metadata have been flagged with a red banner:

Assets flagged as missing a required metadata

If we open a Properties page for one of these assets, we will see that the two mandatory fields are now highlighted:

Highlighted required fields

Attempting to click on Save & Close will generate an error modal informing us that we are missing mandatory fields.

Clicking on the warning icon above each fields reveals the reason for the validation error.

However, it is still possible to give our asset a nonsense name using special characters:

Asset name containing special characters

We’ll tackle this next.

Applying validation to form fields

Now it’s time to crack your fingers, push your glasses up and open CRXDE.

AEM provides a form validation API in Granite UI Foundation, which is documented here. We will use this API to create custom validation for our Title field. If you scroll down to the Validator section of the documentation you will find an example of how to register a validator using the Foundation registry.

Our validation code will be as follows:

As you can see, we will use a selector to target only the Title field, but in order to make sure this custom validation is triggered only for wknd-default or one of its children, we need to check the data-path attribute of the field wrapper. Let’s load this script into the Properties page!

Create a clientlib with the following structure in your project folder:

\-- metadata-validation (cq:ClientLibraryFolder)
\-- js.txt (nt:file)
\-- js (nt:folder)
\-- metadataValidation.js (nt:file)

In the js.txt file, reference the metadataValidation.js script:

#base=jsmetadataValidation.js

Add the following property to the metadata-validation node:

categories  -  String[]  -  dam.gui.coral.metadataeditor

This will tell AEM to add our script to the dam.gui.coral.metadataeditor category which gets loaded with the Properties page.

Let’s check this works by adding console.log('metadataValidation.js loaded') to the metadataValidation.js script.

Go to an asset Properties page under your site directory, refresh and you should see the log appear in the console.

Now paste the code from the snippet above into metadataValidation.js and refresh the Properties page once again. Our custom form validation will now apply to the Title field:

Custom validation warning

If you open the Properties page for an asset outside your site directory, the custom validation will not apply!

Improving the error dialog

There is, however, one problem left. If we click on Save & Close, we will get an error message, but with unhelpful content:

The message we provided in our validator is not being returned to the Coral UI Dialog which, regardless of the nature of the error, will always present the same message. The culprit is the JS script at /libs/dam/gui/coral/components/admin/metadataeditor/clientlibs/metadataeditor/js/form.js which has hard-coded text to return in case of a validation error. Unfortunately there is no easy way to send all validation error text to the dialog so it can display a list of issues. We would have to re-write large parts of the script, which is outside the scope of this article.

What we can do however, is modify the message slightly to make it less specific.

Note: For reasons described in another article I published, it is preferable to avoid overlaying files in the JCR if possible. Every file you overlay needs to be patched with each version update/upgrade, so keep that in mind if you decide to continue.

To change this text, we will need to overlay

/libs/dam/gui/coral/components/admin/metadataeditor/clientlibs/metadataeditor/js/form.js 

to:

/apps/dam/gui/coral/components/admin/metadataeditor/clientlibs/metadataeditor/js/form.js

We then need to make a change to the saveMetadataChanges() function (at line 119 in AEM 6.5.1). Replace the text >

"One or more required field(s) is/are empty." 

with:

"One or more required field(s) is/are invalid."

Reload the Properties page and try to Save & Close a form with validation warning and you should see the following dialog:

I hope this article has taught you something about metadata schemas and Granite UI Foundation validation 🙂 If you have any questions, please don’t hesitate to ask in the comments or to find me on LinkedIn!

--

--

Theo Pendle

Software engineer hoping to learn and inspire by sharing my experiences 🙂 Reach out to me on LinkedIn: https://www.linkedin.com/in/theo-pendle-1630a52a