Add an option to share videos via privacy frontend URLs

When enabled (the default), share links to YouTube videos point to the
active source's web watch page instead of youtube.com. Invidious serves
its frontend at the API URL; Piped uses its configured frontend URL.
Videos the active source can't serve (PeerTube, extracted sources) and
sources without a web frontend keep their original links.

The toggle lives in Settings > Layout & Navigation > Sharing on iOS and
macOS, and is shown only when an enabled source has a web watch page.
This commit is contained in:
Arkadiusz Fal
2026-09-18 23:57:34 +02:00
parent 172d712f25
commit d22abf6088
13 changed files with 128 additions and 8 deletions

View File

@@ -756,6 +756,28 @@ final class AppEnvironment {
}
}
// MARK: - Sharing
/// URL for sharing a video, honoring the privacy-frontend sharing setting.
///
/// When enabled, YouTube videos are shared as links to the active
/// instance's web watch page. Videos the active instance doesn't serve
/// (PeerTube, extracted sources) and instances without a web frontend
/// keep the video's original share URL.
func shareURL(for video: Video) -> URL {
guard settingsManager.privacyFrontendSharingEnabled,
case .global(let provider) = video.id.source,
provider == ContentSource.youtubeProvider,
let base = instancesManager.activeInstance?.watchPageBaseURL,
var components = URLComponents(url: base, resolvingAgainstBaseURL: false)
else {
return video.shareURL
}
components.path += "/watch"
components.queryItems = [URLQueryItem(name: "v", value: video.id.videoID)]
return components.url ?? video.shareURL
}
// MARK: - Notifications
/// Ensures the notification infrastructure is enabled (system permission + master toggle + background refresh).

View File

@@ -580,6 +580,27 @@ extension SettingsManager {
}
}
// MARK: - Sharing Settings
/// Whether share links to YouTube videos point at the active instance's
/// web watch page instead of youtube.com. Default is true.
/// Videos the active instance can't serve keep their original URL.
/// This is a local-only setting (not synced to iCloud).
var privacyFrontendSharingEnabled: Bool {
get {
if let cached = _privacyFrontendSharingEnabled { return cached }
// Default to true if not set
if localDefaults.object(forKey: "privacyFrontendSharingEnabled") == nil {
return true
}
return localDefaults.bool(forKey: "privacyFrontendSharingEnabled")
}
set {
_privacyFrontendSharingEnabled = newValue
localDefaults.set(newValue, forKey: "privacyFrontendSharingEnabled")
}
}
// MARK: - Link Action Settings
/// Default action when opening links from share extension or URL schemes.

View File

@@ -203,6 +203,9 @@ final class SettingsManager {
// Handoff settings
var _handoffEnabled: Bool?
// Sharing settings
var _privacyFrontendSharingEnabled: Bool?
// Remote Control settings
var _remoteControlCustomDeviceName: String?
var _remoteControlHideWhenBackgrounded: Bool?
@@ -541,6 +544,7 @@ final class SettingsManager {
_queueAutoPlayNext = nil
_queueAutoPlayCountdown = nil
_handoffEnabled = nil
_privacyFrontendSharingEnabled = nil
_defaultLinkAction = nil
_remoteControlCustomDeviceName = nil
_remoteControlHideWhenBackgrounded = nil