feat: updated components header styling (#8085)

* Removed unused styles

* Updated node icon to follow design

* Updated node name to follow design and include Beta

* Removed Beta from node status

* Removed unused classes and parameters from GenericNode

* Changed node description padding on input

* Changed paddings and gaps

* removed unused classes

* Added accent purple foreground color to Experimental

* Fixed classes and gaps in generic node

* Fixed node name gaps

* Fixed node status classes and styling

* Removed unused classes and changed run-bg size

* Changed test to use new test id

* Changed Node Name to have beta tooltip

* Changed Build Failed icon to be a circle alert

* Changed Node Status gap and conditions to show spacings correctly

* Changed padding to not change height of other components

* Changed nodeStatus to show validation on small node

* Changed classes to show correct spacing and overflow

* Changed description size

* Fixed description text size

* Fixed input margin

* Fixed description editing not appearing when no description is available

* Fixed status not breaking words

* Updated colors

* Updated node output color

* [autofix.ci] apply automated fixes

* Changed duration style in chat

* Re-added output color

* Updated timeout on mcp server tab test

* Added more timeout to mcp server tab test

* fixed loop component test

---------

Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com>
This commit is contained in:
Lucas Oliveira 2025-05-22 15:32:16 -03:00 committed by GitHub
commit 4f9e2705d8
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
16 changed files with 148 additions and 221 deletions

View file

@ -78,7 +78,8 @@ export default function NodeDescription({
<MemoizedMarkdown
linkTarget="_blank"
className={cn(
"markdown prose flex w-full flex-col text-mmd leading-5 word-break-break-word [&_pre]:whitespace-break-spaces [&_pre]:!bg-code-description-background [&_pre_code]:!bg-code-description-background",
"markdown prose flex w-full flex-col leading-5 word-break-break-word [&_pre]:whitespace-break-spaces [&_pre]:!bg-code-description-background [&_pre_code]:!bg-code-description-background",
stickyNote ? "text-mmd" : "text-xs",
mdClassName,
)}
>
@ -153,7 +154,8 @@ export default function NodeDescription({
<Textarea
maxLength={charLimit}
className={cn(
"nowheel h-full w-full p-0 text-mmd focus:border-primary focus:ring-0",
"nowheel w-full text-xs focus:border-primary focus:ring-0",
stickyNote ? "p-0" : "px-2 py-0.5",
inputClassName,
)}
autoFocus
@ -183,7 +185,7 @@ export default function NodeDescription({
data-testid="generic-node-desc"
ref={overflowRef}
className={cn(
"nodoubleclick generic-node-desc-text h-full cursor-grab text-mmd text-muted-foreground word-break-break-word",
"nodoubleclick generic-node-desc-text h-full cursor-grab text-muted-foreground word-break-break-word",
description === "" || !description ? "font-light italic" : "",
placeholderClassName,
)}

View file

@ -1,7 +1,8 @@
import ForwardedIconComponent from "@/components/common/genericIconComponent";
import ShadTooltip from "@/components/common/shadTooltipComponent";
import { Input } from "@/components/ui/input";
import useFlowsManagerStore from "@/stores/flowsManagerStore";
import useFlowStore from "@/stores/flowStore";
import { VertexBuildTypeAPI } from "@/types/api";
import { cn } from "@/utils/utils";
import { useEffect, useState } from "react";
@ -10,8 +11,6 @@ export default function NodeName({
selected,
nodeId,
showNode,
validationStatus,
isOutdated,
beta,
editNameDescription,
toggleEditNameDescription,
@ -21,8 +20,6 @@ export default function NodeName({
selected?: boolean;
nodeId: string;
showNode: boolean;
validationStatus: VertexBuildTypeAPI | null;
isOutdated: boolean;
beta: boolean;
editNameDescription: boolean;
toggleEditNameDescription: () => void;
@ -77,7 +74,7 @@ export default function NodeName({
};
return editNameDescription ? (
<div className="m-[1px] w-full">
<div className="w-full">
<Input
onBlur={handleBlur}
value={nodeName}
@ -85,33 +82,36 @@ export default function NodeName({
onChange={onChange}
data-testid={`input-title-${display_name}`}
onKeyDown={handleKeyDown}
className="py-1"
className="px-2 py-0"
/>
</div>
) : (
<div className="group flex w-full items-center gap-1">
<div className="group my-px flex flex-1 items-center gap-2 overflow-hidden">
<div
data-testid={"title-" + display_name}
className={cn(
"nodoubleclick w-full truncate font-medium text-primary",
"nodoubleclick truncate font-medium text-primary",
showNode ? "cursor-text" : "cursor-default",
)}
>
<div className="flex cursor-grab items-center gap-2">
<span
className={cn(
"max-w-44 cursor-grab truncate text-sm",
validationStatus?.data?.duration && "max-w-36",
beta && "max-w-36",
validationStatus?.data?.duration && beta && "max-w-20",
isOutdated && "max-w-40",
!showNode && "max-w-28",
)}
>
<span className={cn("cursor-grab truncate text-sm")}>
{display_name}
</span>
</div>
</div>
{beta && (
<div className="shrink-0">
<ShadTooltip content="Beta component">
<div className="flex h-4 w-4 items-center justify-center rounded-sm border border-accent-purple-foreground p-0.5">
<ForwardedIconComponent
name="FlaskConical"
className="text-accent-purple-foreground"
/>
</div>
</ShadTooltip>
</div>
)}
</div>
);
}

View file

@ -381,7 +381,7 @@ function NodeOutputField({
<div
ref={ref}
className={cn(
"relative mt-1 flex h-11 w-full flex-wrap items-center justify-between bg-muted px-5 py-2",
"relative flex h-11 w-full flex-wrap items-center justify-between bg-muted px-5 py-2",
lastOutput ? "rounded-b-[0.69rem]" : "",
isToolMode && "bg-primary",
)}

View file

@ -30,9 +30,11 @@ const ValidationDetails = ({
validationStatus,
}) => (
<div className="max-h-100 px-1 py-2.5">
<div className="flex max-h-80 flex-col gap-2 overflow-auto">
<div className="flex max-h-80 flex-col gap-2">
{validationString && (
<div className="text-sm text-foreground">{validationString}</div>
<div className="break-words text-sm text-foreground">
{validationString}
</div>
)}
{lastRunTime && (
<TimeStamp prefix={RUN_TIMESTAMP_PREFIX} time={lastRunTime} />

View file

@ -1,9 +1,7 @@
import ShadTooltip from "@/components/common/shadTooltipComponent";
import { Badge } from "@/components/ui/badge";
import { Button } from "@/components/ui/button";
import { ICON_STROKE_WIDTH } from "@/constants/constants";
import { BuildStatus, EventDeliveryType } from "@/constants/enums";
import { useGetConfig } from "@/controllers/API/queries/config/use-get-config";
import { BuildStatus } from "@/constants/enums";
import { usePostTemplateValue } from "@/controllers/API/queries/nodes/use-post-template-value";
import { track } from "@/customization/utils/analytics";
import { customOpenNewTab } from "@/customization/utils/custom-open-new-tab";
@ -21,7 +19,6 @@ import { VertexBuildTypeAPI } from "@/types/api";
import { NodeDataType } from "@/types/flow";
import { findLastNode } from "@/utils/reactflowUtils";
import { classNames, cn } from "@/utils/utils";
import { Check } from "lucide-react";
import { useEffect, useRef, useState } from "react";
import { useHotkeys } from "react-hotkeys-hook";
import IconComponent from "../../../../components/common/genericIconComponent";
@ -81,6 +78,12 @@ export default function NodeStatus({
buildStatus === BuildStatus.BUILT ||
(buildStatus !== BuildStatus.TO_BUILD && validationStatus?.valid);
const conditionError = buildStatus === BuildStatus.ERROR;
const conditionInactive = buildStatus === BuildStatus.INACTIVE;
const showNodeStatus =
conditionSuccess || conditionError || conditionInactive;
const lastRunTime = useFlowStore(
(state) => state.flowBuildStatus[nodeId_]?.timestamp,
);
@ -249,7 +252,6 @@ export default function NodeStatus({
}
}, [buildStatus, isBuilding]);
const divRef = useRef<HTMLDivElement>(null);
const [isHovered, setIsHovered] = useState(false);
const stopBuilding = useFlowStore((state) => state.stopBuilding);
@ -275,8 +277,8 @@ export default function NodeStatus({
: "Play";
const iconClasses = cn(
"play-button-icon",
isHovered ? "text-foreground" : "text-placeholder-foreground",
"h-3.5 w-3.5 transition-all group-hover/node:opacity-100",
isHovered ? "text-foreground" : "text-muted-foreground",
BuildStatus.BUILDING === buildStatus &&
(isHovered ? "text-status-red" : "animate-spin"),
);
@ -307,7 +309,7 @@ export default function NodeStatus({
isPolling: boolean,
): string => {
return cn(
"nodrag button-run-bg hit-area-icon group relative h-5 w-5 rounded-sm border border-accent-amber-foreground transition-colors hover:bg-accent-amber",
"nodrag button-run-bg group relative h-4 w-4 p-0.5 rounded-sm border border-accent-amber-foreground transition-colors hover:bg-accent-amber",
connectionLink === "error"
? "border-destructive text-destructive"
: isAuthenticated && !isPolling
@ -327,7 +329,7 @@ export default function NodeStatus({
isPolling: boolean,
): string => {
return cn(
"h-3 w-3 transition-opacity",
"transition-opacity h-2.5 w-2.5",
connectionLink === "error"
? "text-destructive"
: isAuthenticated && !isPolling
@ -348,56 +350,47 @@ export default function NodeStatus({
return `button_disconnected_${display_name.toLowerCase()}`;
};
return showNode ? (
<>
<div className="flex flex-shrink-0 items-center gap-1">
return (
<div className="flex shrink-0 items-center gap-2">
{(showNodeStatus || nodeAuth) && (
<div className="flex items-center gap-2 self-center">
<ShadTooltip
styleClasses={cn(
"border rounded-xl",
conditionSuccess
? "border-accent-emerald-foreground bg-success-background"
: "border-destructive bg-error-background",
)}
content={
<BuildStatusDisplay
buildStatus={buildStatus}
validationStatus={validationStatus}
validationString={validationString}
lastRunTime={lastRunTime}
/>
}
side="bottom"
>
<div className="cursor-help">
{conditionSuccess && validationStatus?.data?.duration ? (
<div className="font-jetbrains mr-1 flex gap-1 rounded-sm bg-accent-emerald px-1 text-xxs font-bold text-accent-emerald-foreground">
<Check className="h-4 w-4 items-center self-center" />
<span>
{normalizeTimeString(validationStatus?.data?.duration)}
</span>
</div>
) : (
<div className="flex items-center self-center pr-1">
{iconStatus}
</div>
{showNodeStatus && (
<ShadTooltip
styleClasses={cn(
"border rounded-xl",
conditionSuccess
? "border-accent-emerald-foreground bg-success-background"
: "border-destructive bg-error-background",
)}
</div>
</ShadTooltip>
{data.node?.beta && showNode && (
<Badge
size="sq"
className="pointer-events-none mr-1 flex h-[22px] w-10 justify-center rounded-[8px] bg-accent-pink text-accent-pink-foreground"
content={
<BuildStatusDisplay
buildStatus={buildStatus}
validationStatus={validationStatus}
validationString={validationString}
lastRunTime={lastRunTime}
/>
}
side="bottom"
>
<span className="text-xxs">Beta</span>
</Badge>
<div className="cursor-help">
{conditionSuccess && validationStatus?.data?.duration ? (
<div className="flex rounded-sm px-1 font-mono text-xs text-accent-emerald-foreground transition-colors hover:bg-accent-emerald">
<span>
{normalizeTimeString(validationStatus?.data?.duration)}
</span>
</div>
) : (
<div className="flex items-center self-center">
{iconStatus}
</div>
)}
</div>
</ShadTooltip>
)}
</div>
{nodeAuth && (
<ShadTooltip content={nodeAuth.auth_tooltip || "Connect"}>
<div>
{showNode && (
{nodeAuth && showNode && (
<ShadTooltip content={nodeAuth.auth_tooltip || "Connect"}>
<div>
<Button
unstyled
disabled={connectionLink === "" || connectionLink === "error"}
@ -430,7 +423,7 @@ export default function NodeStatus({
<IconComponent
name={"Unlink"}
className={cn(
"h-3 w-3 text-accent-amber-foreground opacity-0 transition-opacity",
"h-2.5 w-2.5 text-accent-amber-foreground opacity-0 transition-opacity",
isAuthenticated && !isPolling
? "group-hover:opacity-100"
: "",
@ -439,34 +432,31 @@ export default function NodeStatus({
/>
</div>
</Button>
)}
</div>
</ShadTooltip>
)}
</div>
</ShadTooltip>
)}
</div>
)}
{showNode && (
<ShadTooltip content={getTooltipContent()}>
<div
ref={divRef}
className="button-run-bg hit-area-icon"
onMouseEnter={() => setIsHovered(true)}
onMouseLeave={() => setIsHovered(false)}
onClick={handleClickRun}
className="-m-0.5"
>
{showNode && (
<Button unstyled className="nodrag group">
<div data-testid={`button_run_` + display_name.toLowerCase()}>
<IconComponent
name={iconName}
className={iconClasses}
strokeWidth={ICON_STROKE_WIDTH}
/>
</div>
</Button>
)}
<Button unstyled className="nodrag button-run-bg group">
<div data-testid={`button_run_` + display_name.toLowerCase()}>
<IconComponent
name={iconName}
className={iconClasses}
strokeWidth={ICON_STROKE_WIDTH}
/>
</div>
</Button>
</div>
</ShadTooltip>
</div>
</>
) : (
<></>
)}
</div>
);
}

View file

@ -5,18 +5,15 @@ import { useEffect, useState } from "react";
import { ICON_STROKE_WIDTH } from "@/constants/constants";
import { checkLucideIcons } from "@/CustomNodes/helpers/check-lucide-icons";
import { cn } from "@/utils/utils";
import IconComponent from "../../../../components/common/genericIconComponent";
export function NodeIcon({
icon,
dataType,
showNode,
isGroup,
}: {
icon?: string;
dataType: string;
showNode: boolean;
isGroup?: boolean;
}) {
const types = useTypesStore((state) => state.types);
@ -34,41 +31,18 @@ export function NodeIcon({
const isLucideIcon = checkLucideIcons(iconName);
const iconClassName = cn(
"generic-node-icon",
isLucideIcon ? "lucide-icon" : "integration-icon",
);
const renderIcon = () => {
if (icon && isEmoji) {
return <span className="text-lg">{icon}</span>;
}
if (isLucideIcon) {
return (
<div
className={cn(
"text-foreground",
!showNode && "flex min-h-8 min-w-8 items-center justify-center",
"bg-lucide-icon",
)}
>
<IconComponent
strokeWidth={ICON_STROKE_WIDTH}
name={iconName}
className={cn(iconClassName)}
/>
</div>
);
}
return (
<div className={cn(!showNode && "min-h-8 min-w-8")}>
<IconComponent
name={iconName}
className={iconClassName}
iconColor={iconColor}
/>
<div className="flex h-4 w-4 items-center justify-center">
{isLucideIcon ? (
<IconComponent strokeWidth={ICON_STROKE_WIDTH} name={iconName} />
) : (
<IconComponent name={iconName} iconColor={iconColor} />
)}
</div>
);
};

View file

@ -30,7 +30,6 @@ import useUpdateNodeCode from "../hooks/use-update-node-code";
import NodeDescription from "./components/NodeDescription";
import NodeName from "./components/NodeName";
import NodeOutputs from "./components/NodeOutputParameter/NodeOutputs";
import NodeStatus from "./components/NodeStatus";
import NodeUpdateComponent from "./components/NodeUpdateComponent";
import RenderInputParameters from "./components/RenderInputParameters";
import { NodeIcon } from "./components/nodeIcon";
@ -415,37 +414,31 @@ function GenericNode({
<div
data-testid={`${data.id}-main-node`}
className={cn(
"grid text-wrap p-4 leading-5",
"grid text-wrap leading-5",
showNode ? "border-b" : "relative",
hasDescription && "gap-3",
)}
>
<div
data-testid={"div-generic-node"}
className={
!showNode
? ""
: "generic-node-div-title justify-between rounded-t-lg"
}
className={cn(
"flex w-full flex-1 items-center justify-between gap-2 overflow-hidden px-4 py-3",
)}
>
<div
className={"generic-node-title-arrangement"}
className="flex-max-width items-center overflow-hidden"
data-testid="generic-node-title-arrangement"
>
<MemoizedNodeIcon
dataType={data.type}
showNode={showNode}
icon={data.node?.icon}
isGroup={!!data.node?.flow}
/>
<div className="generic-node-tooltip-div truncate">
<div className="ml-3 flex flex-1 overflow-hidden">
<MemoizedNodeName
display_name={data.node?.display_name}
nodeId={data.id}
selected={selected}
showNode={showNode}
validationStatus={validationStatus}
isOutdated={isOutdated}
beta={data.node?.beta || false}
editNameDescription={editNameDescription}
toggleEditNameDescription={toggleEditNameDescription}
@ -453,9 +446,9 @@ function GenericNode({
/>
</div>
</div>
<div data-testid={`${showNode ? "show" : "hide"}-node-content`}>
{!showNode && (
<>
{!showNode && (
<>
<div data-testid={`${showNode ? "show" : "hide"}-node-content`}>
<MemoizedRenderInputParameters
data={data}
types={types}
@ -474,9 +467,9 @@ function GenericNode({
isToolMode={isToolMode}
showHiddenOutputs={showHiddenOutputs}
/>
</>
)}
</div>
</div>
</>
)}
<MemoizedNodeStatus
data={data}
frozen={data.node?.frozen}
@ -493,8 +486,8 @@ function GenericNode({
getValidationStatus={getValidationStatus}
/>
</div>
{showNode && (
<div>
{showNode && (hasDescription || editNameDescription) && (
<div className="px-4 pb-3">
<MemoizedNodeDescription
description={data.node?.description}
mdClassName={"dark:prose-invert"}

View file

@ -1,5 +1,4 @@
import ForwardedIconComponent from "../../components/common/genericIconComponent";
import Xmark from "../../components/ui/xmark";
import { BuildStatus } from "../../constants/enums";
const useIconStatus = (buildStatus: BuildStatus | undefined) => {
@ -8,23 +7,16 @@ const useIconStatus = (buildStatus: BuildStatus | undefined) => {
const renderIconStatus = () => {
if (buildStatus === BuildStatus.BUILDING) {
return (
// <Loading
// data-testid="loading_icon"
// className="mr-1 text-medium-indigo"
// size={20}
// />
<></>
);
return <></>;
}
const iconConditions = [
{
condition: conditionError,
icon: (
<Xmark
isVisible={true}
className="h-4 w-4 fill-current stroke-2 text-destructive"
<ForwardedIconComponent
name="CircleAlert"
className="h-4 w-4 text-destructive"
/>
),
},

View file

@ -85,7 +85,7 @@ export function ContentBlockDisplay({
name={headerIcon}
className={cn(
"h-4 w-4",
state !== "partial" && "text-status-green",
state !== "partial" && "text-accent-emerald-foreground",
)}
strokeWidth={1.5}
/>

View file

@ -46,17 +46,13 @@ export default function DurationDisplay({
return (
<div
data-testid="duration-display"
className={`inline-flex items-center justify-between gap-1 rounded-[3px] px-2 text-sm ${
className={`inline-flex items-center justify-between gap-1.5 rounded-[3px] px-2 text-sm ${
duration !== undefined
? "bg-accent-emerald text-accent-emerald-foreground"
: "bg-muted text-muted-foreground"
? "text-accent-emerald-foreground"
: "text-muted-foreground"
}`}
>
{duration === undefined ? (
<Loading className="h-4 w-4" />
) : (
<ForwardedIconComponent name="check" className="h-4 w-4" />
)}
{duration === undefined && <Loading className="h-3 w-3" />}
<div className="w-fit">
<AnimatedNumber
value={secondsValue}
@ -65,7 +61,7 @@ export default function DurationDisplay({
bounce: 0,
duration: 300,
}}
className="text-xxs font-bold tabular-nums"
className="font-mono text-xxs font-bold tabular-nums"
/>
</div>
</div>

View file

@ -321,18 +321,6 @@
.generic-node-div {
@apply flex flex-col justify-center bg-background transition-all;
}
.generic-node-div-title {
@apply flex flex-1 items-center gap-2 overflow-hidden;
}
.generic-node-title-arrangement {
@apply flex-max-width items-center truncate;
}
.generic-node-icon {
@apply h-12 w-12 rounded;
}
.generic-node-tooltip-div {
@apply ml-2 flex w-full truncate;
}
.generic-node-validation-div {
@apply max-h-96 overflow-auto;
}
@ -1183,23 +1171,7 @@
}
.button-run-bg {
@apply flex h-7 w-7 cursor-pointer items-center justify-center rounded-sm bg-transparent p-0 hover:bg-muted hover:p-1;
}
.play-button-icon {
@apply h-4 w-4 transition-all group-hover/node:opacity-100;
}
.lucide-icon {
@apply h-5 w-5;
}
.bg-lucide-icon {
@apply flex h-8 w-8 items-center justify-center rounded-md bg-muted p-[6px];
}
.integration-icon {
@apply h-8 w-8 rounded-md;
@apply flex h-6 w-6 cursor-pointer items-center justify-center rounded-sm bg-transparent hover:bg-muted;
}
.show-node-icon {

View file

@ -37,7 +37,7 @@
--canvas: 240 5% 96%; /* hsl(240, 5%, 96%) */
--canvas-dot: 240 5% 65%; /* hsl(240, 5%, 65%) */
--accent-emerald: 149 80% 90%; /* hsl(149, 80%, 90%) */
--accent-emerald-foreground: 161 41% 30%; /* hsl(161, 41%, 30%) */
--accent-emerald-foreground: 161 94% 30%; /* hsl(161, 94%, 30%) */
--accent-emerald-hover: 152.4 76% 80.4%; /* hsl(152.4, 76%, 80.4%) */
--accent-indigo: 226 100% 94%; /* hsl(226, 100%, 94%) */
--accent-indigo-foreground: 243 75% 59%; /* hsl(243, 75%, 59%) */
@ -45,6 +45,9 @@
--accent-pink: 326, 78%, 95%; /* hsl(326, 78%, 95%) */
--accent-pink-foreground: 333 71% 51%; /* hsl(333, 71%, 51%) */
--accent-purple-foreground: 271 81% 56%;
--tooltip: 0 0% 0%; /* hsl(0, 0%, 0%) */
--tooltip-foreground: 0 0% 100%; /* hsl(0, 0%, 100%) */
@ -232,6 +235,7 @@
--accent-indigo-foreground: 234 89% 74%; /* hsl(234, 89%, 74%) */
--accent-pink: 336, 69%, 30%; /* hsl(336, 69%, 30%) */
--accent-pink-foreground: 329 86% 70%; /* hsl(329, 86%, 70%) */
--accent-purple-foreground: 270, 95%, 75%;
--accent-red-foreground: 0 91% 71%; /* hsl(0, 91%, 71%) */
--tooltip: 0 0% 100%; /* hsl(0, 0%, 100%) */

View file

@ -170,6 +170,7 @@ const config = {
"success-foreground": "var(--success-foreground)",
"accent-pink": "hsl(var(--accent-pink))",
"accent-pink-foreground": "hsl(var(--accent-pink-foreground))",
"accent-purple-foreground": "hsl(var(--accent-purple-foreground))",
"accent-red-foreground": "hsl(var(--accent-red-foreground))",
filter: {
foreground: "var(--filter-foreground)",

View file

@ -31,7 +31,7 @@ test(
await page
.getByTestId("dataURL")
.dragTo(page.locator('//*[@id="react-flow-id"]'), {
targetPosition: { x: 100, y: 100 },
targetPosition: { x: 50, y: 100 },
});
// Add Loop component
@ -44,7 +44,7 @@ test(
await page
.getByTestId("logicLoop")
.dragTo(page.locator('//*[@id="react-flow-id"]'), {
targetPosition: { x: 300, y: 100 },
targetPosition: { x: 280, y: 100 },
});
// Add Update Data component
@ -70,14 +70,14 @@ test(
await page
.getByTestId("processingData to Message")
.dragTo(page.locator('//*[@id="react-flow-id"]'), {
targetPosition: { x: 700, y: 100 },
targetPosition: { x: 720, y: 100 },
});
//This one is for testing the wrong loop message
await page
.getByTestId("processingData to Message")
.dragTo(page.locator('//*[@id="react-flow-id"]'), {
targetPosition: { x: 700, y: 400 },
targetPosition: { x: 720, y: 400 },
});
await page
@ -100,7 +100,7 @@ test(
await page
.getByTestId("outputsChat Output")
.dragTo(page.locator('//*[@id="react-flow-id"]'), {
targetPosition: { x: 900, y: 100 },
targetPosition: { x: 940, y: 100 },
});
await page.getByTestId("fit_view").click();

View file

@ -64,7 +64,7 @@ test(
expect(cellsCount).toBeGreaterThan(0);
await page.getByRole("gridcell").first().click();
await page.waitForTimeout(500);
await page.waitForTimeout(1000);
const isChecked = await page
.locator('input[data-ref="eInput"]')
@ -73,7 +73,7 @@ test(
if (!isChecked) {
await page.locator('input[data-ref="eInput"]').first().click();
await page.waitForTimeout(500);
await page.waitForTimeout(1000);
}
const isCheckedAgain = await page
.locator('input[data-ref="eInput"]')
@ -82,7 +82,7 @@ test(
if (isCheckedAgain) {
await page.locator('input[data-ref="eInput"]').first().click();
await page.waitForTimeout(500);
await page.waitForTimeout(1000);
}
const isCheckedAgainAgain = await page
@ -97,13 +97,13 @@ test(
.locator('input[data-ref="eInput"]')
.nth(rowsCount + 1)
.click();
await page.waitForTimeout(500);
await page.waitForTimeout(1000);
await page
.getByRole("gridcell")
.nth(cellsCount - 1)
.click();
await page.waitForTimeout(500);
await page.waitForTimeout(1000);
const isLastChecked = await page
.locator('input[data-ref="eInput"]')
@ -224,8 +224,9 @@ test(
}
// Verify tools are available
await page.waitForTimeout(3000);
await page.getByTestId("dropdown_str_tool").click();
await page.waitForTimeout(2000);
await page.waitForTimeout(3000);
const fetchOptionCount = await page.getByText("mcp_test_name").count();
expect(fetchOptionCount).toBeGreaterThan(0);

View file

@ -2,10 +2,10 @@ import { expect, Page, test } from "@playwright/test";
import { awaitBootstrapTest } from "../../utils/await-bootstrap-test";
async function toggleNodeState(page: Page, action: "minimize" | "expand") {
const expectedCount = action === "minimize" ? 0 : 1;
const expectedCount = action === "minimize" ? 1 : 0;
await page.getByTestId("more-options-modal").click();
await page.getByTestId(`${action}-button-modal`).click();
expect(await page.getByTestId("show-node-content").count()).toBe(
expect(await page.getByTestId("hide-node-content").count()).toBe(
expectedCount,
);
}
@ -36,7 +36,7 @@ test(
expect(await page.getByText("Toolset", { exact: true }).count()).toBe(0);
await page.getByTestId("title-Text Output").click();
expect(await page.getByTestId("show-node-content").count()).toBe(1);
expect(await page.getByTestId("hide-node-content").count()).toBe(0);
for (let i = 0; i < 5; i++) {
await toggleNodeState(page, "minimize");