Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[lexical-link] Test: Removing link from node(children) #6817

Merged
merged 10 commits into from
Nov 15, 2024
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,10 @@ import {
LinkNode,
SerializedLinkNode,
} from '@lexical/link';
import {$createMarkNode, $isMarkNode} from '@lexical/mark';
import {
$createParagraphNode,
$createTextNode,
$getRoot,
$selectAll,
ParagraphNode,
Expand Down Expand Up @@ -409,5 +412,70 @@ describe('LexicalLinkNode tests', () => {
const link = paragraph.children[0] as SerializedLinkNode;
expect(link.title).toBe('Lexical Website');
});

test('$toggleLink correctly removes link when textnode has children(like marknode)', async () => {
const {editor} = testEnv;
await editor.update(() => {
const paragraph = $createParagraphNode();
const precedingText = $createTextNode('some '); // space after
const textNode = $createTextNode('text');

paragraph.append(precedingText, textNode);

const linkNode = $createLinkNode('https://example.com/foo', {
rel: 'noreferrer',
});
textNode.insertAfter(linkNode);
linkNode.append(textNode);

const markNode = $createMarkNode(['knetk']);
textNode.insertBefore(markNode);
markNode.append(textNode);
$getRoot().append(paragraph);
});

editor.read(() => {
const paragraph = $getRoot().getFirstChild() as ParagraphNode;
const [textNode, linkNode] = paragraph.getChildren();

// Check first text node
expect(textNode.getTextContent()).toBe('some ');

// Check link node and its nested structure
if ($isLinkNode(linkNode)) {
expect(linkNode.getURL()).toBe('https://example.com/foo');
expect(linkNode.getRel()).toBe('noreferrer');

// Check mark node nested inside link
const markNode = linkNode.getFirstChild();
if ($isMarkNode(markNode)) {
expect(markNode.getType()).toBe('mark');
expect(markNode.getIDs()).toEqual(['knetk']);
expect(markNode.getTextContent()).toBe('text');
}
}
});

await editor.update(() => {
$selectAll();
$toggleLink(null);
});

// Verify structure after link removal
editor.read(() => {
const paragraph = $getRoot().getFirstChild() as ParagraphNode;
const [textNode, markNode] = paragraph.getChildren();

// Check text node remains unchanged
expect(textNode.getTextContent()).toBe('some ');

// Check mark node is preserved and moved up to paragraph level
if ($isMarkNode(markNode)) {
expect(markNode.getType()).toBe('mark');
expect(markNode.getIDs()).toEqual(['knetk']);
expect(markNode.getTextContent()).toBe('text');
}
});
});
});
});
2 changes: 2 additions & 0 deletions packages/lexical/src/__tests__/utils/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {HashtagNode} from '@lexical/hashtag';
import {createHeadlessEditor} from '@lexical/headless';
import {AutoLinkNode, LinkNode} from '@lexical/link';
import {ListItemNode, ListNode} from '@lexical/list';
import {MarkNode} from '@lexical/mark';
import {OverflowNode} from '@lexical/overflow';
import {
InitialConfigType,
Expand Down Expand Up @@ -486,6 +487,7 @@ const DEFAULT_NODES: NonNullable<InitialConfigType['nodes']> = [
TestInlineElementNode,
TestShadowRootNode,
TestTextNode,
MarkNode,
];

export function TestComposer({
Expand Down
Loading