[WEB-3489] improvement: add support to disable extensions in rich and lite text editor (#6721)

* [WEB-3489] improvement: add support to disable extensions in rich text editor

* improvements: disabled extensions prop for all editor components
This commit is contained in:
Prateek Shourya 2025-03-07 16:34:07 +05:30 committed by GitHub
parent a77fe7aa90
commit a953013f70
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 58 additions and 40 deletions

View file

@ -3,3 +3,5 @@ export type PartialDeep<K> = {
};
export type CompleteOrEmpty<T> = T | Record<string, never>;
export type MakeOptional<T, K extends keyof T> = Omit<T, K> & Partial<Pick<T, K>>;

View file

@ -1,6 +1,7 @@
import React from "react";
// editor
// plane imports
import { EditorRefApi, ILiteTextEditor, LiteTextEditorWithRef, TFileHandler } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot, IssueCommentToolbar } from "@/components/editor";
// helpers
@ -9,7 +10,7 @@ import { getEditorFileHandlers } from "@/helpers/editor.helper";
import { isCommentEmpty } from "@/helpers/string.helper";
interface LiteTextEditorWrapperProps
extends Omit<ILiteTextEditor, "disabledExtensions" | "fileHandler" | "mentionHandler"> {
extends MakeOptional<Omit<ILiteTextEditor, "fileHandler" | "mentionHandler">, "disabledExtensions"> {
anchor: string;
workspaceId: string;
isSubmitting?: boolean;
@ -25,6 +26,7 @@ export const LiteTextEditor = React.forwardRef<EditorRefApi, LiteTextEditorWrapp
isSubmitting = false,
showSubmitButton = true,
uploadFile,
disabledExtensions,
...rest
} = props;
function isMutableRefObject<T>(ref: React.ForwardedRef<T>): ref is React.MutableRefObject<T | null> {
@ -38,7 +40,7 @@ export const LiteTextEditor = React.forwardRef<EditorRefApi, LiteTextEditorWrapp
<div className="border border-custom-border-200 rounded p-3 space-y-3">
<LiteTextEditorWithRef
ref={ref}
disabledExtensions={[]}
disabledExtensions={disabledExtensions ?? []}
fileHandler={getEditorFileHandlers({
anchor,
uploadFile,

View file

@ -1,25 +1,26 @@
import React from "react";
// editor
// plane imports
import { EditorReadOnlyRefApi, ILiteTextReadOnlyEditor, LiteTextReadOnlyEditorWithRef } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
import { cn } from "@/helpers/common.helper";
import { getReadOnlyEditorFileHandlers } from "@/helpers/editor.helper";
type LiteTextReadOnlyEditorWrapperProps = Omit<
ILiteTextReadOnlyEditor,
"disabledExtensions" | "fileHandler" | "mentionHandler"
type LiteTextReadOnlyEditorWrapperProps = MakeOptional<
Omit<ILiteTextReadOnlyEditor, "fileHandler" | "mentionHandler">,
"disabledExtensions"
> & {
anchor: string;
workspaceId: string;
};
export const LiteTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, LiteTextReadOnlyEditorWrapperProps>(
({ anchor, workspaceId, ...props }, ref) => (
({ anchor, workspaceId, disabledExtensions, ...props }, ref) => (
<LiteTextReadOnlyEditorWithRef
ref={ref}
disabledExtensions={[]}
disabledExtensions={disabledExtensions ?? []}
fileHandler={getReadOnlyEditorFileHandlers({
anchor,
workspaceId,

View file

@ -1,20 +1,21 @@
import React, { forwardRef } from "react";
// editor
// plane imports
import { EditorRefApi, IRichTextEditor, RichTextEditorWithRef, TFileHandler } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
import { getEditorFileHandlers } from "@/helpers/editor.helper";
interface RichTextEditorWrapperProps
extends Omit<IRichTextEditor, "disabledExtensions" | "fileHandler" | "mentionHandler"> {
extends MakeOptional<Omit<IRichTextEditor, "fileHandler" | "mentionHandler">, "disabledExtensions"> {
anchor: string;
uploadFile: TFileHandler["upload"];
workspaceId: string;
}
export const RichTextEditor = forwardRef<EditorRefApi, RichTextEditorWrapperProps>((props, ref) => {
const { anchor, containerClassName, uploadFile, workspaceId, ...rest } = props;
const { anchor, containerClassName, uploadFile, workspaceId, disabledExtensions, ...rest } = props;
return (
<RichTextEditorWithRef
@ -22,7 +23,7 @@ export const RichTextEditor = forwardRef<EditorRefApi, RichTextEditorWrapperProp
renderComponent: (props) => <EditorMentionsRoot {...props} />,
}}
ref={ref}
disabledExtensions={[]}
disabledExtensions={disabledExtensions ?? []}
fileHandler={getEditorFileHandlers({
anchor,
uploadFile,

View file

@ -1,25 +1,26 @@
import React from "react";
// editor
// plane imports
import { EditorReadOnlyRefApi, IRichTextReadOnlyEditor, RichTextReadOnlyEditorWithRef } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
import { cn } from "@/helpers/common.helper";
import { getReadOnlyEditorFileHandlers } from "@/helpers/editor.helper";
type RichTextReadOnlyEditorWrapperProps = Omit<
IRichTextReadOnlyEditor,
"disabledExtensions" | "fileHandler" | "mentionHandler"
type RichTextReadOnlyEditorWrapperProps = MakeOptional<
Omit<IRichTextReadOnlyEditor, "fileHandler" | "mentionHandler">,
"disabledExtensions"
> & {
anchor: string;
workspaceId: string;
};
export const RichTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, RichTextReadOnlyEditorWrapperProps>(
({ anchor, workspaceId, ...props }, ref) => (
({ anchor, workspaceId, disabledExtensions, ...props }, ref) => (
<RichTextReadOnlyEditorWithRef
ref={ref}
disabledExtensions={[]}
disabledExtensions={disabledExtensions ?? []}
fileHandler={getReadOnlyEditorFileHandlers({
anchor,
workspaceId,

View file

@ -6,6 +6,7 @@ import { EditorRefApi, ILiteTextEditor, LiteTextEditorWithRef, TFileHandler } fr
// i18n
import { useTranslation } from "@plane/i18n";
// components
import { MakeOptional } from "@plane/types";
import { EditorMentionsRoot, IssueCommentToolbar } from "@/components/editor";
// helpers
import { cn } from "@/helpers/common.helper";
@ -19,7 +20,7 @@ import { WorkspaceService } from "@/plane-web/services";
const workspaceService = new WorkspaceService();
interface LiteTextEditorWrapperProps
extends Omit<ILiteTextEditor, "disabledExtensions" | "fileHandler" | "mentionHandler"> {
extends MakeOptional<Omit<ILiteTextEditor, "fileHandler" | "mentionHandler">, "disabledExtensions"> {
workspaceSlug: string;
workspaceId: string;
projectId: string;
@ -49,6 +50,7 @@ export const LiteTextEditor = React.forwardRef<EditorRefApi, LiteTextEditorWrapp
showToolbarInitially = true,
placeholder = t("issue.comments.placeholder"),
uploadFile,
disabledExtensions: additionalDisabledExtensions,
...rest
} = props;
// states
@ -81,7 +83,7 @@ export const LiteTextEditor = React.forwardRef<EditorRefApi, LiteTextEditorWrapp
>
<LiteTextEditorWithRef
ref={ref}
disabledExtensions={disabledExtensions}
disabledExtensions={[...disabledExtensions, ...(additionalDisabledExtensions ?? [])]}
fileHandler={getEditorFileHandlers({
projectId,
uploadFile,

View file

@ -1,6 +1,7 @@
import React from "react";
// plane editor
// plane imports
import { EditorReadOnlyRefApi, ILiteTextReadOnlyEditor, LiteTextReadOnlyEditorWithRef } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
@ -10,9 +11,9 @@ import { useEditorConfig } from "@/hooks/editor";
// plane web hooks
import { useEditorFlagging } from "@/plane-web/hooks/use-editor-flagging";
type LiteTextReadOnlyEditorWrapperProps = Omit<
ILiteTextReadOnlyEditor,
"disabledExtensions" | "fileHandler" | "mentionHandler"
type LiteTextReadOnlyEditorWrapperProps = MakeOptional<
Omit<ILiteTextReadOnlyEditor, "fileHandler" | "mentionHandler">,
"disabledExtensions"
> & {
workspaceId: string;
workspaceSlug: string;
@ -20,7 +21,7 @@ type LiteTextReadOnlyEditorWrapperProps = Omit<
};
export const LiteTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, LiteTextReadOnlyEditorWrapperProps>(
({ workspaceId, workspaceSlug, projectId, ...props }, ref) => {
({ workspaceId, workspaceSlug, projectId, disabledExtensions: additionalDisabledExtensions, ...props }, ref) => {
// editor flaggings
const { liteTextEditor: disabledExtensions } = useEditorFlagging(workspaceSlug?.toString());
// editor config
@ -29,7 +30,7 @@ export const LiteTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, Lit
return (
<LiteTextReadOnlyEditorWithRef
ref={ref}
disabledExtensions={disabledExtensions}
disabledExtensions={[...disabledExtensions, ...(additionalDisabledExtensions ?? [])]}
fileHandler={getReadOnlyEditorFileHandlers({
projectId,
workspaceId,

View file

@ -1,8 +1,7 @@
import React, { forwardRef } from "react";
// editor
// plane imports
import { EditorRefApi, IRichTextEditor, RichTextEditorWithRef, TFileHandler } from "@plane/editor";
// plane types
import { TSearchEntityRequestPayload, TSearchResponse } from "@plane/types";
import { MakeOptional, TSearchEntityRequestPayload, TSearchResponse } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
@ -13,7 +12,7 @@ import { useEditorConfig, useEditorMention } from "@/hooks/editor";
import { useEditorFlagging } from "@/plane-web/hooks/use-editor-flagging";
interface RichTextEditorWrapperProps
extends Omit<IRichTextEditor, "disabledExtensions" | "fileHandler" | "mentionHandler"> {
extends MakeOptional<Omit<IRichTextEditor, "fileHandler" | "mentionHandler">, "disabledExtensions"> {
searchMentionCallback: (payload: TSearchEntityRequestPayload) => Promise<TSearchResponse>;
workspaceSlug: string;
workspaceId: string;
@ -22,8 +21,16 @@ interface RichTextEditorWrapperProps
}
export const RichTextEditor = forwardRef<EditorRefApi, RichTextEditorWrapperProps>((props, ref) => {
const { containerClassName, workspaceSlug, workspaceId, projectId, searchMentionCallback, uploadFile, ...rest } =
props;
const {
containerClassName,
workspaceSlug,
workspaceId,
projectId,
searchMentionCallback,
uploadFile,
disabledExtensions: additionalDisabledExtensions,
...rest
} = props;
// editor flaggings
const { richTextEditor: disabledExtensions } = useEditorFlagging(workspaceSlug?.toString());
// use editor mention
@ -36,7 +43,7 @@ export const RichTextEditor = forwardRef<EditorRefApi, RichTextEditorWrapperProp
return (
<RichTextEditorWithRef
ref={ref}
disabledExtensions={disabledExtensions}
disabledExtensions={[...disabledExtensions, ...(additionalDisabledExtensions ?? [])]}
fileHandler={getEditorFileHandlers({
projectId,
uploadFile,

View file

@ -1,6 +1,7 @@
import React from "react";
// editor
// plane imports
import { EditorReadOnlyRefApi, IRichTextReadOnlyEditor, RichTextReadOnlyEditorWithRef } from "@plane/editor";
import { MakeOptional } from "@plane/types";
// components
import { EditorMentionsRoot } from "@/components/editor";
// helpers
@ -10,9 +11,9 @@ import { useEditorConfig } from "@/hooks/editor";
// plane web hooks
import { useEditorFlagging } from "@/plane-web/hooks/use-editor-flagging";
type RichTextReadOnlyEditorWrapperProps = Omit<
IRichTextReadOnlyEditor,
"disabledExtensions" | "fileHandler" | "mentionHandler"
type RichTextReadOnlyEditorWrapperProps = MakeOptional<
Omit<IRichTextReadOnlyEditor, "fileHandler" | "mentionHandler">,
"disabledExtensions"
> & {
workspaceId: string;
workspaceSlug: string;
@ -20,7 +21,7 @@ type RichTextReadOnlyEditorWrapperProps = Omit<
};
export const RichTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, RichTextReadOnlyEditorWrapperProps>(
({ workspaceId, workspaceSlug, projectId, ...props }, ref) => {
({ workspaceId, workspaceSlug, projectId, disabledExtensions: additionalDisabledExtensions, ...props }, ref) => {
// editor flaggings
const { richTextEditor: disabledExtensions } = useEditorFlagging(workspaceSlug?.toString());
// editor config
@ -29,7 +30,7 @@ export const RichTextReadOnlyEditor = React.forwardRef<EditorReadOnlyRefApi, Ric
return (
<RichTextReadOnlyEditorWithRef
ref={ref}
disabledExtensions={disabledExtensions}
disabledExtensions={[...disabledExtensions, ...(additionalDisabledExtensions ?? [])]}
fileHandler={getReadOnlyEditorFileHandlers({
projectId,
workspaceId,