Feat/open in desktop app not installed#429
Draft
appflowy wants to merge 7 commits into
Draft
Conversation
Adds open_desktop_app.ts: a reusable helper to open a target in the AppFlowy desktop app and fall back gracefully when the app is not installed, mirroring Notion's behavior. Because browsers cannot reliably detect an installed app, it uses the attempt-and-observe heuristic (fire appflowy-flutter:// scheme, watch for the page losing focus/visibility within a timeout). When the app does not open: - stay on the web (no forced download redirect), - show a non-blocking "Couldn't open the AppFlowy desktop app" prompt with Download / Continue-in-browser actions, - remember the "not detected" result per-device (localStorage, ~weekly TTL) so subsequent links don't stall again; the flag is cleared on any later success. openInDesktopApp() layers the prompt + skip-when-known-missing logic; callers (invite accept page, share-link page) pass onContinueInBrowser to proceed to the web. Includes i18n strings and unit tests (8 cases). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
Foundation for the desktop handoff: a per-user, server-synced preference
stored in user metadata, identical to how timezone/language/date-format are
persisted.
- user-metadata.ts: add MetadataKey.OpenInDesktopApp ('open_in_desktop_app'),
its boolean MetadataValues type, a `false` default, and a
UserMetadataBuilder.setOpenInDesktopApp() helper.
- useOpenInDesktopApp(): read currentUser.metadata[open_in_desktop_app]
(enabled / isSet) and persist via UserService.updateProfile (server JSONB
merge) + updateCurrentUser (local cache), mirroring AccountAppPanel.
No backend change required (the af_user.metadata JSONB merge accepts the key
as-is). The settings toggle and the handoff-gating wrapper build on this hook.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
Adds the Notion-style preference toggle in AccountAppPanel, bound to useOpenInDesktopApp() (reads/writes the synced open_in_desktop_app metadata key). Includes i18n strings under settings.accountPage.openInDesktopApp. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
… flows
- useOpenInDesktopApp: read AFConfigContext directly so the hook is safe on
landing/invitation pages (reports enabled=false outside the provider).
- useDesktopHandoff: preference-gated handoff — when "open in desktop app" is
on, attempt the deep link via openInDesktopApp (with not-installed handling);
otherwise stay on the web (onStayInBrowser).
- Flow 1 (AcceptInvitationPage): after accepting, hand off to
invitation-callback if enabled, else navigate to /app/{ws}.
- Flow 3 (AppContextConsumer/OpenClient): on a fresh share-link load of
/app/:ws/:view, attempt open-page once when enabled (module-scoped guard so
internal navigation doesn't retrigger). The explicit ?is_desktop=true path is
preserved for notification links.
Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
- open_desktop_app.ts: add buildOpenPageLink / buildInvitationCallbackLink as the single source of truth for the deep-link scheme format. - Flow 2 (AsGuest): the "View page" button now hands off to the desktop app (open-page with the shared view_id from getGuestInvitation) when the preference is on, else opens the page on the web. - Refactor AppContextConsumer and AcceptInvitationPage to use the shared builders instead of inline scheme strings. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
- Extract isSpecificPagePath() so the "share-link arrival vs internal navigation" classification (which gates the Flow 3 handoff) is pure and testable. - Tests: deep-link builders, isSpecificPagePath (share vs internal nav), and useDesktopHandoff gating (attempts when preference on, stays in browser when off) via renderHook. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
…ce (P4) When a user who hasn't chosen the preference opens an invite/share link, show a one-time Notion-style prompt instead of silently staying in the browser: - "Open in app" → enables the preference and opens the desktop app - "Stay in browser" → disables it Either choice is remembered, so the prompt is shown once. - open_desktop_app.ts: add promptOpenInDesktopApp (sonner toast + i18n). - useDesktopHandoff: enabled → attempt; unset → prompt (remembers choice); off → stay. - OpenClient: route the share-link handoff through useDesktopHandoff so the unset case prompts (still fire-once per document load). - i18n strings + test for the unset/prompt path (14 tests total). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VB3ZauXUUczqNTLFu9uoMs
🥷 Ninja i18n – 🛎️ Translations need to be updatedProject
|
| lint rule | new reports | level | link |
|---|---|---|---|
| Missing translation | 280 | warning | contribute (via Fink 🐦) |
Reviewer's GuideAdds a user preference and supporting utilities to control opening AppFlowy links in the desktop app, then wires that preference-driven handoff into guest landing, invitation acceptance, and app context navigation flows with robust handling of the desktop app not being installed. File-Level Changes
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Description
Checklist
General
Testing
Feature-Specific
Summary by Sourcery
Add a user preference and shared utilities for opening links in the AppFlowy desktop app, and apply this behavior to invitations, shared pages, and direct desktop deep links.
New Features:
Enhancements:
Tests: