Rich-Text v2 and Markdown Field Types (Preview) | Yext Hitchhikers Platform
With the Spring ‘23 Release, we introduced two new field types, both of which are intended for storing and authoring richly formatted text content in Knowledge Graph. These field types are:
- Rich-Text v2: A what-you-see-is-what-you-get (WYSIWYG) editor with a variety of formatting options
- Markdown: A markdown editor with a side-by-side rendered view, which also supports including HTML directly as markup
This reference will provide details about each field type, including details on supported formatting, storage format, ingesting & exporting content, and known limitations.
Both of these field types are being released as Preview features with Spring ‘23. We plan to iterate on these field types and release them generally in a forthcoming release.
Limitations and Guidance
- At this time, we do not support any conversion from the native storage format of either field type into HTML. The implications here are:
- We do not recommend attempting to render the Rich-Text v2 Field Type on non-React front-ends
- Developers will need to handle conversion from Markdown to HTML themselves. There are existing libraries to handle this conversion, but there is no Yext-owned library.
- At this time, we do not have tooling to assist users with migrating from a field of the existing Rich-Text type to either of the new field types.
Rich-Text v2
The Rich-Text v2 Field Type offers a fully featured WYSIWYG editor, with support for a wide variety of formatting.
- Target Use Case: This field type is intended primarily for authoring formatted content in Knowledge Graph.
- Target Audience: This field type is suitable for use by all content managers, regardless of technical abilities.
Supported Formatting
The following is the current list of supported formatting options in the Rich-Text v2 Field Type.
Format | Notable Details and Limitataions |
---|---|
Bold, Italic, Underline | |
Headings | H1 through H6 |
Text Color | Supports custom color palette |
Text Highlight Color | Supports custom color palette |
Bulleted List | Supports nested bullets |
Numbered List | Supports beginning at arbitrary numbers |
Strikethrough | |
Superscript, Subscript | |
Hyperlink Text | |
Image Upload & Hyperlink | Use the Yext Image Uploader to upload an image and then link text to that image using the returned Yext Hosted URL for that image. |
Quote | |
Horizontal Line | |
Code Snippet | |
Code Block | |
Tables | |
Undo/Redo | |
Text Alignment | |
Clipboard Support | Copy and pasting from one rich-text editor (i.e. a Word Processor) to the Rich-Text v2 Field preserves (most) formatting. Note: Formatting is not preserved when pasting from Google Docs. This lack of support is a known issue when leveraging a restrictive Content Security Policy in a Lexical Rich-Text Editor, based on how Google Docs constructs styling when copying. The technical details are explained here , and we are pursuing a solution. A workaround is to paste into another editor, like Word, before pasting into the rich-text field. |
Storage Format
The underlying storage format of the Rich-Text v2 Field Type is a JSON Abstract Syntax Tree (AST). This storage format is based primarily on the library that the system leverages, which is Lexical.dev .
Most modern rich-text editors use an AST as their storage format, as this structured format makes working with formatted content in code much simpler, and ensures that the types of supported formatting can be expanded over time.
Because the storage format is an AST, importing and exporting content to the Rich-Text v2 field type requires processing to/from the AST. This import and export process is covered in detail below.
Object Structure
In code interfaces, Rich-Text v2 Field Types are represented as a structured object with a sub-property called json
, where the AST is included. The following is an example of a simple Rich-Text v2 Field (c_richTextv2Description
) as returned by the Content API.
{
"id": "product-1",
"name": "Product 1",
"c_richTextv2Description": {
"json": {
"root": {
"children": [
{
"children": [
{
"detail": 0,
"format": 1,
"mode": "normal",
"style": "",
"text": "bold text",
"type": "text",
"version": 1
}
],
"direction": "ltr",
"format": "",
"indent": 0,
"type": "paragraph",
"version": 1
}
],
"direction": "ltr",
"format": "",
"indent": 0,
"type": "root",
"version": 1
}
}
}
}
In the future, when the system supports exporting from this field type in other formats, these conversions will be contained in other named subproperties, such as html
and plaintext
.
Importing Content to Rich-Text v2
Commonly, when moving over from another source of truth, the content in that system can be exported in a standard format, such as HTML or Markdown. If you intend to manage this content out of Knowledge Graph going forward, you’ll need to convert the content into the Yext Rich-Text AST in order to successfully import it into Yext.
At this time, we do not support any native transformations from HTML/Markdown to the Rich-Text AST. We intend to add support for a Connectors Transform in a coming release.
If you wish to import HTML or MD to the rich-text field type in the interim, you can leverage the Lexical.dev packages directly. Note that using the Lexical packages is a bit more involved than running a simple conversion function, as you will need to initialize an editor state, even if you have no intention of rendering an editor, which is why we intend to provide better support for this use case. Specifically the following packages are relevant:
Note: The Rich-Text v2 field type is primarily intended for authoring content in Knowledge Graph. If you do not intend to author directly in KG, but wish to pass formatted content through KG to be served on your digital experiences, we recommend leveraging the Markdown field type.
Exporting and Rendering Content From Rich-Text v2
In order to render content from the Rich-Text v2 field type on a website, the content needs to eventually be converted into HTML. As such, we intend to provide tooling to make this conversion task as easy and ergonomic as possible.
At this time, we support a React Component for rendering the Rich-Text AST in our @yext/react-components library . We recommend leveraging this component on any React-based front-end experiences, as it abstracts away the complexity of processing the AST.
We do not currently support a native conversion from AST->HTML. We intend to support an upstream conversion, so that front-ends written in other languages besides React can easily leverage this field type. We plan to provide support for conversion from AST->HTML in Streams (and thus Pages, Search, and Content API), as well as in the Entities API (Management API), in a coming release.
Until that point, if you are not leveraging a React-based front-end, we do not recommend attempting to leverage the Rich-Text v2 Field Type on your front-ends. Lexical.dev does provide an HTML package which supports converting their AST to HTML; however, as we introduce new formatting (and thus, new node types) to our own AST, the burden on a developer to implement support for these new node types by extending the Lexical library will become increasingly challenging.
Limitations
- No Yext-provided tools for converting content from HTML/MD to Yext Rich-Text AST (importing content)
- No Yext-provided tools for converting content from Yext Rich-Text AST to HTML (exporting and rendering content)
- Only recommended for usage on React front-ends at this time
Markdown
The Markdown Field Type offers a Markdown editor with a side-by-side rendered view.
- Target Use Cases:
- This field type is intended primarily for authoring formatted content in Markdown/HTML in Knowledge Graph
- This field type is well suited when an external system is the source of truth, and the formatted content will not be managed primarily out of KG, as it can ingest formatted content from external sources losslessly.
- Target Audience: This field type is suitable for use by technical content managers who prefer to author formatted content in code.
Support Formatting
The full list of supported formatting is any formatting which is supported:
- Natively in Markdown (specifically Github-Flavored) Markdown )
- In HTML, as HTML can be included in Markdown directly as markup
Thus, this field type is guaranteed to be the most flexible, as it will support any formatting supported on the web.
Storage Format
The underlying storage format of the Markdown Field Type is Github-Flavored) Markdown (GFM). As mentioned above, HTML can be included in the field directly as markup.
Object Structure (Code)
In code interfaces, Markdown Field Types are represented as a structured object with a sub-property called markdown
, where the Markdown is included. The following is an example of a simple Markdown Field (c_markdownDescription
) as returned by the Content API.
{
"id": "product-1",
"name": "Product 1",
"c_markdownDescription": {
"markdown": "**bold text**\n\n"
}
}
In the future, when the system supports exporting from this field type in other formats, these conversions will be contained in other named subproperties, such as html
and plaintext
.
Importing Content to Markdown
No conversion is needed to import content into the Markdown Field Type. Because the field type has a storage format of Markdown, and also accepts arbitrary HTML, any text can be stored in this field type.
Because this field type requires no conversion on-import, it is well suited for ingesting formatted content from external source systems. This import will be lossless, since the system will store the content as provided, assuming a valid string is provided.
When rendering the stored content in Entity Edit, the system leverages rehype , a Javascript package for sanitizing HTML. This library ensures that any malicious scripts are not executed when rendering this content.
In the future, we may consider supporting some tooling to help strip out in-line CSS during ingestion, likely in the Connectors Transform layer. We understand that sometimes formatted content comes with extra styling which is unnecessary when attempting to only preserve the document structure. If you think this is a good idea, and believe it would be valuable for your use case, please submit to the Hitchhiker Ideas Board !
Exporting and Rendering Content from Markdown
In order to render content from the Markdown field type on a website, the content needs to eventually be converted into HTML.
Since Github-Flavored) Markdown is a standard format, there are a wide swath of well maintained libraries that handle converting GFM to HTML which can be leveraged to achieve this goal. For Javascript front-ends, we recommend ShowdownJS ; if you choose to use Showdown, be sure to set your “flavor” to GFM.
Additionally, as mentioned above, we leverage the rehype javascript library to sanitize content when rendering in Entity Edit. We recommend leveraging this library, or a similar library, to sanitize your HTML; this approach will ensure your front-end matches what you see in Entity Edit, and you are protected against any scripts which might otherwise break your website.
We also have a pre-built React component which handles sanitizing and rendering Github-flavored Markdown. You can find this component in our @yext/react-components library .
In a coming release, we plan to support conversion from MD->HTML in Streams (and thus Pages, Search, and Content API), as well as in the Entities API (Management API). At this point, developers can simply request HTML instead of converting the content themselves.
Known Limitations
- No Yext-provided tools for converting content from MD to HTML (exporting and rendering content)
- No Yext-provided tools for stripping in-line CSS when importing HTML to the Markdown field type
Migrating from Existing Rich-Text Field Type
At this time, we do not have tooling to assist users with migrating from a field of the existing Rich-Text type to either of the new field types.
This lack of tooling means that if you wish to begin using either of the new field types as replacements for your existing Rich-Text field(s), you will need to manually create new fields, and migrate the content over. We do not recommend attempting this migration yourself at this time, as it is going to be error prone due to a mismatch in the storage formats, and a lack of tooling for converting between formats.
In a coming release, we plan to introduce tooling to alleviate the burden of moving from the Rich-Text v1 field type to either of the new field types. This tooling will assist users in creating a new field from the legacy field, and porting the content over in the appropriate storage format.