diff options
| author | polwex <polwex@sortug.com> | 2025-11-18 16:59:24 +0700 |
|---|---|---|
| committer | polwex <polwex@sortug.com> | 2025-11-18 16:59:24 +0700 |
| commit | 420a543f8af3075502b0a7530a0fa06af264eb8b (patch) | |
| tree | 7446a8c59bd4b66ca2bb5ed04bce40d382e31c36 /gui/src/components/nostr | |
| parent | 76f99af3c98a689441315b5ed087c4b83c083191 (diff) | |
refactoring gui too, improvements to Nostr user logic
Diffstat (limited to 'gui/src/components/nostr')
| -rw-r--r-- | gui/src/components/nostr/Feed.tsx | 1 | ||||
| -rw-r--r-- | gui/src/components/nostr/User.tsx | 128 |
2 files changed, 129 insertions, 0 deletions
diff --git a/gui/src/components/nostr/Feed.tsx b/gui/src/components/nostr/Feed.tsx index 0e74cea..d21307b 100644 --- a/gui/src/components/nostr/Feed.tsx +++ b/gui/src/components/nostr/Feed.tsx @@ -14,6 +14,7 @@ export default function Nostr() { })); console.log({ relays }); const [isSyncing, setIsSyncing] = useState(false); + console.log({ nostrFeed }); const feed = eventsToFc(nostrFeed); console.log({ feed }); const refetch = () => feed; diff --git a/gui/src/components/nostr/User.tsx b/gui/src/components/nostr/User.tsx new file mode 100644 index 0000000..a9e9e2f --- /dev/null +++ b/gui/src/components/nostr/User.tsx @@ -0,0 +1,128 @@ +import useLocalState from "@/state/state"; +import { useState } from "react"; +import Icon from "@/components/Icon"; +import toast from "react-hot-toast"; +import type { UserType } from "@/types/nostrill"; +import type { FC } from "@/types/trill"; +import Composer from "../composer/Composer"; +import PostList from "@/components/feed/PostList"; + +export default function NostrUser({ + user, + userString, + feed, + isFollowLoading, + setIsFollowLoading, + isAccessLoading, + setIsAccessLoading, +}: { + user: UserType; + userString: string; + feed: FC | undefined; + isFollowLoading: boolean; + setIsFollowLoading: (b: boolean) => void; + isAccessLoading: boolean; + setIsAccessLoading: (b: boolean) => void; +}) { + const { api } = useLocalState((s) => ({ + api: s.api, + })); + const [fc, setFC] = useState<FC>(); + + // Show empty state with resync option when no feed data + + async function refetch() { + // + } + async function handleFollow() { + if (!api) return; + + setIsFollowLoading(true); + try { + if (feed) { + await api.unfollow(user); + } else { + await api.follow(user); + toast.success(`Follow request sent to ${userString}`); + } + } catch (error) { + toast.error(`Failed to ${!!feed ? "unfollow" : "follow"} ${userString}`); + setIsFollowLoading(false); + console.error("Follow error:", error); + } + } + async function handleRequestAccess() { + if (!api) return; + + setIsAccessLoading(true); + // try { + // const res = await api.peekFeed(user.urbit); + // toast.success(`Access request sent to ${user.urbit}`); + // addNotification({ + // type: "access_request", + // from: userString, + // message: `Access request sent to ${userString}`, + // }); + // if ("error" in res) toast.error(res.error); + // else { + // console.log("peeked", res.ok.feed); + // setFC(res.ok.feed); + // if (res.ok.profile) addProfile(userString, res.ok.profile); + // } + // } catch (error) { + // toast.error(`Failed to request access from ${user.urbit}`); + // console.error("Access request error:", error); + // } finally { + // setIsAccessLoading(false); + // } + } + return ( + <> + <div className="user-actions"> + <button + onClick={handleFollow} + disabled={isFollowLoading} + className={`action-btn ${!!feed ? "" : "follow"}`} + > + {isFollowLoading ? ( + <> + <Icon name="settings" size={16} /> + {!!feed ? "Unfollowing..." : "Following..."} + </> + ) : ( + <> + <Icon name={!!feed ? "bell" : "pals"} size={16} /> + {!!feed ? "Unfollow" : "Follow"} + </> + )} + </button> + + {(!feed || !feed.feed || Object.keys(feed.feed).length === 0) && ( + <button + onClick={handleRequestAccess} + disabled={isAccessLoading} + className="action-btn access" + > + {isAccessLoading ? ( + <> + <Icon name="settings" size={16} /> + Fetching... + </> + ) : ( + <> + <Icon name="key" size={16} /> + Fetch Feed + </> + )} + </button> + )} + </div> + {(feed || fc) && ( + <div id="feed-proper"> + <Composer /> + <PostList data={(feed || fc)!} refetch={refetch} /> + </div> + )} + </> + ); +} |
