Skip to content

Commit

Permalink
fix: add validator for exit code link
Browse files Browse the repository at this point in the history
  • Loading branch information
rahulyadav-57 committed Feb 5, 2025
1 parent df05c01 commit e37f03f
Show file tree
Hide file tree
Showing 3 changed files with 25 additions and 15 deletions.
30 changes: 17 additions & 13 deletions src/components/shared/LogView/LogPopover.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import { ExitCodes } from '@/constant/exitCodes';
import { WebLinkProvider } from '@/utility/terminal/xtermWebLinkProvider';
import { EXIT_CODE_ICON_PATTERN } from '@/utility/text';
import { EXIT_CODE_PATTERN } from '@/utility/text';
import { Terminal } from '@xterm/xterm';
import { Popover } from 'antd';
import { FC, useCallback, useEffect, useRef, useState } from 'react';
Expand All @@ -13,14 +13,14 @@ interface Props {

interface IPopoverState {
visible: boolean;
text: string;
exitCode: string | null;
x: number;
y: number;
}

const defaultState: IPopoverState = {
visible: false,
text: '',
exitCode: null,
x: 0,
y: 0,
};
Expand All @@ -31,16 +31,16 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
const hideTimerRef = useRef<number | null>(null);

const showPopover = useCallback(
(opts: { text: string; x: number; y: number }) => {
({ exitCode, x, y }: Omit<IPopoverState, 'visible'>) => {
if (hideTimerRef.current) {
window.clearTimeout(hideTimerRef.current);
hideTimerRef.current = null;
}
setPopoverState({
visible: true,
text: opts.text,
x: opts.x,
y: opts.y,
exitCode,
x,
y,
});
},
[],
Expand Down Expand Up @@ -71,7 +71,7 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
if (!terminal) return;

terminal.registerLinkProvider(
new WebLinkProvider(terminal, EXIT_CODE_ICON_PATTERN, () => {}, {
new WebLinkProvider(terminal, EXIT_CODE_PATTERN, () => {}, {
hover: (_, text, location) => {
const terminalRect = terminal.element?.getBoundingClientRect();
if (!terminalRect) return;
Expand Down Expand Up @@ -100,14 +100,18 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
const exitCode = text.split(': ')[1];

showPopover({
text: exitCode.replace(' ⓘ', ''),
exitCode,
x: linkX + 5,
y: linkY + 25,
});
},
leave: () => {
hidePopover();
},
validator(match) {
const code = match[1];
return ExitCodes[code] !== undefined;
},
}),
);
}, [terminal]);
Expand All @@ -116,9 +120,9 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
onInit();
}, [terminal]);

const { visible, text, x, y } = popoverState;
const { visible, exitCode, x, y } = popoverState;

if (!visible) return <></>;
if (!visible || !exitCode) return <></>;

return (
<div
Expand All @@ -140,7 +144,7 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
onMouseEnter={onPopoverMouseEnter}
onMouseLeave={onPopoverMouseLeave}
>
<h4 className={s.exitCodeHeading}>Exit Code: {text}</h4>
<h4 className={s.exitCodeHeading}>Exit Code: {exitCode}</h4>
<Markdown
components={{
a: ({ href, children, ...props }) => {
Expand All @@ -152,7 +156,7 @@ export const LogPopover: FC<Props> = ({ terminal }) => {
},
}}
>
{ExitCodes[text]?.description}
{ExitCodes[exitCode]?.description}
</Markdown>
<a
href={`https://docs.tact-lang.org/book/exit-codes/#${text}`}
Expand Down
7 changes: 7 additions & 0 deletions src/utility/terminal/xtermWebLinkProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ export interface ILinkProviderOptions {
hover?(event: MouseEvent, text: string, location: IViewportRange): void;
leave?(event: MouseEvent, text: string): void;
urlRegex?: RegExp;
validator?: (match: RegExpExecArray) => boolean;
}

export class WebLinkProvider implements ILinkProvider {
Expand All @@ -34,6 +35,7 @@ export class WebLinkProvider implements ILinkProvider {
this._regex,
this._terminal,
this._handler,
this._options.validator ?? (() => true),
);
callback(this._addCallbacks(links));
}
Expand All @@ -59,6 +61,7 @@ export class LinkComputer {
regex: RegExp,
terminal: Terminal,
activate: (event: MouseEvent, uri: string) => void,
validator: (match: RegExpExecArray) => boolean = () => true,
): ILink[] {
const rex = new RegExp(regex.source, (regex.flags || '') + 'g');

Expand All @@ -74,6 +77,10 @@ export class LinkComputer {
while ((match = rex.exec(line))) {
const text = match[0];

if (!validator(match)) {
continue;
}

// map string positions back to buffer positions
// values are 0-based right side excluding
const [startY, startX] = LinkComputer._mapStrIdx(
Expand Down
3 changes: 1 addition & 2 deletions src/utility/text.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,13 @@ import { ExitCodes } from '@/constant/exitCodes';
import { applyAnsiUnderline } from './terminal/ansiStyles';

export const EXIT_CODE_PATTERN = /exit_code:\s*(\d+)/;
export const EXIT_CODE_ICON_PATTERN = /exit_code:\s*\d+\s*/;

export const highLightExitCode = (message: string) => {
const match = message.match(EXIT_CODE_PATTERN);
const code = match ? match[1] : undefined;

if (match && code && ExitCodes[code]) {
const highlightedMessage = applyAnsiUnderline(`exit_code: ${code}`);
const highlightedMessage = applyAnsiUnderline(`exit_code: ${code}`);
const newMessage = message.replace(EXIT_CODE_PATTERN, highlightedMessage);
return newMessage;
}
Expand Down

0 comments on commit e37f03f

Please sign in to comment.