From f0dcbcd54f551d5acb53cde80241b1b9ede6929b Mon Sep 17 00:00:00 2001 From: Rick Carlino Date: Tue, 10 Dec 2019 13:26:32 -0600 Subject: [PATCH] Fix most failures. TODO: Fix frontend/devices/__tests__/reducer_test.ts --- frontend/folders/actions.ts | 112 +----------------------------- frontend/folders/data_transfer.ts | 111 +++++++++++++++++++++++++++++ frontend/resources/reducer.ts | 40 ++++++----- 3 files changed, 134 insertions(+), 129 deletions(-) diff --git a/frontend/folders/actions.ts b/frontend/folders/actions.ts index a0bbf678c..37184bdbe 100644 --- a/frontend/folders/actions.ts +++ b/frontend/folders/actions.ts @@ -1,10 +1,9 @@ import { RootFolderNode as Tree, - FolderUnion, - RootFolderNode + FolderUnion } from "./constants"; import { cloneAndClimb } from "./climb"; -import { Color, TaggedResource, TaggedSequence } from "farmbot"; +import { Color } from "farmbot"; import { store } from "../redux/store"; import { initSave, destroy, edit, save, init } from "../api/crud"; import { Folder } from "farmbot/dist/resources/api_resources"; @@ -110,113 +109,6 @@ export const updateSearchTerm = (payload: string | undefined) => { }); }; -interface FolderSearchProps { - references: Record; - input: string; - root: RootFolderNode; -} - -const isSearchMatchSeq = - (searchTerm: string, s?: TaggedResource): s is TaggedSequence => { - if (s && s.kind == "Sequence") { - const name = s.body.name.toLowerCase(); - return name.includes(searchTerm); - } else { - return false; - } - }; - -const isSearchMatchFolder = (searchTerm: string, f: FolderUnion) => { - if (f.name.toLowerCase().includes(searchTerm)) { - return true; - } - - return false; -}; - -/** Given an input search term, returns folder IDs (number) and Sequence UUIDs - * that match */ -export const searchFoldersAndSequencesForTerm = (props: FolderSearchProps) => { - // A sequence is included if: - // * CASE 1: The name is a search match - // * CASE 2: The containing folder is a search match. - - // A folder is included if: - // * CASE 3: The name is a search match - // * CASE 4: It contains a sequence that is a match. - // * CASE 5: It has a child that has a search match. - - const searchTerm = props.input.toLowerCase(); - const sequenceSet = new Set(); - const folderSet = new Set(); - - props.root.folders.map(level1 => { - level1.content.map(level1Sequence => { // ========= Level 1 - if (isSearchMatchSeq(searchTerm, props.references[level1Sequence])) { - // CASE 1: - sequenceSet.add(level1Sequence); - // CASE 4: - folderSet.add(level1); - } - }); - - if (isSearchMatchFolder(searchTerm, level1)) { - // CASE 2 - level1.content.map(uuid => sequenceSet.add(uuid)); - // CASE 3 - folderSet.add(level1); - } - - level1.children.map(level2 => { // ================ LEVEL 2 - if (isSearchMatchFolder(searchTerm, level2)) { - // CASE 2 - level2.content.map(uuid => sequenceSet.add(uuid)); - // CASE 3 - folderSet.add(level2); - // CASE 5 - folderSet.add(level1); - } - - level2.content.map(level2Sequence => { - if (isSearchMatchSeq(searchTerm, props.references[level2Sequence])) { - // CASE 1: - sequenceSet.add(level2Sequence); - // CASE 4: - folderSet.add(level2); - // CASE 5 - folderSet.add(level1); - } - }); - level2.children.map(level3 => { // ============== LEVEL 3 - if (isSearchMatchFolder(searchTerm, level3)) { - // CASE 2 - level3.content.map(uuid => sequenceSet.add(uuid)); - // CASE 3 - folderSet.add(level3); - // CASE 5 - folderSet.add(level2); - // CASE 5 - folderSet.add(level1); - } - level3.content.map(level3Sequence => { - if (isSearchMatchSeq(searchTerm, props.references[level3Sequence])) { - // CASE 1: - sequenceSet.add(level3Sequence); - // CASE 3 - folderSet.add(level3); - // CASE 5 - folderSet.add(level2); - // CASE 5 - folderSet.add(level1); - } - }); - }); - }); - }); - - return Array.from(folderSet); -}; - export const toggleFolderOpenState = (id: number) => Promise .resolve(store.dispatch({ type: Actions.FOLDER_TOGGLE, payload: { id } })); diff --git a/frontend/folders/data_transfer.ts b/frontend/folders/data_transfer.ts index 1e0525c8d..a2129915a 100644 --- a/frontend/folders/data_transfer.ts +++ b/frontend/folders/data_transfer.ts @@ -4,8 +4,13 @@ import { FolderNodeTerminal, RootFolderNode, FolderMeta, + FolderUnion, } from "./constants"; import { sortBy } from "lodash"; +import { + TaggedResource, + TaggedSequence +} from "farmbot/dist/resources/tagged_resource"; type FoldersIndexedByParentId = Record; @@ -77,3 +82,109 @@ export const ingest: IngestFn = ({ folders, localMetaAttributes }) => { return output; }; +interface FolderSearchProps { + references: Record; + input: string; + root: RootFolderNode; +} + +const isSearchMatchSeq = + (searchTerm: string, s?: TaggedResource): s is TaggedSequence => { + if (s && s.kind == "Sequence") { + const name = s.body.name.toLowerCase(); + return name.includes(searchTerm); + } else { + return false; + } + }; + +const isSearchMatchFolder = (searchTerm: string, f: FolderUnion) => { + if (f.name.toLowerCase().includes(searchTerm)) { + return true; + } + + return false; +}; + +/** Given an input search term, returns folder IDs (number) and Sequence UUIDs + * that match */ +export const searchFoldersAndSequencesForTerm = (props: FolderSearchProps) => { + // A sequence is included if: + // * CASE 1: The name is a search match + // * CASE 2: The containing folder is a search match. + + // A folder is included if: + // * CASE 3: The name is a search match + // * CASE 4: It contains a sequence that is a match. + // * CASE 5: It has a child that has a search match. + + const searchTerm = props.input.toLowerCase(); + const sequenceSet = new Set(); + const folderSet = new Set(); + + props.root.folders.map(level1 => { + level1.content.map(level1Sequence => { // ========= Level 1 + if (isSearchMatchSeq(searchTerm, props.references[level1Sequence])) { + // CASE 1: + sequenceSet.add(level1Sequence); + // CASE 4: + folderSet.add(level1); + } + }); + + if (isSearchMatchFolder(searchTerm, level1)) { + // CASE 2 + level1.content.map(uuid => sequenceSet.add(uuid)); + // CASE 3 + folderSet.add(level1); + } + + level1.children.map(level2 => { // ================ LEVEL 2 + if (isSearchMatchFolder(searchTerm, level2)) { + // CASE 2 + level2.content.map(uuid => sequenceSet.add(uuid)); + // CASE 3 + folderSet.add(level2); + // CASE 5 + folderSet.add(level1); + } + + level2.content.map(level2Sequence => { + if (isSearchMatchSeq(searchTerm, props.references[level2Sequence])) { + // CASE 1: + sequenceSet.add(level2Sequence); + // CASE 4: + folderSet.add(level2); + // CASE 5 + folderSet.add(level1); + } + }); + level2.children.map(level3 => { // ============== LEVEL 3 + if (isSearchMatchFolder(searchTerm, level3)) { + // CASE 2 + level3.content.map(uuid => sequenceSet.add(uuid)); + // CASE 3 + folderSet.add(level3); + // CASE 5 + folderSet.add(level2); + // CASE 5 + folderSet.add(level1); + } + level3.content.map(level3Sequence => { + if (isSearchMatchSeq(searchTerm, props.references[level3Sequence])) { + // CASE 1: + sequenceSet.add(level3Sequence); + // CASE 3 + folderSet.add(level3); + // CASE 5 + folderSet.add(level2); + // CASE 5 + folderSet.add(level1); + } + }); + }); + }); + }); + + return Array.from(folderSet); +}; diff --git a/frontend/resources/reducer.ts b/frontend/resources/reducer.ts index 058b9a686..49ddddc4a 100644 --- a/frontend/resources/reducer.ts +++ b/frontend/resources/reducer.ts @@ -24,8 +24,10 @@ import { farmwareState } from "../farmware/reducer"; import { initialState as regimenState } from "../regimens/reducer"; import { initialState as sequenceState } from "../sequences/reducer"; import { initialState as alertState } from "../messages/reducer"; -// import { searchFoldersAndSequencesForTerm } from "../folders/actions"; -// import { ingest } from "../folders/data_transfer"; +import { + ingest, + searchFoldersAndSequencesForTerm +} from "../folders/data_transfer"; export const emptyState = (): RestResources => { return { @@ -185,22 +187,22 @@ export const resourceReducer = return s; }) - .add(Actions.FOLDER_SEARCH, (s/*, { payload }*/) => { - // s.index.sequenceFolders.searchTerm = payload; - // if (payload && payload.length > 2) { - // const folders = searchFoldersAndSequencesForTerm({ - // references: s.index.references, - // input: payload, - // root: s.index.sequenceFolders.folders - // }); - // const nextFolder = ingest({ - // localMetaAttributes: s.index.sequenceFolders.localMetaAttributes, - // folders - // }); - // s.index.sequenceFolders.filteredFolders = nextFolder; - // } else { - // s.index.sequenceFolders.filteredFolders = undefined; - // } - // reindexFolders(s.index); + .add(Actions.FOLDER_SEARCH, (s, { payload }) => { + s.index.sequenceFolders.searchTerm = payload; + if (payload && payload.length > 2) { + const folders = searchFoldersAndSequencesForTerm({ + references: s.index.references, + input: payload, + root: s.index.sequenceFolders.folders + }); + const nextFolder = ingest({ + localMetaAttributes: s.index.sequenceFolders.localMetaAttributes, + folders + }); + s.index.sequenceFolders.filteredFolders = nextFolder; + } else { + s.index.sequenceFolders.filteredFolders = undefined; + } + reindexFolders(s.index); return s; });