LPD-11235 CKEditor 5 Fragment RichText editable field

Hi,
I’m currently using DXP 2025.Q3.0 and have enabled the Enhanced Rich Text Editor feature: LPD-11235.

I’d like to add the sourceEditing button (CKEditor documentation)
to the CKEditor 5 balloon toolbar used inside fragment rich text editable fields.

To customize the editor configuration, I’m using a Client Extension (CX) based on the example provided in Liferay’s sample workspace:
Sample Editor Config Contributor

I modified the sample index.ts file to:

  • Keep only the CKEditor 5 configuration

  • Add the 'sourceEditing' button to the toolbar

I also removed the editorConfigKeys property in the client-extension.yaml file to apply the configuration changes to all editors.

I have attached the client extension.

Observations:

The new toolbar configuration works as expected in Web Content fields – the “Source” button is visible.
However, it is not displayed in the “Description” field, where the button is missing:

The “Source” button is also missing in the CKEditor 5 balloon editor when editing a rich text editable field inside a Fragment:

ckeditor5_RichTextFragment.png

It seems that the SourceEditing plugin is not loaded for the CKEditor 5 balloon editor, while it is correctly loaded for the Web Content editor.

Questions:

  • How can I display the “Source” button in the CKEditor 5 balloon editor?

  • If the issue is due to the plugin not being loaded, how can I include it via the Client Extension?

Hi jconrad - thanks for bringing this to us. As you know, this feature is currently in Beta, so it may just be that we haven't implemented support for this yet - but I will let the product team know.

7 Answers

7

Hi @jconrad

I am going through your comments:

The new toolbar configuration works as expected in Web Content fields – the “Source” button is visible. :ok_button:

However, it is not displayed in the “Description” field, where the button is missing:

This is because we have different presets, and “Content” field is using Advanced Preset, that includes “Source” plugin, and “Description” field is using basic preset, that doesn’t include it by default.

To overcome this, you could use the Sample Editor Config Contributor to add the “Source” plugin to the basic preset.

The “Source” button is also missing in the CKEditor 5 balloon editor when editing a rich text editable field inside a Fragment

This, for now, is a product limitation, we have not include the source plugin in the Ballon Editor version, as it has other implications. We are figuring out how to add it and solve this limitation.

Just a small correction here. You cannot modify a preset, but you can set a fully custom toobar, through toolbar config property. It just needs to have sourceEditing in the end.

Hi @MarkoCikos Is it possible to set a fully custom CKEditor 5 toolbar with the SourceEditing plugin for the Fragment Balloon Editor?

Hello,

I tested the CX Sample Editor Config Contributor on the version liferay-dxp-tomcat-2025.q3.4.

I kept only the code related to ckeditor5, without the plugins (‘bookmark’, ‘timestamp’, ‘fullscreen’, ‘helloworld’).

The toolbar configuration works correctly in a Web Content and in the balloon editor of a Fragment:

However, I can’t get the plugins present in the example to work: ‘bookmark’, ‘timestamp’, ‘fullscreen’, ‘helloworld’

As soon as I add the extraPlugins line at this point:

javascript

const updatedConfig = {
...config,
extraPlugins: [Fullscreen, HelloWorld],
toolbar,
};

the CX no longer works, and the default ckeditor5 configuration appears again (for both Web Content and the balloon editor) .

Did I miss something?

Thank you in advance for your feedback.

Could you share the .yaml file as you have it? Take into account that to affect the WebContent experience in CK Editor 5, you should:

  • Enable CK Editor Feature Flag: Beta FF–11235
  • Add “rich_text” to the list of affected CK Editor entries in the yaml

I confirm that I have activated the CK Editor Feature Flag: Beta FF–11235.

In the .yaml file, I initially removed the editorConfigKeys element so that all editors would be taken into account.
Following your comment, I added editorConfigKeys with the rich_text entry, but that didn’t solve the problem I’m encountering.
I did not find how to attach these two versions of the file here.

Unfortunately, I’m still facing the same issue: I can’t get the example plugins to work.
If I remove 'bookmark', 'timestamp', 'fullscreen', and 'helloworld', and also delete the line extraPlugins: [Fullscreen, HelloWorld],
the new toolbar configured in the Client Extension works correctly — but without any plugins.

Another question:
With Alloy Editor, in a rich-text editable field of a fragment, can I add the SourceEditing plugin?
If so, how?

Thanks in advance for your help.

This is an issue from the core side. Currently, it seems that it cannot load all CKEditor 5 plugins. I had to modify the following files to make it work:

  • modules/apps/frontend-editor/frontend-editor-ckeditor-web/src/main/resources/META-INF/resources/js/ckeditor5/utils/getDefaultEditorConfig.ts

  • modules/apps/frontend-editor/frontend-editor-ckeditor-web/node-scripts.config.js

  • modules/_node-scripts/util/getExportedSymbols.js

I found that the Source Code Editing plugin is only available for the Classic Editor type:

Therefore, I’ll need to use the Enhanced Source Editing feature instead:

Is it possible to use this functionality through an Editor Config Contributor Client Extension?

Also, how can I enable the CKEditor 5 Premium features?

Hi @Jconrad, I am struggling with the same problem, did you find how to add Source Code Editing plugin for fragment's rich-text ballon editor or it is a product limitation as mentioned in above comment by Gerardo. Thanks !

Hi @Ravi_kumar_Ravi , Below is the code that works on my side (2026.Q1) :

src/index.ts

import { SourceEditingEnhanced } from 'ckeditor5-premium-features';
import { EditorConfigTransformer, EditorTransformer } from '@liferay/js-api/editor';

const editorConfigTransformer: EditorConfigTransformer<any> = (config) => {

    // CKEditor 5
    if (config?.editorType === 'ckeditor5') {

        const toolbar = config.toolbar || {items: []};

        const items = [...(toolbar.items || [])];

        if (!items.includes('SourceEditingEnhanced')) {
            items.push('SourceEditingEnhanced');
        }

        const htmlSupport = {
            ...(config.htmlSupport || {}),
            allow: [
                {
                    name: /.*/,
                    attributes: true,
                    classes: true,
                    styles: true
                }
            ]
        };

        const updatedConfig = {
            ...config,
            extraPlugins: [SourceEditingEnhanced],
            htmlSupport,
            toolbar: {
                ...toolbar,
                items,
            },
        };

        return updatedConfig;
    }

    return config;
};

const editorTransformer: EditorTransformer<any> = {
    editorConfigTransformer,
};

export default editorTransformer;

client-extension.yaml :

assemble:
- from: build
into: static
acme-editor-config-contributor:
editorConfigKeys:
- fragmentEntryLinkRichTextEditor
name: ACME Editor Config Contributor
type: editorConfigContributor
url: index.js

src/types.d.ts :

declare module '@ckeditor/ckeditor5-core/dist/index.js' { export * from '@ckeditor/ckeditor5-core'; } declare module '@ckeditor/ckeditor5-fullscreen/dist/index.js' { export * from '@ckeditor/ckeditor5-fullscreen'; } declare module '@ckeditor/ckeditor5-ui/dist/index.js' { export * from '@ckeditor/ckeditor5-ui'; }

tsconfig.json :

{ "compilerOptions": { "esModuleInterop": true, "jsx": "react", "lib": [ "DOM", "ES2020" ], "module": "ES2020", "moduleResolution": "node", "outDir": "./build", "resolveJsonModule": true, "sourceMap": false, "target": "ES2020", "types": [ ] }, "include": [ "./src/**/*" ] }

Please let me know if it works on your side.

Jérémy