fix(channels): land on the subscriptions tab for channel-targeted navigation

The Channel manager's tab (subscriptions vs playlist discovery) was persisted
locally, so the header's "N without full history" link and the focus-channel
jump (subscribe notice, tag manager) could dump the user on the Discovery tab
while quietly applying a status/name filter that only affects the subscriptions
table — the targeted channel was there, just on the hidden tab.

Lift the tab state to App alongside the status filter it pairs with, and have
those navigation intents switch it back to "subscribed".
This commit is contained in:
npeter83 2026-06-19 03:38:57 +02:00
parent 141dd32855
commit 1bedfca666
2 changed files with 24 additions and 13 deletions

View file

@ -23,7 +23,7 @@ import ChannelDiscovery from "./ChannelDiscovery";
import TagManager from "./TagManager";
import { useConfirm } from "./ConfirmProvider";
type ChannelsView = "subscribed" | "discovery";
export type ChannelsView = "subscribed" | "discovery";
export type ChannelStatusFilter = "all" | "needs_full" | "fully_synced" | "hidden";
@ -50,6 +50,8 @@ export default function Channels({
focusChannelName,
statusFilter,
setStatusFilter,
view,
setView,
onOpenWizard,
}: {
canWrite: boolean;
@ -60,23 +62,16 @@ export default function Channels({
focusChannelName: string | null;
statusFilter: ChannelStatusFilter;
setStatusFilter: (f: ChannelStatusFilter) => void;
// The active tab lives in App so navigation intents that target the subscriptions table
// (the header's "without full history" link, focus-channel) can force it back here.
view: ChannelsView;
setView: (v: ChannelsView) => void;
onOpenWizard: () => void;
}) {
const { t } = useTranslation();
const qc = useQueryClient();
const confirm = useConfirm();
// Which tab is showing: the user's subscriptions, or channels discovered from their
// playlists. Persisted so a reload keeps the active tab (see other siftlode.* keys).
const [view, setView] = useState<ChannelsView>(() =>
localStorage.getItem("siftlode.channelsView") === "discovery"
? "discovery"
: "subscribed"
);
useEffect(() => {
localStorage.setItem("siftlode.channelsView", view);
}, [view]);
// A YouTube-gated action (sync, backfill, unsubscribe) that 403s means the user hasn't
// granted the needed scope — surface that with a "Connect" action instead of a vague fail.
const notifyActionError = (err: unknown, fallbackKey: string) => {