Fix Application Crash with Multiple Nested Dict Components in Flow (#2011)

* ♻️ (dictComponent): improve value change detection logic
🐛 (parameterComponent): remove unnecessary console.log statement

* ♻️ (frontend): remove redundant comments and clean up code formatting

♻️ (editNodeModal): refactor to use nodeId instead of passing data directly

* ♻️ (editNodeModal): refactor to use data prop instead of nodeId for better data handling
♻️ (nodeToolbarComponent): refactor to improve code readability and consistency
This commit is contained in:
Cristhian Zanforlin Lousa 2024-05-29 23:26:12 -03:00 • committed by GitHub
commit fb018eda10
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
5 changed files with 29 additions and 34 deletions

View file

@ -841,9 +841,7 @@ export default function CodeTabsComponent({
node.data.node!.template[ node.data.node!.template[
templateField templateField
].value?.toString() === "{}" ].value?.toString() === "{}"
? { ? {}
// yourkey: "value",
}
: node.data.node! : node.data.node!
.template[ .template[
templateField templateField

View file

@ -18,16 +18,13 @@ export default function DictComponent({
} }
}, [disabled]); }, [disabled]);
useEffect(() => {
if (value) onChange(value);
}, [value]);
const ref = useRef(value); const ref = useRef(value);
return ( return (
<div <div
className={classNames( className={classNames(
value.length > 1 && editNode ? "my-1" : "", value.length > 1 && editNode ? "my-1" : "",
"flex flex-col gap-3" "flex flex-col gap-3",
)} )}
> >
{ {

View file

@ -89,7 +89,7 @@ export default function ParameterComponent({
setNode, setNode,
renderTooltips, renderTooltips,
isLoading, isLoading,
setIsLoading setIsLoading,
); );
const { handleNodeClass: handleNodeClassHook } = useHandleNodeClass( const { handleNodeClass: handleNodeClassHook } = useHandleNodeClass(
@ -98,7 +98,7 @@ export default function ParameterComponent({
takeSnapshot, takeSnapshot,
setNode, setNode,
updateNodeInternals, updateNodeInternals,
renderTooltips renderTooltips,
); );
const { handleRefreshButtonPress: handleRefreshButtonPressHook } = const { handleRefreshButtonPress: handleRefreshButtonPressHook } =
@ -107,7 +107,7 @@ export default function ParameterComponent({
let disabled = let disabled =
edges.some( edges.some(
(edge) => (edge) =>
edge.targetHandle === scapedJSONStringfy(proxy ? { ...id, proxy } : id) edge.targetHandle === scapedJSONStringfy(proxy ? { ...id, proxy } : id),
) ?? false; ) ?? false;
const handleRefreshButtonPress = async (name, data) => { const handleRefreshButtonPress = async (name, data) => {
@ -120,12 +120,12 @@ export default function ParameterComponent({
handleUpdateValues, handleUpdateValues,
setNode, setNode,
renderTooltips, renderTooltips,
setIsLoading setIsLoading,
); );
const handleOnNewValue = async ( const handleOnNewValue = async (
newValue: string | string[] | boolean | Object[], newValue: string | string[] | boolean | Object[],
skipSnapshot: boolean | undefined = false skipSnapshot: boolean | undefined = false,
): Promise<void> => { ): Promise<void> => {
handleOnNewValueHook(newValue, skipSnapshot); handleOnNewValueHook(newValue, skipSnapshot);
}; };
@ -207,7 +207,7 @@ export default function ParameterComponent({
className={classNames( className={classNames(
left ? "my-12 -ml-0.5 " : " my-12 -mr-0.5 ", left ? "my-12 -ml-0.5 " : " my-12 -mr-0.5 ",
"h-3 w-3 rounded-full border-2 bg-background", "h-3 w-3 rounded-full border-2 bg-background",
!showNode ? "mt-0" : "" !showNode ? "mt-0" : "",
)} )}
style={{ style={{
borderColor: color ?? nodeColors.unknown, borderColor: color ?? nodeColors.unknown,
@ -296,7 +296,7 @@ export default function ParameterComponent({
} }
className={classNames( className={classNames(
left ? "-ml-0.5" : "-mr-0.5", left ? "-ml-0.5" : "-mr-0.5",
"h-3 w-3 rounded-full border-2 bg-background" "h-3 w-3 rounded-full border-2 bg-background",
)} )}
style={{ borderColor: color ?? nodeColors.unknown }} style={{ borderColor: color ?? nodeColors.unknown }}
onClick={() => setFilterEdge(groupedEdge.current)} onClick={() => setFilterEdge(groupedEdge.current)}
@ -547,9 +547,7 @@ export default function ParameterComponent({
value={ value={
!data.node!.template[name]?.value || !data.node!.template[name]?.value ||
data.node!.template[name]?.value?.toString() === "{}" data.node!.template[name]?.value?.toString() === "{}"
? { ? {}
// yourkey: "value",
}
: data.node!.template[name]?.value : data.node!.template[name]?.value
} }
onChange={handleOnNewValue} onChange={handleOnNewValue}

View file

@ -43,19 +43,23 @@ import BaseModal from "../baseModal";
const EditNodeModal = forwardRef( const EditNodeModal = forwardRef(
( (
{ {
data,
nodeLength, nodeLength,
open, open,
setOpen, setOpen,
data,
}: { }: {
data: NodeDataType;
nodeLength: number; nodeLength: number;
open: boolean; open: boolean;
setOpen: (open: boolean) => void; setOpen: (open: boolean) => void;
data: NodeDataType;
}, },
ref, ref,
) => { ) => {
const [myData, setMyData] = useState(data); const nodes = useFlowStore((state) => state.nodes);
const dataFromStore = nodes.find((node) => node.id === node.id)?.data;
const [myData, setMyData] = useState(dataFromStore ?? data);
const edges = useFlowStore((state) => state.edges); const edges = useFlowStore((state) => state.edges);
const setNode = useFlowStore((state) => state.setNode); const setNode = useFlowStore((state) => state.setNode);
@ -297,9 +301,7 @@ const EditNodeModal = forwardRef(
myData.node!.template[ myData.node!.template[
templateParam templateParam
]?.value?.toString() === "{}" ]?.value?.toString() === "{}"
? { ? {}
// yourkey: "value",
}
: myData.node!.template[templateParam] : myData.node!.template[templateParam]
.value .value
} }

View file

@ -58,7 +58,7 @@ export default function NodeToolbarComponent({
data.node.template[templateField].type === "Any" || data.node.template[templateField].type === "Any" ||
data.node.template[templateField].type === "int" || data.node.template[templateField].type === "int" ||
data.node.template[templateField].type === "dict" || data.node.template[templateField].type === "dict" ||
data.node.template[templateField].type === "NestedDict") data.node.template[templateField].type === "NestedDict"),
).length; ).length;
const templates = useTypesStore((state) => state.templates); const templates = useTypesStore((state) => state.templates);
const hasStore = useStoreStore((state) => state.hasStore); const hasStore = useStoreStore((state) => state.hasStore);
@ -85,7 +85,7 @@ export default function NodeToolbarComponent({
const [showconfirmShare, setShowconfirmShare] = useState(false); const [showconfirmShare, setShowconfirmShare] = useState(false);
const [showOverrideModal, setShowOverrideModal] = useState(false); const [showOverrideModal, setShowOverrideModal] = useState(false);
const [flowComponent, setFlowComponent] = useState<FlowType>( const [flowComponent, setFlowComponent] = useState<FlowType>(
createFlowComponent(cloneDeep(data), version) createFlowComponent(cloneDeep(data), version),
); );
const openInNewTab = (url) => { const openInNewTab = (url) => {
@ -100,7 +100,7 @@ export default function NodeToolbarComponent({
const updateNodeInternals = useUpdateNodeInternals(); const updateNodeInternals = useUpdateNodeInternals();
const setLastCopiedSelection = useFlowStore( const setLastCopiedSelection = useFlowStore(
(state) => state.setLastCopiedSelection (state) => state.setLastCopiedSelection,
); );
const setSuccessData = useAlertStore((state) => state.setSuccessData); const setSuccessData = useAlertStore((state) => state.setSuccessData);
@ -150,7 +150,7 @@ export default function NodeToolbarComponent({
nodes, nodes,
edges, edges,
setNodes, setNodes,
setEdges setEdges,
); );
break; break;
case "override": case "override":
@ -174,7 +174,7 @@ export default function NodeToolbarComponent({
y: 10, y: 10,
paneX: nodes.find((node) => node.id === data.id)?.position.x, paneX: nodes.find((node) => node.id === data.id)?.position.x,
paneY: nodes.find((node) => node.id === data.id)?.position.y, paneY: nodes.find((node) => node.id === data.id)?.position.y,
} },
); );
break; break;
case "update": case "update":
@ -212,13 +212,13 @@ export default function NodeToolbarComponent({
}; };
const isSaved = flows.some((flow) => const isSaved = flows.some((flow) =>
Object.values(flow).includes(data.node?.display_name!) Object.values(flow).includes(data.node?.display_name!),
); );
const setNode = useFlowStore((state) => state.setNode); const setNode = useFlowStore((state) => state.setNode);
const handleOnNewValue = ( const handleOnNewValue = (
newValue: string | string[] | boolean | Object[] newValue: string | string[] | boolean | Object[],
): void => { ): void => {
if (data.node!.template[name].value !== newValue) { if (data.node!.template[name].value !== newValue) {
takeSnapshot(); takeSnapshot();
@ -401,7 +401,7 @@ export default function NodeToolbarComponent({
data-testid="save-button-modal" data-testid="save-button-modal"
className={classNames( className={classNames(
"relative -ml-px inline-flex items-center bg-background px-2 py-2 text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10", "relative -ml-px inline-flex items-center bg-background px-2 py-2 text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10",
hasCode ? " " : " rounded-l-md " hasCode ? " " : " rounded-l-md ",
)} )}
onClick={(event) => { onClick={(event) => {
event.preventDefault(); event.preventDefault();
@ -419,7 +419,7 @@ export default function NodeToolbarComponent({
<button <button
data-testid="duplicate-button-modal" data-testid="duplicate-button-modal"
className={classNames( className={classNames(
"relative -ml-px inline-flex items-center bg-background px-2 py-2 text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10" "relative -ml-px inline-flex items-center bg-background px-2 py-2 text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10",
)} )}
onClick={(event) => { onClick={(event) => {
event.preventDefault(); event.preventDefault();
@ -467,7 +467,7 @@ export default function NodeToolbarComponent({
<div <div
data-testid="more-options-modal" data-testid="more-options-modal"
className={classNames( className={classNames(
"relative -ml-px inline-flex h-8 w-[31px] items-center rounded-r-md bg-background text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10" "relative -ml-px inline-flex h-8 w-[31px] items-center rounded-r-md bg-background text-foreground shadow-md ring-1 ring-inset ring-ring transition-all duration-500 ease-in-out hover:bg-muted focus:z-10",
)} )}
> >
<IconComponent <IconComponent