Merge branch 'zustand/io/migration' of github.com:logspace-ai/langflow into zustand/io/migration
This commit is contained in:
commit
e120bfe869
44 changed files with 813 additions and 314 deletions
|
|
@ -88,10 +88,36 @@ export default function ParameterComponent({
|
|||
|
||||
const takeSnapshot = useFlowsManagerStore((state) => state.takeSnapshot);
|
||||
|
||||
const handleRefreshButtonPress = async (name, data) => {
|
||||
setIsLoading(true);
|
||||
try {
|
||||
let newTemplate = await handleUpdateValues(name, data);
|
||||
if (newTemplate) {
|
||||
setNode(data.id, (oldNode) => {
|
||||
let newNode = cloneDeep(oldNode);
|
||||
newNode.data = {
|
||||
...newNode.data,
|
||||
};
|
||||
newNode.data.node.template = newTemplate;
|
||||
return newNode;
|
||||
});
|
||||
}
|
||||
} catch (error) {
|
||||
let responseError = error as ResponseErrorTypeAPI;
|
||||
setErrorData({
|
||||
title: "Error while updating the Component",
|
||||
list: [responseError.response.data.detail.error ?? "Unknown error"],
|
||||
});
|
||||
}
|
||||
setIsLoading(false);
|
||||
renderTooltips();
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
async function fetchData() {
|
||||
if (
|
||||
data.node?.template[name]?.refresh &&
|
||||
(data.node?.template[name]?.real_time_refresh ||
|
||||
data.node?.template[name]?.refresh_button) &&
|
||||
// options can be undefined but not an empty array
|
||||
(data.node?.template[name]?.options?.length ?? 0) === 0
|
||||
) {
|
||||
|
|
@ -128,7 +154,8 @@ export default function ParameterComponent({
|
|||
takeSnapshot();
|
||||
}
|
||||
const shouldUpdate =
|
||||
data.node?.template[name].refresh &&
|
||||
data.node?.template[name].real_time_refresh &&
|
||||
!data.node?.template[name].refresh_button &&
|
||||
data.node!.template[name].value !== newValue;
|
||||
|
||||
data.node!.template[name].value = newValue; // necessary to enable ctrl+z inside the input
|
||||
|
|
@ -154,7 +181,7 @@ export default function ParameterComponent({
|
|||
...newNode.data,
|
||||
};
|
||||
|
||||
if (data.node?.template[name].refresh && newTemplate) {
|
||||
if (data.node?.template[name].real_time_refresh && newTemplate) {
|
||||
newNode.data.node.template = newTemplate;
|
||||
} else newNode.data.node.template[name].value = newValue;
|
||||
|
||||
|
|
@ -458,7 +485,7 @@ export default function ParameterComponent({
|
|||
}
|
||||
onChange={handleOnNewValue}
|
||||
/>
|
||||
{/* {data.node?.template[name].refresh && (
|
||||
{/* {data.node?.template[name].refresh_button && (
|
||||
<div className="w-1/6">
|
||||
<RefreshButton
|
||||
isLoading={isLoading}
|
||||
|
|
@ -466,26 +493,47 @@ export default function ParameterComponent({
|
|||
name={name}
|
||||
data={data}
|
||||
className="extra-side-bar-buttons ml-2 mt-1"
|
||||
handleUpdateValues={handleUpdateValues}
|
||||
handleUpdateValues={handleRefreshButtonPress}
|
||||
id={"refresh-button-" + name}
|
||||
/>
|
||||
</div>
|
||||
)} */}
|
||||
</div>
|
||||
) : data.node?.template[name].multiline ? (
|
||||
<TextAreaComponent
|
||||
disabled={disabled}
|
||||
value={data.node.template[name].value ?? ""}
|
||||
onChange={handleOnNewValue}
|
||||
id={"textarea-" + data.node.template[name].name}
|
||||
data-testid={"textarea-" + data.node.template[name].name}
|
||||
/>
|
||||
<div className="mt-2 flex w-full flex-col ">
|
||||
<div className="flex-grow">
|
||||
<TextAreaComponent
|
||||
disabled={disabled}
|
||||
value={data.node.template[name].value ?? ""}
|
||||
onChange={handleOnNewValue}
|
||||
id={"textarea-" + data.node.template[name].name}
|
||||
data-testid={"textarea-" + data.node.template[name].name}
|
||||
/>
|
||||
</div>
|
||||
{data.node?.template[name].refresh_button && (
|
||||
<div className="flex-grow">
|
||||
<RefreshButton
|
||||
isLoading={isLoading}
|
||||
disabled={disabled}
|
||||
name={name}
|
||||
data={data}
|
||||
button_text={
|
||||
data.node?.template[name].refresh_button_text ??
|
||||
"Refresh"
|
||||
}
|
||||
className="extra-side-bar-buttons mt-1"
|
||||
handleUpdateValues={handleRefreshButtonPress}
|
||||
id={"refresh-button-" + name}
|
||||
/>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
) : (
|
||||
<div className="mt-2 flex w-full items-center">
|
||||
<div
|
||||
className={
|
||||
"flex-grow " +
|
||||
(data.node?.template[name].refresh ? "w-5/6" : "")
|
||||
(data.node?.template[name].refresh_button ? "w-5/6" : "")
|
||||
}
|
||||
>
|
||||
<InputComponent
|
||||
|
|
@ -496,15 +544,19 @@ export default function ParameterComponent({
|
|||
onChange={handleOnNewValue}
|
||||
/>
|
||||
</div>
|
||||
{data.node?.template[name].refresh && (
|
||||
{data.node?.template[name].refresh_button && (
|
||||
<div className="w-1/6">
|
||||
<RefreshButton
|
||||
isLoading={isLoading}
|
||||
disabled={disabled}
|
||||
name={name}
|
||||
data={data}
|
||||
button_text={
|
||||
data.node?.template[name].refresh_button_text ??
|
||||
"Refresh"
|
||||
}
|
||||
className="extra-side-bar-buttons ml-2 mt-1"
|
||||
handleUpdateValues={handleUpdateValues}
|
||||
handleUpdateValues={handleRefreshButtonPress}
|
||||
id={"refresh-button-" + name}
|
||||
/>
|
||||
</div>
|
||||
|
|
@ -535,7 +587,7 @@ export default function ParameterComponent({
|
|||
) : left === true &&
|
||||
type === "str" &&
|
||||
(data.node?.template[name].options ||
|
||||
data.node?.template[name]?.refresh) ? (
|
||||
data.node?.template[name]?.real_time_refresh) ? (
|
||||
// TODO: Improve CSS
|
||||
<div className="mt-2 flex w-full items-center">
|
||||
<div className="w-5/6 flex-grow">
|
||||
|
|
@ -548,15 +600,18 @@ export default function ParameterComponent({
|
|||
id={"dropdown-" + name}
|
||||
/>
|
||||
</div>
|
||||
{data.node?.template[name].refresh && (
|
||||
{data.node?.template[name].refresh_button && (
|
||||
<div className="w-1/6">
|
||||
<RefreshButton
|
||||
isLoading={isLoading}
|
||||
disabled={disabled}
|
||||
name={name}
|
||||
data={data}
|
||||
button_text={
|
||||
data.node?.template[name].refresh_button_text ?? "Refresh"
|
||||
}
|
||||
className="extra-side-bar-buttons ml-2 mt-1"
|
||||
handleUpdateValues={handleUpdateValues}
|
||||
handleUpdateValues={handleRefreshButtonPress}
|
||||
id={"refresh-button-" + name}
|
||||
/>
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -1,51 +1,53 @@
|
|||
import dynamicIconImports from "lucide-react/dynamicIconImports";
|
||||
import { Suspense, forwardRef, lazy } from "react";
|
||||
import { Suspense, forwardRef, lazy, memo } from "react";
|
||||
import { IconComponentProps } from "../../types/components";
|
||||
import { nodeIconsLucide } from "../../utils/styleUtils";
|
||||
|
||||
const ForwardedIconComponent = forwardRef(
|
||||
(
|
||||
{
|
||||
name,
|
||||
className,
|
||||
iconColor,
|
||||
stroke,
|
||||
strokeWidth,
|
||||
id = "",
|
||||
}: IconComponentProps,
|
||||
ref
|
||||
) => {
|
||||
let TargetIcon = nodeIconsLucide[name];
|
||||
if (!TargetIcon) {
|
||||
// check if name exists in dynamicIconImports
|
||||
if (!dynamicIconImports[name]) {
|
||||
TargetIcon = nodeIconsLucide["unknown"];
|
||||
} else TargetIcon = lazy(dynamicIconImports[name]);
|
||||
}
|
||||
const ForwardedIconComponent = memo(
|
||||
forwardRef(
|
||||
(
|
||||
{
|
||||
name,
|
||||
className,
|
||||
iconColor,
|
||||
stroke,
|
||||
strokeWidth,
|
||||
id = "",
|
||||
}: IconComponentProps,
|
||||
ref
|
||||
) => {
|
||||
let TargetIcon = nodeIconsLucide[name];
|
||||
if (!TargetIcon) {
|
||||
// check if name exists in dynamicIconImports
|
||||
if (!dynamicIconImports[name]) {
|
||||
TargetIcon = nodeIconsLucide["unknown"];
|
||||
} else TargetIcon = lazy(dynamicIconImports[name]);
|
||||
}
|
||||
|
||||
const style = {
|
||||
strokeWidth: strokeWidth ?? 1.5,
|
||||
...(stroke && { stroke: stroke }),
|
||||
...(iconColor && { color: iconColor, stroke: stroke }),
|
||||
};
|
||||
const style = {
|
||||
strokeWidth: strokeWidth ?? 1.5,
|
||||
...(stroke && { stroke: stroke }),
|
||||
...(iconColor && { color: iconColor, stroke: stroke }),
|
||||
};
|
||||
|
||||
if (!TargetIcon) {
|
||||
return null; // Render nothing until the icon is loaded
|
||||
if (!TargetIcon) {
|
||||
return null; // Render nothing until the icon is loaded
|
||||
}
|
||||
const fallback = (
|
||||
<div style={{ background: "#ddd", width: 24, height: 24 }} />
|
||||
);
|
||||
return (
|
||||
<Suspense fallback={fallback}>
|
||||
<TargetIcon
|
||||
className={className}
|
||||
style={style}
|
||||
ref={ref}
|
||||
data-testid={id ? `${id}-${name}` : `icon-${name}`}
|
||||
/>
|
||||
</Suspense>
|
||||
);
|
||||
}
|
||||
const fallback = (
|
||||
<div style={{ background: "#ddd", width: 24, height: 24 }} />
|
||||
);
|
||||
return (
|
||||
<Suspense fallback={fallback}>
|
||||
<TargetIcon
|
||||
className={className}
|
||||
style={style}
|
||||
ref={ref}
|
||||
data-testid={id ? `${id}-${name}` : `icon-${name}`}
|
||||
/>
|
||||
</Suspense>
|
||||
);
|
||||
}
|
||||
)
|
||||
);
|
||||
|
||||
export default ForwardedIconComponent;
|
||||
|
|
|
|||
|
|
@ -7,6 +7,7 @@ function RefreshButton({
|
|||
isLoading,
|
||||
disabled,
|
||||
name,
|
||||
button_text,
|
||||
data,
|
||||
handleUpdateValues,
|
||||
className,
|
||||
|
|
@ -15,6 +16,7 @@ function RefreshButton({
|
|||
isLoading: boolean;
|
||||
disabled: boolean;
|
||||
name: string;
|
||||
button_text: string;
|
||||
data: NodeDataType;
|
||||
className?: string;
|
||||
handleUpdateValues: (name: string, data: NodeDataType) => void;
|
||||
|
|
@ -43,6 +45,7 @@ function RefreshButton({
|
|||
onClick={handleClick}
|
||||
id={id}
|
||||
>
|
||||
<span className="mr-1">{button_text}</span>
|
||||
<IconComponent
|
||||
name={isLoading ? "Loader2" : "RefreshCcw"}
|
||||
className={iconClassName}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
// src/constants/constants.ts
|
||||
|
||||
import { languageMap } from "../types/components";
|
||||
import { FlowType } from "../types/flow";
|
||||
|
||||
/**
|
||||
* invalid characters for flow name
|
||||
|
|
@ -739,4 +740,75 @@ export const PRIORITY_SIDEBAR_ORDER = [
|
|||
"helpers",
|
||||
"experimental",
|
||||
];
|
||||
/*
|
||||
Data ingestion
|
||||
Basic Prompting
|
||||
Chat com memória
|
||||
Working with data (file/website)
|
||||
API requests
|
||||
Vector Store
|
||||
Assistant
|
||||
*/
|
||||
|
||||
export const EXAMPLES_MOCK:FlowType[] = [
|
||||
{
|
||||
name: "Working with data",
|
||||
id: "Working with data Description",
|
||||
data: {
|
||||
nodes: [],
|
||||
edges: [],
|
||||
viewport: { zoom: 1, x: 1, y: 1 }
|
||||
},
|
||||
description: "This flow represents the first process in our application.",
|
||||
folder: STARTER_FOLDER_NAME,
|
||||
user_id: undefined,
|
||||
},
|
||||
{
|
||||
name: "Basic Prompting",
|
||||
id: "Basic Prompting Description",
|
||||
data: {
|
||||
nodes: [],
|
||||
edges: [],
|
||||
viewport: { zoom: 1, x: 1, y: 1 }
|
||||
},
|
||||
description: "This flow represents the first process in our application.",
|
||||
folder: STARTER_FOLDER_NAME,
|
||||
user_id: undefined,
|
||||
},
|
||||
{
|
||||
name: "Chat with memory",
|
||||
id: "Chat with memory Description",
|
||||
data: {
|
||||
nodes: [],
|
||||
edges: [],
|
||||
viewport: { zoom: 1, x: 1, y: 1 }
|
||||
},
|
||||
description: "This flow represents the first process in our application.",
|
||||
folder: STARTER_FOLDER_NAME,
|
||||
user_id: undefined,
|
||||
},
|
||||
{
|
||||
name: "API requests",
|
||||
id: "API requests Description",
|
||||
data: {
|
||||
nodes: [],
|
||||
edges: [],
|
||||
viewport: { zoom: 1, x: 1, y: 1 }
|
||||
},
|
||||
description: "This flow represents the first process in our application.",
|
||||
folder: STARTER_FOLDER_NAME,
|
||||
user_id: undefined,
|
||||
},
|
||||
{
|
||||
name: "Assistant",
|
||||
id: "Assistant Description",
|
||||
data: {
|
||||
nodes: [],
|
||||
edges: [],
|
||||
viewport: { zoom: 1, x: 1, y: 1 }
|
||||
},
|
||||
description: "This flow represents the first process in our application.",
|
||||
folder: STARTER_FOLDER_NAME,
|
||||
user_id: undefined,
|
||||
},
|
||||
];
|
||||
|
|
|
|||
|
|
@ -1,12 +1,11 @@
|
|||
import { cloneDeep } from "lodash";
|
||||
import { LinkIcon, SparklesIcon } from "lucide-react";
|
||||
import { useEffect, useMemo, useState } from "react";
|
||||
import ShadTooltip from "../../../../components/ShadTooltipComponent";
|
||||
import IconComponent from "../../../../components/genericIconComponent";
|
||||
import { Input } from "../../../../components/ui/input";
|
||||
import { Separator } from "../../../../components/ui/separator";
|
||||
import { UPLOAD_ERROR_ALERT } from "../../../../constants/alerts_constants";
|
||||
import { PRIORITY_SIDEBAR_ORDER } from "../../../../constants/constants";
|
||||
import ApiModal from "../../../../modals/ApiModal";
|
||||
import ExportModal from "../../../../modals/exportModal";
|
||||
import ShareModal from "../../../../modals/shareModal";
|
||||
import useAlertStore from "../../../../stores/alertStore";
|
||||
|
|
@ -268,37 +267,37 @@ export default function ExtraSidebar(): JSX.Element {
|
|||
<>
|
||||
{index === 0 && (
|
||||
<div className="pt-0.5">
|
||||
<div className="p-2 px-4 font-semibold" key={index}>
|
||||
Native
|
||||
<div className="p-2 px-4 font-semibold text-sm" key={index}>
|
||||
Native Components
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
{index === PRIORITY_SIDEBAR_ORDER.length - 1 && (
|
||||
<>
|
||||
<a target={"_blank"} href="https://langflow.store" className="components-disclosure-arrangement">
|
||||
<a
|
||||
target={"_blank"}
|
||||
href="https://langflow.store"
|
||||
className="components-disclosure-arrangement"
|
||||
>
|
||||
<div className="flex gap-4">
|
||||
{/* BUG ON THIS ICON */}
|
||||
<IconComponent
|
||||
<SparklesIcon
|
||||
strokeWidth={1.5}
|
||||
name="sparkles"
|
||||
className="text-primary"
|
||||
className="text-primary w-[22px]"
|
||||
/>
|
||||
|
||||
<span className="components-disclosure-title">
|
||||
Discover More
|
||||
</span>
|
||||
</div>
|
||||
<div className="components-disclosure-div">
|
||||
<div>
|
||||
<IconComponent
|
||||
name="link"
|
||||
className={`
|
||||
h-4 w-4 text-foreground`}
|
||||
/>
|
||||
<LinkIcon className="h-4 w-4 text-foreground" />
|
||||
</div>
|
||||
</div>
|
||||
</a>
|
||||
<div className="p-2 px-4 font-semibold" key={index}>
|
||||
Legacy
|
||||
<div className="p-2 px-4 font-semibold text-sm" key={index}>
|
||||
Legacy Components
|
||||
</div>
|
||||
</>
|
||||
)}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ import SidebarNav from "../../components/sidebarComponent";
|
|||
import { Button } from "../../components/ui/button";
|
||||
import { CONSOLE_ERROR_MSG } from "../../constants/alerts_constants";
|
||||
import {
|
||||
EXAMPLES_MOCK,
|
||||
MY_COLLECTION_DESC,
|
||||
USER_PROJECTS_HEADER,
|
||||
} from "../../constants/constants";
|
||||
|
|
@ -133,7 +134,7 @@ export default function HomePage(): JSX.Element {
|
|||
</BaseModal.Header>
|
||||
<BaseModal.Content>
|
||||
<div className="flex h-full w-full flex-wrap gap-3 overflow-auto p-4 custom-scroll">
|
||||
{examples.map((example, idx) => {
|
||||
{EXAMPLES_MOCK.map((example, idx) => {
|
||||
return <UndrawCardComponent key={idx} flow={example} />;
|
||||
})}
|
||||
<NewFlowCardComponent />
|
||||
|
|
|
|||
|
|
@ -69,7 +69,7 @@
|
|||
@apply flex h-full w-[14.5rem] flex-col overflow-hidden border-r scrollbar-hide;
|
||||
}
|
||||
.side-bar-search-div-placement {
|
||||
@apply relative mx-auto flex items-center py-5;
|
||||
@apply relative mx-auto flex items-center py-3;
|
||||
}
|
||||
.side-bar-components-icon {
|
||||
@apply h-6 w-4 text-ring;
|
||||
|
|
|
|||
|
|
@ -55,7 +55,9 @@ export type TemplateVariableType = {
|
|||
input_types?: Array<string>;
|
||||
display_name?: string;
|
||||
name?: string;
|
||||
refresh?: boolean;
|
||||
real_time_refresh?: boolean;
|
||||
refresh_button?: boolean;
|
||||
refresh_button_text?: string;
|
||||
[key: string]: any;
|
||||
};
|
||||
export type sendAllProps = {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue