order
This commit is contained in:
parent
66a770faec
commit
4f31d10da4
6 changed files with 33 additions and 16 deletions
|
@ -24,6 +24,7 @@
|
||||||
"date-fns": "^3.6.0",
|
"date-fns": "^3.6.0",
|
||||||
"hast-util-to-jsx-runtime": "^2.3.0",
|
"hast-util-to-jsx-runtime": "^2.3.0",
|
||||||
"hast-util-to-mdast": "^10.1.0",
|
"hast-util-to-mdast": "^10.1.0",
|
||||||
|
"immutable": "^4.3.6",
|
||||||
"javascript-time-ago": "^2.5.10",
|
"javascript-time-ago": "^2.5.10",
|
||||||
"jotai": "^2.8.1",
|
"jotai": "^2.8.1",
|
||||||
"katex": "^0.16.10",
|
"katex": "^0.16.10",
|
||||||
|
|
|
@ -11,36 +11,38 @@ import { QueryClient, QueryClientProvider } from "@tanstack/react-query";
|
||||||
import TimeAgo from "javascript-time-ago";
|
import TimeAgo from "javascript-time-ago";
|
||||||
import en from "javascript-time-ago/locale/en";
|
import en from "javascript-time-ago/locale/en";
|
||||||
import Sidebar from "./components/Sidebar";
|
import Sidebar from "./components/Sidebar";
|
||||||
import { atom, useAtom } from "jotai";
|
import { atom, useAtom, useAtomValue } from "jotai";
|
||||||
|
import { OrderedMap, OrderedSet } from "immutable";
|
||||||
|
|
||||||
const queryClient = new QueryClient();
|
const queryClient = new QueryClient();
|
||||||
|
|
||||||
TimeAgo.addDefaultLocale(en);
|
TimeAgo.addDefaultLocale(en);
|
||||||
|
|
||||||
export const nodesOpenedAtom = atom<string[]>([]);
|
export const nodesOpenedAtom = atom<OrderedSet<string>>(OrderedSet<string>());
|
||||||
|
|
||||||
function App() {
|
function App() {
|
||||||
const [nodesOpened, setNodesOpened] = useAtom(nodesOpenedAtom);
|
const nodesOpened = useAtomValue(nodesOpenedAtom);
|
||||||
|
const openNode = useOpenNode();
|
||||||
|
|
||||||
// Open today's journal entry if it's not already opened
|
// Open today's journal entry if it's not already opened
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
(async () => {
|
(async () => {
|
||||||
console.log("ndoes", nodesOpened);
|
console.log("ndoes", nodesOpened);
|
||||||
if (nodesOpened.length === 0) {
|
if (nodesOpened.size === 0) {
|
||||||
console.log("Opening today's entry.");
|
console.log("Opening today's entry.");
|
||||||
const resp = await fetch(
|
const resp = await fetch(
|
||||||
"http://localhost:5195/journal/get_todays_journal_id",
|
"http://localhost:5195/journal/get_todays_journal_id",
|
||||||
);
|
);
|
||||||
const data = await resp.json();
|
const data = await resp.json();
|
||||||
console.log("resp", data);
|
console.log("resp", data);
|
||||||
setNodesOpened([data.node_id]);
|
openNode(data.node_id);
|
||||||
}
|
}
|
||||||
})();
|
})();
|
||||||
}, [nodesOpened]);
|
}, [nodesOpened, openNode]);
|
||||||
|
|
||||||
const nodes = nodesOpened.map((nodeId) => (
|
const nodes = nodesOpened
|
||||||
<NodeDisplay key={nodeId} id={nodeId} />
|
.reverse()
|
||||||
));
|
.map((nodeId) => <NodeDisplay key={nodeId} id={nodeId} />);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<QueryClientProvider client={queryClient}>
|
<QueryClientProvider client={queryClient}>
|
||||||
|
@ -57,3 +59,10 @@ function App() {
|
||||||
}
|
}
|
||||||
|
|
||||||
export default App;
|
export default App;
|
||||||
|
|
||||||
|
export function useOpenNode() {
|
||||||
|
const [nodesOpened, setNodesOpened] = useAtom(nodesOpenedAtom);
|
||||||
|
return (node_id: string) => {
|
||||||
|
setNodesOpened(nodesOpened.remove(node_id).add(node_id));
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
|
@ -49,5 +49,6 @@
|
||||||
|
|
||||||
.subtitle {
|
.subtitle {
|
||||||
font-size: .75rem;
|
font-size: .75rem;
|
||||||
|
color: rgba(0, 0, 0, 0.8);
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -14,7 +14,7 @@ import {
|
||||||
import { useDebounce } from "use-debounce";
|
import { useDebounce } from "use-debounce";
|
||||||
import { useEffect, useState } from "react";
|
import { useEffect, useState } from "react";
|
||||||
import { atom, useAtom, useSetAtom } from "jotai";
|
import { atom, useAtom, useSetAtom } from "jotai";
|
||||||
import { nodesOpenedAtom } from "../App";
|
import { nodesOpenedAtom, useOpenNode } from "../App";
|
||||||
|
|
||||||
const searchQueryAtom = atom("");
|
const searchQueryAtom = atom("");
|
||||||
const showMenuAtom = atom(false);
|
const showMenuAtom = atom(false);
|
||||||
|
@ -87,25 +87,25 @@ export default function SearchBar() {
|
||||||
}
|
}
|
||||||
|
|
||||||
function SearchMenu({ results }) {
|
function SearchMenu({ results }) {
|
||||||
const setNodesOpened = useSetAtom(nodesOpenedAtom);
|
|
||||||
const setSearchQuery = useSetAtom(searchQueryAtom);
|
const setSearchQuery = useSetAtom(searchQueryAtom);
|
||||||
const setShowMenu = useSetAtom(showMenuAtom);
|
const setShowMenu = useSetAtom(showMenuAtom);
|
||||||
|
const openNode = useOpenNode();
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className={styles.searchResults}>
|
<div className={styles.searchResults}>
|
||||||
{results.map((result) => (
|
{results.map((result) => (
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
key={result.score.toString()}
|
key={result.node_id}
|
||||||
className={styles.searchResult}
|
className={styles.searchResult}
|
||||||
onClick={() => {
|
onClick={() => {
|
||||||
setSearchQuery("");
|
setSearchQuery("");
|
||||||
setShowMenu(false);
|
setShowMenu(false);
|
||||||
setNodesOpened((prev) => [result.node_id, ...prev]);
|
openNode(result.node_id);
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
<div className={styles.title}>{result.title}</div>
|
<div className={styles.title}>{result.title}</div>
|
||||||
<div className={styles.subtitle}>{result.score}</div>
|
<div className={styles.subtitle}>{result.content}</div>
|
||||||
</button>
|
</button>
|
||||||
))}
|
))}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -233,6 +233,10 @@ pub async fn search_nodes(
|
||||||
State(state): State<AppState>,
|
State(state): State<AppState>,
|
||||||
Query(query): Query<SearchQuery>,
|
Query(query): Query<SearchQuery>,
|
||||||
) -> AppResult<Json<Value>> {
|
) -> AppResult<Json<Value>> {
|
||||||
|
// TODO: This is temporary, there may be more ways to search so tacking on *
|
||||||
|
// at the end may destroy some queries
|
||||||
|
let query = format!("{}*", query.query);
|
||||||
|
|
||||||
let results = state.db.run_script(
|
let results = state.db.run_script(
|
||||||
"
|
"
|
||||||
results[node_id, content, score] := ~journal:text_index {node_id, content, |
|
results[node_id, content, score] := ~journal:text_index {node_id, content, |
|
||||||
|
@ -249,7 +253,7 @@ pub async fn search_nodes(
|
||||||
:order -score
|
:order -score
|
||||||
",
|
",
|
||||||
btmap! {
|
btmap! {
|
||||||
"q".to_owned() => DataValue::from(query.query),
|
"q".to_owned() => DataValue::from(query),
|
||||||
},
|
},
|
||||||
ScriptMutability::Immutable,
|
ScriptMutability::Immutable,
|
||||||
)?;
|
)?;
|
||||||
|
|
|
@ -53,6 +53,9 @@ importers:
|
||||||
hast-util-to-mdast:
|
hast-util-to-mdast:
|
||||||
specifier: ^10.1.0
|
specifier: ^10.1.0
|
||||||
version: 10.1.0
|
version: 10.1.0
|
||||||
|
immutable:
|
||||||
|
specifier: ^4.3.6
|
||||||
|
version: 4.3.6
|
||||||
javascript-time-ago:
|
javascript-time-ago:
|
||||||
specifier: ^2.5.10
|
specifier: ^2.5.10
|
||||||
version: 2.5.10
|
version: 2.5.10
|
||||||
|
@ -1975,7 +1978,6 @@ packages:
|
||||||
|
|
||||||
/immutable@4.3.6:
|
/immutable@4.3.6:
|
||||||
resolution: {integrity: sha512-Ju0+lEMyzMVZarkTn/gqRpdqd5dOPaz1mCZ0SH3JV6iFw81PldE/PEB1hWVEA288HPt4WXW8O7AWxB10M+03QQ==}
|
resolution: {integrity: sha512-Ju0+lEMyzMVZarkTn/gqRpdqd5dOPaz1mCZ0SH3JV6iFw81PldE/PEB1hWVEA288HPt4WXW8O7AWxB10M+03QQ==}
|
||||||
dev: true
|
|
||||||
|
|
||||||
/import-fresh@3.3.0:
|
/import-fresh@3.3.0:
|
||||||
resolution: {integrity: sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==}
|
resolution: {integrity: sha512-veYYhQa+D1QBKznvhUHxb8faxlrwUnxseDAbAp457E0wLNio2bOSKnjYDhMj+YiAq61xrMGhQk9iXVk5FzgQMw==}
|
||||||
|
|
Loading…
Reference in a new issue