From dbd2bd9375cd8e34aea0947cfdc6fe2ba7f9ba80 Mon Sep 17 00:00:00 2001 From: anovazzi1 Date: Mon, 20 Jan 2025 22:47:19 -0300 Subject: [PATCH] fix: update LANGFLOW_COMPONENTS_PATH env variable behavior (#5700) * Refactor directory_reader.py to simplify file filtering logic * Refactor flowSidebarComponent to filter out bundles and custom components in CategoryGroup * [autofix.ci] apply automated fixes * refactor: Improve file filtering in DirectoryReader This commit improves the file filtering logic in the DirectoryReader class. Previously, it only excluded files that started with "__" and included all files that were not in a "deactivated" directory. Now, it also considers the depth of the file relative to the safe path. Only files that are one or two levels deep are included in the file list. --------- Co-authored-by: autofix-ci[bot] <114827586+autofix-ci[bot]@users.noreply.github.com> Co-authored-by: Gabriel Luiz Freitas Almeida --- .../directory_reader/directory_reader.py | 13 +++-- .../components/categoryGroup/index.tsx | 53 +++++++++++++----- .../components/flowSidebarComponent/index.tsx | 55 ++++++------------- 3 files changed, 63 insertions(+), 58 deletions(-) diff --git a/src/backend/base/langflow/custom/directory_reader/directory_reader.py b/src/backend/base/langflow/custom/directory_reader/directory_reader.py index 81ac913f5..fb0388059 100644 --- a/src/backend/base/langflow/custom/directory_reader/directory_reader.py +++ b/src/backend/base/langflow/custom/directory_reader/directory_reader.py @@ -9,6 +9,8 @@ from loguru import logger from langflow.custom import Component +MAX_DEPTH = 2 + class CustomComponentPathValueError(ValueError): pass @@ -135,12 +137,11 @@ class DirectoryReader: if "deactivated" in file_path.parent.name: continue - # The other condtion is that it should be - # in the safe_path/[folder]/[file].py format - # any folders below [folder] will be ignored - # basically the parent folder of the file should be a - # folder in the safe_path - if file_path.is_file() and file_path.parent.parent == safe_path_obj and not file_path.name.startswith("__"): + # Calculate the depth of the file relative to the safe path + relative_depth = len(file_path.relative_to(safe_path_obj).parts) + + # Only include files that are one or two levels deep + if relative_depth <= MAX_DEPTH and file_path.is_file() and not file_path.name.startswith("__"): file_list.append(str(file_path)) return file_list diff --git a/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/components/categoryGroup/index.tsx b/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/components/categoryGroup/index.tsx index 3756e37bf..2e54e274b 100644 --- a/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/components/categoryGroup/index.tsx +++ b/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/components/categoryGroup/index.tsx @@ -3,6 +3,7 @@ import { SidebarGroupContent, SidebarMenu, } from "@/components/ui/sidebar"; +import { SIDEBAR_BUNDLES } from "@/utils/styleUtils"; import { memo } from "react"; import { CategoryGroupProps } from "../../types"; import { CategoryDisclosure } from "../categoryDisclouse"; @@ -23,20 +24,42 @@ export const CategoryGroup = memo(function CategoryGroup({ - {CATEGORIES.toSorted( - (a, b) => - (search !== "" ? sortedCategories : CATEGORIES).findIndex( - (value) => value === a.name, - ) - - (search !== "" ? sortedCategories : CATEGORIES).findIndex( - (value) => value === b.name, - ), - ).map( - (item) => - dataFilter[item.name] && - Object.keys(dataFilter[item.name]).length > 0 && ( + {Object.entries(dataFilter) + .filter( + ([categoryName, items]) => + // filter out bundles + !SIDEBAR_BUNDLES.some((cat) => cat.name === categoryName) && + categoryName !== "custom_component" && + Object.keys(items).length > 0, + ) + .sort(([aName], [bName]) => { + const categoryList = + search !== "" + ? sortedCategories + : CATEGORIES.map((c) => c.name); + const aIndex = categoryList.indexOf(aName); + const bIndex = categoryList.indexOf(bName); + + // If neither is in CATEGORIES, keep their relative order + if (aIndex === -1 && bIndex === -1) return 0; + // If only a is not in CATEGORIES, put it after b + if (aIndex === -1) return 1; + // If only b is not in CATEGORIES, put it after a + if (bIndex === -1) return -1; + // If both are in CATEGORIES, sort by their index + return aIndex - bIndex; + }) + .map(([categoryName]) => { + const item = CATEGORIES.find( + (cat) => cat.name === categoryName, + ) ?? { + name: categoryName, + icon: "folder", + display_name: categoryName, + }; + return ( - ), - )} + ); + })} diff --git a/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/index.tsx b/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/index.tsx index 32e41fb34..857430ee8 100644 --- a/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/index.tsx +++ b/src/frontend/src/pages/FlowPage/components/flowSidebarComponent/index.tsx @@ -120,19 +120,12 @@ export function FlowSidebarComponent() { const sortedCategories = useMemo(() => { if (!searchResults || !searchFilteredData) return []; - return Object.keys(searchFilteredData) - .filter( - (category) => - Object.keys(searchFilteredData[category]).length > 0 && - (CATEGORIES.find((c) => c.name === category) || - BUNDLES.find((b) => b.name === category)), - ) - .toSorted((a, b) => - searchResults.fuseCategories.indexOf(b) < - searchResults.fuseCategories.indexOf(a) - ? 1 - : -1, - ); + return Object.keys(searchFilteredData).toSorted((a, b) => + searchResults.fuseCategories.indexOf(b) < + searchResults.fuseCategories.indexOf(a) + ? 1 + : -1, + ); }, [searchResults, searchFilteredData, CATEGORIES, BUNDLES]); const finalFilteredData = useMemo(() => { @@ -305,16 +298,6 @@ export function FlowSidebarComponent() { [dataFilter], ); - const hasCategoryItems = useMemo( - () => - CATEGORIES.some( - (item) => - dataFilter[item.name] && - Object.keys(dataFilter[item.name]).length > 0, - ), - [dataFilter], - ); - return ( {hasResults ? ( <> - {hasCategoryItems && ( - - )} + {hasBundleItems && (