Lock network settings for builds >= 3000

This commit is contained in:
Davide De Rosa 2022-04-13 20:12:25 +02:00
parent 320513dd38
commit 2565b9f3d0
12 changed files with 78 additions and 14 deletions

View File

@ -126,7 +126,7 @@
<EnvironmentVariables>
<EnvironmentVariable
key = "APP_TYPE"
value = "2"
value = "0"
isEnabled = "YES">
</EnvironmentVariable>
<EnvironmentVariable

View File

@ -114,7 +114,8 @@ class AppContext {
productManager = ProductManager(.init(
appType: Constants.InApp.appType,
lastFullVersionBuild: Constants.InApp.lastFullVersionBuild
lastFullVersionBuild: Constants.InApp.lastFullVersionBuild,
lastNetworkSettingsBuild: Constants.InApp.lastNetworkSettingsBuild
))
intentsManager = IntentsManager()
reviewer = Reviewer()
@ -163,6 +164,15 @@ class AppContext {
return true
}
// eligibility: ignore network settings if ineligible
private func isEligibleForNetworkSettings() -> Bool {
guard productManager.isEligible(forFeature: .networkSettings) else {
pp_log.warning("Ignore network settings, not eligible")
return false
}
return true
}
// eligibility: reset on-demand rules if no trusted networks
private func isEligibleForOnDemandRules() -> Bool {
guard productManager.isEligible(forFeature: .trustedNetworks) else {

View File

@ -75,6 +75,8 @@ extension Constants {
#else
static let lastFullVersionBuild: (Int, LocalProduct) = (0, .fullVersion_macOS)
#endif
static let lastNetworkSettingsBuild = 2999
private static var isBeta: Bool {
#if os(iOS)

View File

@ -68,6 +68,8 @@ struct LocalProduct: RawRepresentable, Equatable, Hashable {
// MARK: Features
static let allProviders = LocalProduct(featureId: "all_providers")
static let networkSettings = LocalProduct(featureId: "network_settings")
static let trustedNetworks = LocalProduct(featureId: "trusted_networks")
@ -81,6 +83,7 @@ struct LocalProduct: RawRepresentable, Equatable, Hashable {
static let allFeatures: [LocalProduct] = [
.allProviders,
.networkSettings,
.trustedNetworks,
.siriShortcuts,
.fullVersion_iOS,

View File

@ -49,12 +49,16 @@ class ProductManager: NSObject, ObservableObject {
let lastFullVersionBuild: (Int, LocalProduct)
let lastNetworkSettingsBuild: Int
init(
appType: AppType,
lastFullVersionBuild: (Int, LocalProduct)
lastFullVersionBuild: (Int, LocalProduct),
lastNetworkSettingsBuild: Int
) {
self.appType = appType
self.lastFullVersionBuild = lastFullVersionBuild
self.lastNetworkSettingsBuild = lastNetworkSettingsBuild
}
}
@ -193,6 +197,11 @@ class ProductManager: NSObject, ObservableObject {
}
func isEligible(forFeature feature: LocalProduct) -> Bool {
if let purchasedAppBuild = purchasedAppBuild {
if feature == .networkSettings && purchasedAppBuild <= cfg.lastNetworkSettingsBuild {
return true
}
}
#if os(iOS)
return isFullVersion() || purchasedFeatures.contains(feature)
#else

View File

@ -34,6 +34,10 @@ extension ProfileView {
@Binding private var modalType: ModalType?
private var isEligibleForNetworkSettings: Bool {
productManager.isEligible(forFeature: .networkSettings)
}
private var isEligibleForTrustedNetworks: Bool {
productManager.isEligible(forFeature: .trustedNetworks)
}
@ -75,10 +79,20 @@ extension ProfileView {
Label(L10n.Account.title, systemImage: themeAccountImage)
}
}
NavigationLink {
NetworkSettingsView(currentProfile: currentProfile)
} label: {
Label(L10n.NetworkSettings.title, systemImage: themeNetworkSettingsImage)
// eligibility: enter network settings or present paywall
if isEligibleForNetworkSettings {
NavigationLink {
NetworkSettingsView(currentProfile: currentProfile)
} label: {
networkSettingsRow
}
} else {
Button {
modalType = .paywallNetworkSettings
} label: {
networkSettingsRow
}
}
// eligibility: enter trusted networks or present paywall
@ -97,6 +111,10 @@ extension ProfileView {
}
}
}
private var networkSettingsRow: some View {
Label(L10n.NetworkSettings.title, systemImage: themeNetworkSettingsImage)
}
private var onDemandRow: some View {
Label(L10n.OnDemand.title, systemImage: themeOnDemandImage)

View File

@ -31,6 +31,8 @@ struct ProfileView: View {
enum ModalType: Int, Identifiable {
case rename
case paywallNetworkSettings
case paywallTrustedNetworks
var id: Int {
@ -123,6 +125,14 @@ struct ProfileView: View {
RenameView(currentProfile: profileManager.currentProfile)
}.themeGlobal()
case .paywallNetworkSettings:
NavigationView {
PaywallView(
modalType: $modalType,
feature: .networkSettings
)
}.themeGlobal()
case .paywallTrustedNetworks:
NavigationView {
PaywallView(

View File

@ -41,10 +41,12 @@ extension Profile.OpenVPNSettings: VPNConfigurationProviding {
}
// network settings
customBuilder.applyGateway(from: parameters.networkSettings.gateway)
customBuilder.applyDNS(from: parameters.networkSettings.dns)
customBuilder.applyProxy(from: parameters.networkSettings.proxy)
customBuilder.applyMTU(from: parameters.networkSettings.mtu)
if parameters.withNetworkSettings {
customBuilder.applyGateway(from: parameters.networkSettings.gateway)
customBuilder.applyDNS(from: parameters.networkSettings.dns)
customBuilder.applyProxy(from: parameters.networkSettings.proxy)
customBuilder.applyMTU(from: parameters.networkSettings.mtu)
}
let customConfiguration = customBuilder.build()

View File

@ -33,9 +33,11 @@ extension Profile.WireGuardSettings: VPNConfigurationProviding {
var customBuilder = configuration.builder()
// network settings
customBuilder.applyGateway(from: parameters.networkSettings.gateway)
customBuilder.applyDNS(from: parameters.networkSettings.dns)
customBuilder.applyMTU(from: parameters.networkSettings.mtu)
if parameters.withNetworkSettings {
customBuilder.applyGateway(from: parameters.networkSettings.gateway)
customBuilder.applyDNS(from: parameters.networkSettings.dns)
customBuilder.applyMTU(from: parameters.networkSettings.mtu)
}
let customConfiguration = customBuilder.build()

View File

@ -54,6 +54,7 @@ extension VPNManager {
appGroup: profileManager.appGroup,
preferences: appManager.preferences,
passwordReference: profileManager.passwordReference(forProfile: profile),
withNetworkSettings: isNetworkSettingsSupported(),
withCustomRules: isOnDemandRulesSupported()
)

View File

@ -41,6 +41,8 @@ public class VPNManager: ObservableObject, RateLimited {
private let strategy: VPNManagerStrategy
public var isNetworkSettingsSupported: () -> Bool
public var isOnDemandRulesSupported: () -> Bool
// MARK: State
@ -72,6 +74,7 @@ public class VPNManager: ObservableObject, RateLimited {
self.profileManager = profileManager
self.providerManager = providerManager
self.strategy = strategy
isNetworkSettingsSupported = { true }
isOnDemandRulesSupported = { true }
currentState = ObservableState()

View File

@ -47,6 +47,8 @@ struct VPNConfigurationParameters {
let passwordReference: Data?
let withNetworkSettings: Bool
let onDemandRules: [NEOnDemandRule]
init(
@ -54,6 +56,7 @@ struct VPNConfigurationParameters {
appGroup: String,
preferences: AppPreferences,
passwordReference: Data?,
withNetworkSettings: Bool,
withCustomRules: Bool
) {
title = profile.header.name
@ -62,6 +65,7 @@ struct VPNConfigurationParameters {
networkSettings = profile.networkSettings
username = !profile.account.username.isEmpty ? profile.account.username : nil
self.passwordReference = passwordReference
self.withNetworkSettings = withNetworkSettings
onDemandRules = profile.onDemand.rules(withCustomRules: withCustomRules)
}
}