Upgrade blocknote dependencies from 0.31.1 to 0.47.0. (#18207)

This PR pgrades all BlockNote packages (@blocknote/core,
@blocknote/react, @blocknote/mantine, @blocknote/server-util,
@blocknote/xl-docx-exporter, @blocknote/xl-pdf-exporter) to 0.47.0 and
adapts the codebase to the new API.

### Changes
- Dependency upgrades: Bumped all BlockNote packages to 0.47.0, added
required Mantine v8 peer dependencies, removed unnecessary prosemirror
resolutions
- Formatting toolbar: Replaced the manual reimplementation of
FormattingToolbarController (which handled visibility, positioning,
portal rendering, text-alignment-based placement, and a
dangerouslySetInnerHTML transition trick) with BlockNote's built-in
FormattingToolbarController. The toolbar buttons themselves are
unchanged.
- Side menu: Replaced manual drag handle menu positioning and rendering
(DashboardBlockDragHandleMenu, DashboardBlockColorPicker, and their
floating configs) with BlockNote's built-in SideMenuController,
DragHandleButton, and DragHandleMenu components. Deleted 4 files that
became dead code.
- Extension API migration: Replaced deprecated editor.suggestionMenus
and editor.formattingToolbar APIs with the new extension system
(SuggestionMenu, useExtensionState, editor.getExtension())
- Slash menu fixes: Filtered out BlockNote's new default "File" item
(added in 0.47) to avoid duplicates with our custom one; added icon
mappings for new block types (Toggle List, Divider, Toggle Headings,
Headings 4-6)
- Server-side: Switched @blocknote/server-util to dynamic import() to
handle ESM-only transitive dependencies in CJS context
This commit is contained in:
Abdullah.
2026-02-27 13:16:49 +05:00
committed by GitHub
parent def5ea5764
commit 4ed09a3feb
26 changed files with 851 additions and 1220 deletions
@@ -5,19 +5,28 @@ import {
} from 'twenty-shared/types';
import { isDefined } from 'twenty-shared/utils';
import type { ServerBlockNoteEditor } from '@blocknote/server-util';
// Reuse a single ServerBlockNoteEditor across all calls to avoid
// the cost of dynamic import resolution + instance creation (~90ms) on every transform.
// eslint-disable-next-line @typescript-eslint/no-explicit-any
let cachedServerBlockNoteEditor: any = null;
let cachedServerBlockNoteEditor: ServerBlockNoteEditor | null = null;
const getServerBlockNoteEditor = async () => {
if (!cachedServerBlockNoteEditor) {
const { ServerBlockNoteEditor } = await import('@blocknote/server-util');
// SWC compiles import() to require() in CJS mode, which breaks ESM-only
// transitive dependencies in @blocknote/core. Native import() resolves
// the ESM bundle path where the full chain works.
const nativeImport = new Function('specifier', 'return import(specifier)');
cachedServerBlockNoteEditor = ServerBlockNoteEditor.create();
const getServerBlockNoteEditor = async (): Promise<ServerBlockNoteEditor> => {
if (cachedServerBlockNoteEditor) {
return cachedServerBlockNoteEditor;
}
return cachedServerBlockNoteEditor;
const module = await nativeImport('@blocknote/server-util');
const editor: ServerBlockNoteEditor = module.ServerBlockNoteEditor.create();
cachedServerBlockNoteEditor = editor;
return editor;
};
export const transformRichTextV2Value = async (