diff --git a/apps/roam/src/components/DiscourseContextOverlay.tsx b/apps/roam/src/components/DiscourseContextOverlay.tsx index f4e83691d..8ef2ede56 100644 --- a/apps/roam/src/components/DiscourseContextOverlay.tsx +++ b/apps/roam/src/components/DiscourseContextOverlay.tsx @@ -11,12 +11,10 @@ import ReactDOM from "react-dom"; import { ContextContent } from "./DiscourseContext"; import useInViewport from "react-in-viewport/dist/es/lib/useInViewport"; import normalizePageTitle from "roamjs-components/queries/normalizePageTitle"; -import { USE_STORED_RELATIONS } from "~/data/userSettings"; -import { getSetting } from "~/utils/extensionSettings"; import deriveDiscourseNodeAttribute from "~/utils/deriveDiscourseNodeAttribute"; -import getSettingValueFromTree from "roamjs-components/util/getSettingValueFromTree"; -import getBasicTreeByParentUid from "roamjs-components/queries/getBasicTreeByParentUid"; -import getSubTree from "roamjs-components/util/getSubTree"; +import { getDiscourseNodeSetting } from "~/components/settings/utils/accessors"; +import { DISCOURSE_NODE_KEYS } from "~/components/settings/utils/settingKeys"; +import { getStoredRelationsEnabled } from "~/utils/storedRelations"; import nanoid from "nanoid"; import getPageUidByPageTitle from "roamjs-components/queries/getPageUidByPageTitle"; import getDiscourseContextResults from "~/utils/getDiscourseContextResults"; @@ -190,11 +188,10 @@ const useDiscourseContext = (uid: string, tag: string) => { ).length, ) .reduce((acc, cur) => acc + cur, 0); - const attribute = getSettingValueFromTree({ - tree: getBasicTreeByParentUid(discourseNode.type), - key: "Overlay", - defaultValue: "Overlay", - }); + const attribute = + getDiscourseNodeSetting(discourseNode.type, [ + DISCOURSE_NODE_KEYS.overlay, + ]) || "Overlay"; return deriveDiscourseNodeAttribute({ uid: uid, attribute, @@ -203,17 +200,11 @@ const useDiscourseContext = (uid: string, tag: string) => { setRefs(refs); setScore(score); - const nodeType = discourseNode.type; - const attributeNode = getSubTree({ - tree: getBasicTreeByParentUid(nodeType || ""), - key: "Attributes", - }); - const scoreFormula = attributeNode?.children - ? getSettingValueFromTree({ - tree: attributeNode.children, - key: attribute, - }) - : ""; + const scoreFormula = + getDiscourseNodeSetting(discourseNode.type, [ + DISCOURSE_NODE_KEYS.attributes, + attribute, + ]) ?? ""; if (scoreFormula === "" && score !== numResults) { internalError({ error: "DiscourseContext: Score does not match Num relations", @@ -222,7 +213,7 @@ const useDiscourseContext = (uid: string, tag: string) => { score, numResults, ignoreCache, - reified: getSetting(USE_STORED_RELATIONS), + reified: getStoredRelationsEnabled(), }, }); } diff --git a/apps/roam/src/components/DiscourseFloatingMenu.tsx b/apps/roam/src/components/DiscourseFloatingMenu.tsx index 07f71b694..3a7e337b9 100644 --- a/apps/roam/src/components/DiscourseFloatingMenu.tsx +++ b/apps/roam/src/components/DiscourseFloatingMenu.tsx @@ -13,6 +13,8 @@ import { import { FeedbackWidget } from "./BirdEatsBugs"; import { render as renderSettings } from "~/components/settings/Settings"; import posthog from "posthog-js"; +import { getPersonalSetting } from "./settings/utils/accessors"; +import { PERSONAL_KEYS } from "./settings/utils/settingKeys"; type DiscourseFloatingMenuProps = { // CSS placement class @@ -128,7 +130,7 @@ export const installDiscourseFloatingMenu = ( floatingMenuAnchor.id = ANCHOR_ID; document.getElementById("app")?.appendChild(floatingMenuAnchor); } - if (onLoadArgs.extensionAPI.settings.get("hide-feedback-button") as boolean) { + if (getPersonalSetting([PERSONAL_KEYS.hideFeedbackButton])) { floatingMenuAnchor.classList.add("hidden"); } ReactDOM.render( diff --git a/apps/roam/src/components/DiscourseNodeMenu.tsx b/apps/roam/src/components/DiscourseNodeMenu.tsx index f458e80a7..c7f2e2b96 100644 --- a/apps/roam/src/components/DiscourseNodeMenu.tsx +++ b/apps/roam/src/components/DiscourseNodeMenu.tsx @@ -27,7 +27,11 @@ import { getNewDiscourseNodeText } from "~/utils/formatUtils"; import { OnloadArgs } from "roamjs-components/types"; import { formatHexColor } from "./settings/DiscourseNodeCanvasSettings"; import posthog from "posthog-js"; -import { setPersonalSetting } from "~/components/settings/utils/accessors"; +import { + getPersonalSetting, + setPersonalSetting, +} from "~/components/settings/utils/accessors"; +import { PERSONAL_KEYS } from "~/components/settings/utils/settingKeys"; type Props = { textarea?: HTMLTextAreaElement; @@ -423,9 +427,12 @@ export const NodeMenuTriggerComponent = ({ const [isActive, setIsActive] = useState(false); const [comboKey, setComboKey] = useState( () => - (extensionAPI.settings.get( - "personal-node-menu-trigger", - ) as IKeyCombo) || { modifiers: 0, key: "" }, + getPersonalSetting([ + PERSONAL_KEYS.personalNodeMenuTrigger, + ]) || { + modifiers: 0, + key: "", + }, ); const handleKeyDown = useCallback( @@ -438,7 +445,7 @@ export const NodeMenuTriggerComponent = ({ const combo = { key: comboObj.key, modifiers: comboObj.modifiers }; setComboKey(combo); void extensionAPI.settings.set("personal-node-menu-trigger", combo); - setPersonalSetting(["Personal node menu trigger"], combo); + setPersonalSetting([PERSONAL_KEYS.personalNodeMenuTrigger], combo); }, [extensionAPI], ); @@ -460,7 +467,7 @@ export const NodeMenuTriggerComponent = ({ onClick={() => { setComboKey({ modifiers: 0, key: "" }); void extensionAPI.settings.set("personal-node-menu-trigger", ""); - setPersonalSetting(["Personal node menu trigger"], ""); + setPersonalSetting([PERSONAL_KEYS.personalNodeMenuTrigger], ""); }} minimal /> diff --git a/apps/roam/src/components/DiscourseNodeSearchMenu.tsx b/apps/roam/src/components/DiscourseNodeSearchMenu.tsx index abef73705..03fdfc82d 100644 --- a/apps/roam/src/components/DiscourseNodeSearchMenu.tsx +++ b/apps/roam/src/components/DiscourseNodeSearchMenu.tsx @@ -24,9 +24,12 @@ import { OnloadArgs } from "roamjs-components/types"; import getDiscourseNodes, { DiscourseNode } from "~/utils/getDiscourseNodes"; import getDiscourseNodeFormatExpression from "~/utils/getDiscourseNodeFormatExpression"; import { Result } from "~/utils/types"; -import { getSetting } from "~/utils/extensionSettings"; import MiniSearch from "minisearch"; -import { setPersonalSetting } from "~/components/settings/utils/accessors"; +import { + getPersonalSetting, + setPersonalSetting, +} from "~/components/settings/utils/accessors"; +import { PERSONAL_KEYS } from "~/components/settings/utils/settingKeys"; type Props = { textarea: HTMLTextAreaElement; @@ -711,7 +714,7 @@ export const NodeSearchMenuTriggerSetting = ({ }) => { const extensionAPI = onloadArgs.extensionAPI; const [nodeSearchTrigger, setNodeSearchTrigger] = useState( - getSetting("node-search-trigger", "@"), + getPersonalSetting([PERSONAL_KEYS.nodeSearchMenuTrigger]) ?? "@", ); const handleNodeSearchTriggerChange = ( @@ -726,7 +729,7 @@ export const NodeSearchMenuTriggerSetting = ({ setNodeSearchTrigger(trigger); void extensionAPI.settings.set("node-search-trigger", trigger); - setPersonalSetting(["Node search menu trigger"], trigger); + setPersonalSetting([PERSONAL_KEYS.nodeSearchMenuTrigger], trigger); }; return ( + getLeftSidebarSettings(discourseConfigRef.tree); + const parseReference = (text: string) => { const extracted = extractRef(text); if (text.startsWith("((") && text.endsWith("))")) { @@ -95,12 +117,18 @@ const toggleFoldedState = ({ setIsOpen, folded, parentUid, + isGlobal, + sectionIndex, }: { isOpen: boolean; setIsOpen: Dispatch>; folded: { uid?: string; value: boolean }; parentUid: string; + isGlobal?: boolean; + sectionIndex?: number; }) => { + const newFolded = !isOpen; + if (isOpen) { setIsOpen(false); if (folded.uid) { @@ -118,6 +146,24 @@ const toggleFoldedState = ({ folded.uid = newUid; folded.value = true; } + + if (isGlobal) { + setGlobalSetting( + [ + GLOBAL_KEYS.leftSidebar, + LEFT_SIDEBAR_KEYS.settings, + LEFT_SIDEBAR_SETTINGS_KEYS.folded, + ], + newFolded, + ); + } else if (sectionIndex !== undefined) { + const sections = + getPersonalSetting([PERSONAL_KEYS.leftSidebar]) || []; + if (sections[sectionIndex]) { + sections[sectionIndex].Settings.Folded = newFolded; + setPersonalSetting([PERSONAL_KEYS.leftSidebar], sections); + } + } }; const SectionChildren = ({ @@ -160,8 +206,10 @@ const SectionChildren = ({ const PersonalSectionItem = ({ section, + sectionIndex, }: { section: LeftSidebarPersonalSectionConfig; + sectionIndex: number; }) => { const titleRef = parseReference(section.text); const blockText = useMemo( @@ -182,6 +230,7 @@ const PersonalSectionItem = ({ setIsOpen, folded: section.settings.folded, parentUid: section.settings.uid || "", + sectionIndex, }); }; @@ -226,9 +275,9 @@ const PersonalSections = ({ config }: { config: LeftSidebarConfig }) => { return (
- {sections.map((section) => ( + {sections.map((section, index) => (
- +
))}
@@ -253,6 +302,7 @@ const GlobalSection = ({ config }: { config: LeftSidebarConfig["global"] }) => { setIsOpen, folded: config.settings.folded, parentUid: config.settings.uid, + isGlobal: true, }); }} > @@ -276,22 +326,61 @@ const GlobalSection = ({ config }: { config: LeftSidebarConfig["global"] }) => { ); }; +// TODO(ENG-1471): Remove old-system merge when migration complete — just use accessor values directly. +// See mergeGlobalSectionWithAccessor/mergePersonalSectionsWithAccessor for why the merge exists. +const buildConfig = (): LeftSidebarConfig => { + // Read VALUES from accessor (handles flag routing + mismatch detection) + const globalValues = getGlobalSetting([ + GLOBAL_KEYS.leftSidebar, + ]); + const personalValues = getPersonalSetting([ + PERSONAL_KEYS.leftSidebar, + ]); + + // Read UIDs from old system (needed for fold CRUD during dual-write) + const oldConfig = getCurrentLeftSidebarConfig(); + + return { + uid: oldConfig.uid, + favoritesMigrated: oldConfig.favoritesMigrated, + sidebarMigrated: oldConfig.sidebarMigrated, + global: mergeGlobalSectionWithAccessor(oldConfig.global, globalValues), + personal: { + uid: oldConfig.personal.uid, + sections: mergePersonalSectionsWithAccessor( + oldConfig.personal.sections, + personalValues, + ), + }, + allPersonalSections: oldConfig.allPersonalSections, + }; +}; + export const useConfig = () => { - const [config, setConfig] = useState( - () => getFormattedConfigTree().leftSidebar, - ); + const [config, setConfig] = useState(() => buildConfig()); useEffect(() => { const handleUpdate = () => { - setConfig(getFormattedConfigTree().leftSidebar); + setConfig(buildConfig()); }; - const unsubscribe = subscribe(handleUpdate); + const unsubGlobal = onSettingChange( + settingKeys.globalLeftSidebar, + handleUpdate, + ); + const unsubPersonal = onSettingChange( + settingKeys.personalLeftSidebar, + handleUpdate, + ); return () => { - unsubscribe(); + unsubGlobal(); + unsubPersonal(); }; }, []); return { config, setConfig }; }; +// TODO(ENG-1471): refreshAndNotify still needed by settings panels +// (LeftSidebarGlobalSettings, LeftSidebarPersonalSettings) for old-system CRUD. +// Remove when settings panels also read via accessors + emitter. export const refreshAndNotify = () => { refreshConfigTree(); notify(); @@ -420,7 +509,7 @@ const LeftSidebarView = ({ onloadArgs }: { onloadArgs: OnloadArgs }) => { }; const migrateFavorites = async () => { - const config = getFormattedConfigTree().leftSidebar; + const config = getCurrentLeftSidebarConfig(); if (config.favoritesMigrated.value) return; diff --git a/apps/roam/src/components/ModifyNodeDialog.tsx b/apps/roam/src/components/ModifyNodeDialog.tsx index 3137e338f..ce2c6b834 100644 --- a/apps/roam/src/components/ModifyNodeDialog.tsx +++ b/apps/roam/src/components/ModifyNodeDialog.tsx @@ -280,10 +280,7 @@ const ModifyNodeDialog = ({ } if (keyImageOption === "query-builder") { - const parentUid = resolveQueryBuilderRef({ - queryRef: qbAlias, - extensionAPI, - }); + const parentUid = resolveQueryBuilderRef({ queryRef: qbAlias }); const results = await runQuery({ extensionAPI, parentUid, diff --git a/apps/roam/src/components/QueryEditor.tsx b/apps/roam/src/components/QueryEditor.tsx index fbca18c49..fc7bc1d20 100644 --- a/apps/roam/src/components/QueryEditor.tsx +++ b/apps/roam/src/components/QueryEditor.tsx @@ -46,6 +46,10 @@ import { ALL_SELECTION_SUGGESTIONS } from "~/utils/predefinedSelections"; import { getAlias } from "~/utils/parseResultSettings"; import { setDiscourseNodeSetting } from "~/components/settings/utils/accessors"; import { IndexSchema } from "~/components/settings/utils/zodSchema"; +import { + DISCOURSE_NODE_KEYS, + SPECIFICATION_KEYS, +} from "~/components/settings/utils/settingKeys"; const getSourceCandidates = (cs: Condition[]): string[] => cs.flatMap((c) => @@ -513,7 +517,9 @@ const QueryEditor: QueryEditorComponent = ({ } const path = - settingKey === "index" ? ["index"] : ["specification", "query"]; + settingKey === "index" + ? [DISCOURSE_NODE_KEYS.index] + : [DISCOURSE_NODE_KEYS.specification, SPECIFICATION_KEYS.query]; window.clearTimeout(blockPropSyncTimeoutRef.current); blockPropSyncTimeoutRef.current = window.setTimeout(() => { diff --git a/apps/roam/src/components/SuggestionsBody.tsx b/apps/roam/src/components/SuggestionsBody.tsx index 794e60214..7f751e31f 100644 --- a/apps/roam/src/components/SuggestionsBody.tsx +++ b/apps/roam/src/components/SuggestionsBody.tsx @@ -24,8 +24,13 @@ import getDiscourseRelations from "~/utils/getDiscourseRelations"; import getDiscourseNodes from "~/utils/getDiscourseNodes"; import normalizePageTitle from "roamjs-components/queries/normalizePageTitle"; import { type RelationDetails } from "~/utils/hyde"; -import { getFormattedConfigTree } from "~/utils/discourseConfigRef"; import { render as renderToast } from "roamjs-components/components/Toast"; +import { getGlobalSetting } from "~/components/settings/utils/accessors"; +import { + GLOBAL_KEYS, + SUGGESTIVE_MODE_KEYS, +} from "~/components/settings/utils/settingKeys"; +import type { PageGroup } from "~/components/settings/utils/zodSchema"; import { createReifiedRelation } from "~/utils/createReifiedBlock"; import { getStoredRelationsEnabled } from "~/utils/storedRelations"; import posthog from "posthog-js"; @@ -416,12 +421,15 @@ const SuggestionsBody = ({ }; useEffect(() => { - const config = getFormattedConfigTree(); - const groups = config.suggestiveMode.pageGroups.groups; + const groups = + getGlobalSetting([ + GLOBAL_KEYS.suggestiveMode, + SUGGESTIVE_MODE_KEYS.pageGroups, + ]) ?? []; const groupsRecord = groups.reduce( (acc, group) => { - acc[group.name] = group.pages.map((p) => p.name); + acc[group.name] = group.pages; return acc; }, {} as Record, diff --git a/apps/roam/src/components/canvas/DiscourseNodeUtil.tsx b/apps/roam/src/components/canvas/DiscourseNodeUtil.tsx index fc2f1d742..1cba2a1c1 100644 --- a/apps/roam/src/components/canvas/DiscourseNodeUtil.tsx +++ b/apps/roam/src/components/canvas/DiscourseNodeUtil.tsx @@ -35,11 +35,8 @@ import calcCanvasNodeSizeAndImg from "~/utils/calcCanvasNodeSizeAndImg"; import { createTextJsxFromSpans } from "./DiscourseRelationShape/helpers"; import { loadImage } from "~/utils/loadImage"; import { getRelationColor } from "./DiscourseRelationShape/DiscourseRelationUtil"; -import { - AUTO_CANVAS_RELATIONS_KEY, - DISCOURSE_CONTEXT_OVERLAY_IN_CANVAS_KEY, -} from "~/data/userSettings"; -import { getSetting } from "~/utils/extensionSettings"; +import { getPersonalSetting } from "~/components/settings/utils/accessors"; +import { PERSONAL_KEYS } from "~/components/settings/utils/settingKeys"; import DiscourseContextOverlay from "~/components/DiscourseContextOverlay"; import { getDiscourseNodeColors } from "~/utils/getDiscourseNodeColors"; import { render as renderToast } from "roamjs-components/components/Toast"; @@ -435,7 +432,7 @@ export class BaseDiscourseNodeUtil extends BaseBoxShapeUtil } = discourseContext.nodes[shape.type] || {}; // eslint-disable-next-line react-hooks/rules-of-hooks const isOverlayEnabled = useMemo( - () => getSetting(DISCOURSE_CONTEXT_OVERLAY_IN_CANVAS_KEY, false), + () => getPersonalSetting([PERSONAL_KEYS.overlayInCanvas]), [], ); @@ -516,10 +513,9 @@ export class BaseDiscourseNodeUtil extends BaseBoxShapeUtil uid, }); - const autoCanvasRelations = getSetting( - AUTO_CANVAS_RELATIONS_KEY, - false, - ); + const autoCanvasRelations = getPersonalSetting([ + PERSONAL_KEYS.autoCanvasRelations, + ]); if (autoCanvasRelations) { try { const relationIds = getRelationIds(); diff --git a/apps/roam/src/components/canvas/Tldraw.tsx b/apps/roam/src/components/canvas/Tldraw.tsx index e77e91dcd..360b623ef 100644 --- a/apps/roam/src/components/canvas/Tldraw.tsx +++ b/apps/roam/src/components/canvas/Tldraw.tsx @@ -94,8 +94,6 @@ import { CanvasDrawerPanel } from "./CanvasDrawer"; import { ClipboardPanel, ClipboardProvider } from "./Clipboard"; import internalError from "~/utils/internalError"; import { syncCanvasNodeTitlesOnLoad } from "~/utils/syncCanvasNodeTitlesOnLoad"; -import { AUTO_CANVAS_RELATIONS_KEY } from "~/data/userSettings"; -import { getSetting } from "~/utils/extensionSettings"; import { isPluginTimerReady, waitForPluginTimer } from "~/utils/pluginTimer"; import { HistoryEntry } from "@tldraw/store"; import { TLRecord } from "@tldraw/tlschema"; @@ -116,6 +114,8 @@ import { useCanvasStoreAdapterArgs, } from "./useCanvasStoreAdapterArgs"; import posthog from "posthog-js"; +import { getPersonalSetting } from "~/components/settings/utils/accessors"; +import { PERSONAL_KEYS } from "~/components/settings/utils/settingKeys"; import { json, normalizeProps } from "~/utils/getBlockProps"; declare global { @@ -1440,10 +1440,9 @@ const InsideEditorAndUiContext = ({ editor.sideEffects.registerAfterCreateHandler("shape", (shape) => { const util = editor.getShapeUtil(shape); if (util instanceof BaseDiscourseNodeUtil) { - const autoCanvasRelations = getSetting( - AUTO_CANVAS_RELATIONS_KEY, - false, - ); + const autoCanvasRelations = getPersonalSetting([ + PERSONAL_KEYS.autoCanvasRelations, + ]); if (autoCanvasRelations) { void util.createExistingRelations({ shape: shape as DiscourseNodeShape, diff --git a/apps/roam/src/components/canvas/uiOverrides.tsx b/apps/roam/src/components/canvas/uiOverrides.tsx index 049c84edf..4c71b8c47 100644 --- a/apps/roam/src/components/canvas/uiOverrides.tsx +++ b/apps/roam/src/components/canvas/uiOverrides.tsx @@ -51,11 +51,11 @@ import calcCanvasNodeSizeAndImg from "~/utils/calcCanvasNodeSizeAndImg"; import { AddReferencedNodeType } from "./DiscourseRelationShape/DiscourseRelationTool"; import { getRelationColor } from "./DiscourseRelationShape/DiscourseRelationUtil"; import DiscourseGraphPanel from "./DiscourseToolPanel"; -import { DISCOURSE_TOOL_SHORTCUT_KEY } from "~/data/userSettings"; -import { getSetting } from "~/utils/extensionSettings"; import { CustomDefaultToolbar } from "./CustomDefaultToolbar"; import { renderModifyNodeDialog } from "~/components/ModifyNodeDialog"; import { CanvasSyncMode } from "./canvasSyncMode"; +import { getPersonalSetting } from "~/components/settings/utils/accessors"; +import { PERSONAL_KEYS } from "~/components/settings/utils/settingKeys"; import posthog from "posthog-js"; const SyncModeMenuSwitchItem = ({ @@ -377,10 +377,12 @@ export const createUiOverrides = ({ }): TLUiOverrides => ({ tools: (editor, tools) => { // Get the custom keyboard shortcut for the discourse tool - const discourseToolCombo = getSetting(DISCOURSE_TOOL_SHORTCUT_KEY, { + const discourseToolCombo = getPersonalSetting([ + PERSONAL_KEYS.discourseToolShortcut, + ]) || { key: "", modifiers: 0, - }) as IKeyCombo; + }; // For discourse tool, just use the key directly since we don't allow modifiers const discourseToolShortcut = discourseToolCombo?.key?.toUpperCase() || ""; diff --git a/apps/roam/src/components/settings/AdminPanel.tsx b/apps/roam/src/components/settings/AdminPanel.tsx index 4baac12b4..5c4bd7317 100644 --- a/apps/roam/src/components/settings/AdminPanel.tsx +++ b/apps/roam/src/components/settings/AdminPanel.tsx @@ -14,6 +14,14 @@ import { } from "@blueprintjs/core"; import Description from "roamjs-components/components/Description"; import { Select } from "@blueprintjs/select"; +import { + getFeatureFlag, + setFeatureFlag, +} from "~/components/settings/utils/accessors"; +import { + onSettingChange, + settingKeys, +} from "~/components/settings/utils/settingsEmitter"; import { getSupabaseContext, getLoggedInClient, @@ -29,11 +37,14 @@ import { import type { DGSupabaseClient } from "@repo/database/lib/client"; import internalError from "~/utils/internalError"; import SuggestiveModeSettings from "./SuggestiveModeSettings"; -import { getFormattedConfigTree } from "~/utils/discourseConfigRef"; +import discourseConfigRef from "~/utils/discourseConfigRef"; import refreshConfigTree from "~/utils/refreshConfigTree"; import createBlock from "roamjs-components/writes/createBlock"; import deleteBlock from "roamjs-components/writes/deleteBlock"; -import { setFeatureFlag } from "~/components/settings/utils/accessors"; +import { FeatureFlagPanel } from "./components/BlockPropSettingPanels"; +import getPageUidByPageTitle from "roamjs-components/queries/getPageUidByPageTitle"; +import { getUidAndBooleanSetting } from "~/utils/getExportSettings"; +import { DISCOURSE_CONFIG_PAGE_TITLE } from "~/data/constants"; const NodeRow = ({ node }: { node: PConceptFull }) => { return ( @@ -254,16 +265,22 @@ const NodeListTab = (): React.ReactElement => { }; const FeatureFlagsTab = (): React.ReactElement => { - const settings = useMemo(() => { + const legacySuggestiveModeMeta = useMemo(() => { refreshConfigTree(); - return getFormattedConfigTree(); + return { + settingsUid: getPageUidByPageTitle(DISCOURSE_CONFIG_PAGE_TITLE), + suggestiveModeEnabledUid: getUidAndBooleanSetting({ + tree: discourseConfigRef.tree, + text: "(BETA) Suggestive Mode Enabled", + }).uid, + }; }, []); const [suggestiveModeEnabled, setSuggestiveModeEnabled] = useState( - settings.suggestiveModeEnabled.value || false, + getFeatureFlag("Suggestive mode enabled"), ); const [suggestiveModeUid, setSuggestiveModeUid] = useState( - settings.suggestiveModeEnabled.uid, + legacySuggestiveModeMeta.suggestiveModeEnabledUid, ); const [isAlertOpen, setIsAlertOpen] = useState(false); const [isInstructionOpen, setIsInstructionOpen] = useState(false); @@ -300,7 +317,7 @@ const FeatureFlagsTab = (): React.ReactElement => { isOpen={isAlertOpen} onConfirm={() => { void createBlock({ - parentUid: settings.settingsUid, + parentUid: legacySuggestiveModeMeta.settingsUid, node: { text: "(BETA) Suggestive Mode Enabled" }, }).then((uid) => { setSuggestiveModeUid(uid); @@ -326,10 +343,8 @@ const FeatureFlagsTab = (): React.ReactElement => { window.location.reload()} - onCancel={() => setIsInstructionOpen(false)} - confirmButtonText="Reload Graph" - cancelButtonText="Later" + onConfirm={() => setIsInstructionOpen(false)} + confirmButtonText="OK" intent={Intent.PRIMARY} >

@@ -337,15 +352,17 @@ const FeatureFlagsTab = (): React.ReactElement => { upload all node embeddings to supabase.

- Please reload the graph to see the new 'Suggestive Mode' - tab. -

-

- Then go to Suggestive Mode{" "} + Go to Suggestive Mode{" "} {"-> Sync Config -> Click on 'Generate & Upload All Node Embeddings'"}

+ +