Skip to content

Commit

Permalink
Implement force update
Browse files Browse the repository at this point in the history
  • Loading branch information
kp-said-rehouni committed Oct 9, 2024
1 parent a138838 commit 433e8e0
Show file tree
Hide file tree
Showing 10 changed files with 201 additions and 4 deletions.
20 changes: 20 additions & 0 deletions PIA VPN.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -715,6 +715,10 @@
E53627372BE802200064DEDF /* SignupUseCaseMock.swift in Sources */ = {isa = PBXBuildFile; fileRef = E53627362BE802200064DEDF /* SignupUseCaseMock.swift */; };
E548E1FF2C1238BD001E9874 /* SnapshotTesting in Frameworks */ = {isa = PBXBuildFile; productRef = E548E1FE2C1238BD001E9874 /* SnapshotTesting */; };
E548E2002C1238CD001E9874 /* WelcomeViewSnapshotTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = E548E1EC2C123782001E9874 /* WelcomeViewSnapshotTest.swift */; };
E55188932CB66BCA00E4C241 /* ForceUpdateViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = E55188912CB66BCA00E4C241 /* ForceUpdateViewController.swift */; };
E55188942CB66BCA00E4C241 /* ForceUpdateViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = E55188922CB66BCA00E4C241 /* ForceUpdateViewController.xib */; };
E55188952CB66BCA00E4C241 /* ForceUpdateViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = E55188912CB66BCA00E4C241 /* ForceUpdateViewController.swift */; };
E55188962CB66BCA00E4C241 /* ForceUpdateViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = E55188922CB66BCA00E4C241 /* ForceUpdateViewController.xib */; };
E55216342BEF63EA001A287F /* SignupIntegrationTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = E55216332BEF63EA001A287F /* SignupIntegrationTests.swift */; };
E55216362BF1393C001A287F /* SignupEmailIntegrationTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = E55216352BF1393C001A287F /* SignupEmailIntegrationTests.swift */; };
E55216382BF14A5B001A287F /* SignupDomainErrorMapper.swift in Sources */ = {isa = PBXBuildFile; fileRef = E55216372BF14A5B001A287F /* SignupDomainErrorMapper.swift */; };
Expand Down Expand Up @@ -1685,6 +1689,8 @@
E548E1EC2C123782001E9874 /* WelcomeViewSnapshotTest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = WelcomeViewSnapshotTest.swift; sourceTree = "<group>"; };
E548E1F52C1238B5001E9874 /* PIA VPN-tvOS snapshot.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = "PIA VPN-tvOS snapshot.xctest"; sourceTree = BUILT_PRODUCTS_DIR; };
E548E2012C124AA0001E9874 /* PIA VPN-tvOS snapshot.xctestplan */ = {isa = PBXFileReference; lastKnownFileType = text; path = "PIA VPN-tvOS snapshot.xctestplan"; sourceTree = "<group>"; };
E55188912CB66BCA00E4C241 /* ForceUpdateViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ForceUpdateViewController.swift; sourceTree = "<group>"; };
E55188922CB66BCA00E4C241 /* ForceUpdateViewController.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = ForceUpdateViewController.xib; sourceTree = "<group>"; };
E55216332BEF63EA001A287F /* SignupIntegrationTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SignupIntegrationTests.swift; sourceTree = "<group>"; };
E55216352BF1393C001A287F /* SignupEmailIntegrationTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SignupEmailIntegrationTests.swift; sourceTree = "<group>"; };
E55216372BF14A5B001A287F /* SignupDomainErrorMapper.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SignupDomainErrorMapper.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -2373,6 +2379,7 @@
296BBFEE1840066A00944151 /* UI */ = {
isa = PBXGroup;
children = (
E55188902CB66B7900E4C241 /* Force update */,
E5217F5C2AEAE01400123442 /* NotificationCategory.swift */,
E5217F532AEAD54600123442 /* WalkthroughPageView.swift */,
E5217F4A2AEAD29F00123442 /* PurchasePlanCell.swift */,
Expand Down Expand Up @@ -3567,6 +3574,15 @@
path = "PIA VPNTests snapshot";
sourceTree = "<group>";
};
E55188902CB66B7900E4C241 /* Force update */ = {
isa = PBXGroup;
children = (
E55188912CB66BCA00E4C241 /* ForceUpdateViewController.swift */,
E55188922CB66BCA00E4C241 /* ForceUpdateViewController.xib */,
);
name = "Force update";
sourceTree = "<group>";
};
E55216322BEF63AD001A287F /* Integration */ = {
isa = PBXGroup;
children = (
Expand Down Expand Up @@ -5007,6 +5023,7 @@
0ED66BD020A9918000333B35 /* staging.endpoint in Resources */,
DD76292021ECCD510092DF50 /* UsageTileCollectionViewCell.xib in Resources */,
E501CBB72AE97EC800515006 /* Welcome.storyboard in Resources */,
E55188962CB66BCA00E4C241 /* ForceUpdateViewController.xib in Resources */,
DD6DC5C321B6C27F00F9D538 /* pia-spinner.json in Resources */,
0E0715E7201CBB7100D6F666 /* Flags-dev.plist in Resources */,
DD1C138A21E60C63004004B3 /* IPTile.xib in Resources */,
Expand Down Expand Up @@ -5103,6 +5120,7 @@
291C6398183EBC210039EC03 /* Images.xcassets in Resources */,
82183D9625014FDC0033023F /* NetworkCollectionViewCell.xib in Resources */,
82183D9825014FDC0033023F /* CustomNetworkCollectionViewCell.xib in Resources */,
E55188942CB66BCA00E4C241 /* ForceUpdateViewController.xib in Resources */,
E501CBF72AE9806800515006 /* Signup.strings in Resources */,
0E0786DE1EFA7EAE00F77466 /* Components.plist in Resources */,
E501CBB32AE97EBA00515006 /* Signup.storyboard in Resources */,
Expand Down Expand Up @@ -5422,6 +5440,7 @@
E5C507702B0DEC2400200A6A /* AutolayoutViewController.swift in Sources */,
82CAB8F3255C0CD100BB08EF /* MessagesTileCollectionViewCell.swift in Sources */,
E5217F462AEACE0200123442 /* NavigationLogoView.swift in Sources */,
E55188952CB66BCA00E4C241 /* ForceUpdateViewController.swift in Sources */,
E58A45622BA8E373002A0704 /* LoginProvider.swift in Sources */,
E59E8FB02AEA7A81009278F5 /* MagicLinkLoginViewController.swift in Sources */,
0E3A352D1FD9CDC5000B0F99 /* Theme+App.swift in Sources */,
Expand Down Expand Up @@ -5516,6 +5535,7 @@
8272C6332657EE4E00D846A8 /* AutomationSettingsViewController.swift in Sources */,
E59E8FBB2AEA7A81009278F5 /* GDPRViewController.swift in Sources */,
DDF7F755240D35BA00A671C7 /* CustomServerSettingsViewController.swift in Sources */,
E55188932CB66BCA00E4C241 /* ForceUpdateViewController.swift in Sources */,
0ECF5C082017EBAD0047596C /* ThemeCode.swift in Sources */,
3545E98026AAD60C00B812CC /* ServerSelectionDelegate.swift in Sources */,
E5217F402AEAC7A900123442 /* Theme+LightPalette.swift in Sources */,
Expand Down
1 change: 0 additions & 1 deletion PIA VPN/AppDelegate.swift
Original file line number Diff line number Diff line change
Expand Up @@ -230,7 +230,6 @@ class AppDelegate: NSObject, UIApplicationDelegate {
let accountInformationVerifier = AccountInformationAvailabilityFactory.makeAccountInformationAvailabilityVerifier()

accountInformationVerifier.verifyAccountInformationAvailabity(after: AccountInformationAvailabilityVerifier.defaultDeadlineInSeconds, completion: nil)

}

private func refreshShortcutItems(in application: UIApplication) {
Expand Down
17 changes: 15 additions & 2 deletions PIA VPN/Bootstrapper.swift
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,11 @@ import TunnelKitOpenVPN
import PIAWireguard
#endif
import SwiftyBeaver
import UIKit

extension NSNotification.Name {
public static let __AppDidFetchForceUpdateFeatureFlag = Notification.Name("__AppDidFetchForceUpdateFeatureFlag")
}

class Bootstrapper {

Expand Down Expand Up @@ -105,7 +109,8 @@ class Bootstrapper {
Client.configuration.rsa4096Certificate = rsa4096Certificate()

#if PIA_DEV
Client.environment = AppPreferences.shared.appEnvironmentIsProduction ? .production : .staging
//Client.environment = AppPreferences.shared.appEnvironmentIsProduction ? .production : .staging
Client.environment = .staging
#else
Client.environment = AppConfiguration.clientEnvironment
#endif
Expand Down Expand Up @@ -163,11 +168,11 @@ class Bootstrapper {
AppPreferences.shared.disablesMultiDipTokens = Client.configuration.featureFlags.contains(Client.FeatureFlags.disableMultiDipTokens)
AppPreferences.shared.showNewInitialScreen = Client.configuration.featureFlags.contains(Client.FeatureFlags.showNewInitialScreen)


/// Updates the feature flags values to the ones set on the server only on Release builds.
/// (like Leak protection feature)
self.updateFeatureFlagsForReleaseIfNeeded()

self.checkForceUpdateIfNeeded()
})

//FORCE THE MIGRATION TO GEN4
Expand Down Expand Up @@ -327,3 +332,11 @@ class Bootstrapper {
#endif
}
}

extension Bootstrapper {
func checkForceUpdateIfNeeded() {
if Client.configuration.featureFlags.contains("force_update") {
NotificationCenter.default.post(name: Notification.Name.__AppDidFetchForceUpdateFeatureFlag, object: nil)
}
}
}
9 changes: 9 additions & 0 deletions PIA VPN/DashboardViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -133,6 +133,7 @@ class DashboardViewController: AutolayoutViewController {
nc.addObserver(self, selector: #selector(connectionVPNStatusDidChange(_:)), name: NSNotification.Name.NEVPNStatusDidChange, object: nil)
nc.addObserver(self, selector: #selector(handleDidConnectToRFC1918CompliantWifi(_:)), name: NSNotification.Name.DeviceDidConnectToRFC1918CompliantWifi, object: nil)
nc.addObserver(self, selector: #selector(checkConnectToRFC1918VulnerableWifi(_:)), name: NSNotification.Name.DeviceDidConnectToRFC1918VulnerableWifi, object: nil)
nc.addObserver(self, selector: #selector(presentForceUpdate), name: NSNotification.Name.__AppDidFetchForceUpdateFeatureFlag, object: nil)

self.viewContentHeight = self.viewContentHeightConstraint.constant
}
Expand Down Expand Up @@ -701,6 +702,14 @@ class DashboardViewController: AutolayoutViewController {
}
}

@objc func presentForceUpdate() {
let forceUpdate = ForceUpdateViewController()
forceUpdate.modalPresentationStyle = .fullScreen
DispatchQueue.main.async { [weak self] in
self?.present(forceUpdate, animated: false)
}
}

//MARK: Non compliant Wifi alert

private struct WifiAlertAction {
Expand Down
40 changes: 40 additions & 0 deletions PIA VPN/ForceUpdateViewController.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
//
// ForceUpdateViewController.swift
// PIA VPN
//
// Created by Said Rehouni on 9/10/24.
// Copyright © 2024 Private Internet Access Inc. All rights reserved.
//

import UIKit
import PIALibrary

class ForceUpdateViewController: UIViewController {
@IBOutlet weak var updateButton: PIAButton!
@IBOutlet weak var titleLabel: UILabel!
@IBOutlet weak var descriptionLabel: UILabel!


override func viewDidLoad() {
super.viewDidLoad()

// Do any additional setup after loading the view.

styleUpdateButton()

updateButton.addTarget(self, action: #selector(updateButtonTapped), for: .touchUpInside)
updateButton.setTitle("Update Now", for: .normal)
}

@objc func updateButtonTapped() {
Client.providers.vpnProvider.uninstallAll()
UIApplication.shared.open(URL(string: "https://itunes.apple.com/app/private-internet-access-anonymous/id955626407")!)
}

private func styleUpdateButton() {
updateButton.setRounded()
updateButton.style(style: TextStyle.Buttons.piaGreenButton)
updateButton.setTitle(L10n.Welcome.Purchase.submit.uppercased(),
for: [])
}
}
90 changes: 90 additions & 0 deletions PIA VPN/ForceUpdateViewController.xib
Original file line number Diff line number Diff line change
@@ -0,0 +1,90 @@
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="32700.99.1234" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
<device id="retina6_12" orientation="portrait" appearance="light"/>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="22685"/>
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<objects>
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="ForceUpdateViewController" customModule="PIA_VPN" customModuleProvider="target">
<connections>
<outlet property="descriptionLabel" destination="ecX-Zr-LdC" id="6Bv-B0-uO8"/>
<outlet property="titleLabel" destination="KbD-fS-iw2" id="zVZ-aP-q9i"/>
<outlet property="updateButton" destination="HLl-yh-l1E" id="goe-zj-ZRg"/>
<outlet property="view" destination="i5M-Pr-FkT" id="sfx-zR-JGt"/>
</connections>
</placeholder>
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
<view clearsContextBeforeDrawing="NO" contentMode="scaleToFill" id="i5M-Pr-FkT">
<rect key="frame" x="0.0" y="0.0" width="393" height="852"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
<subviews>
<stackView opaque="NO" tag="2" contentMode="scaleToFill" axis="vertical" alignment="center" spacing="24" translatesAutoresizingMaskIntoConstraints="NO" id="liw-vr-nmU">
<rect key="frame" x="20" y="119" width="353" height="639"/>
<subviews>
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" image="force_update_shield" translatesAutoresizingMaskIntoConstraints="NO" id="7dx-Zd-LvJ">
<rect key="frame" x="103.66666666666669" y="0.0" width="146" height="138"/>
<constraints>
<constraint firstAttribute="width" constant="146" id="DDI-PN-m5q"/>
<constraint firstAttribute="height" constant="138" id="XbN-Iz-yzO"/>
</constraints>
</imageView>
<stackView opaque="NO" contentMode="scaleToFill" axis="vertical" alignment="top" spacing="24" translatesAutoresizingMaskIntoConstraints="NO" id="FQV-ZF-r2m">
<rect key="frame" x="10.333333333333343" y="162" width="332.66666666666663" height="111.33333333333331"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Upgrade Your Experience" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="KbD-fS-iw2">
<rect key="frame" x="0.0" y="0.0" width="248.33333333333334" height="26.333333333333332"/>
<fontDescription key="fontDescription" type="system" weight="medium" pointSize="22"/>
<color key="textColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<nil key="highlightedColor"/>
</label>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="You’re using an older version of PIA. Update your app now to enjoy an enhanced experience with all the latest features." textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="ecX-Zr-LdC">
<rect key="frame" x="0.0" y="50.333333333333314" width="332.66666666666669" height="61"/>
<fontDescription key="fontDescription" type="system" weight="light" pointSize="17"/>
<color key="textColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<nil key="highlightedColor"/>
</label>
</subviews>
</stackView>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Ty5-Yz-511">
<rect key="frame" x="56.666666666666686" y="297.33333333333326" width="240" height="267.66666666666674"/>
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
</view>
<button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="system" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="HLl-yh-l1E" customClass="PIAButton" customModule="PIALibrary">
<rect key="frame" x="0.0" y="589" width="353" height="50"/>
<constraints>
<constraint firstAttribute="height" constant="50" id="Vt7-9x-RzF"/>
</constraints>
<color key="tintColor" red="0.99999600649999998" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<state key="normal" title="Button"/>
<buttonConfiguration key="configuration" style="plain" title="Button"/>
</button>
</subviews>
<constraints>
<constraint firstAttribute="trailing" secondItem="HLl-yh-l1E" secondAttribute="trailing" id="d0Y-di-7gB"/>
<constraint firstItem="HLl-yh-l1E" firstAttribute="leading" secondItem="liw-vr-nmU" secondAttribute="leading" id="qQa-K0-vqg"/>
</constraints>
</stackView>
</subviews>
<viewLayoutGuide key="safeArea" id="fnl-2z-Ty3"/>
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<constraints>
<constraint firstItem="fnl-2z-Ty3" firstAttribute="bottom" secondItem="liw-vr-nmU" secondAttribute="bottom" constant="60" id="DYi-Hx-NzJ"/>
<constraint firstItem="liw-vr-nmU" firstAttribute="leading" secondItem="fnl-2z-Ty3" secondAttribute="leading" constant="20" id="DsA-7H-Iv1"/>
<constraint firstItem="fnl-2z-Ty3" firstAttribute="trailing" secondItem="liw-vr-nmU" secondAttribute="trailing" constant="20" id="IJR-hN-7PH"/>
<constraint firstItem="liw-vr-nmU" firstAttribute="top" secondItem="fnl-2z-Ty3" secondAttribute="top" constant="60" id="z6E-K9-CBQ"/>
</constraints>
<point key="canvasLocation" x="139.69465648854961" y="20.422535211267608"/>
</view>
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFit" horizontalHuggingPriority="251" verticalHuggingPriority="251" id="joW-BT-sWM">
<rect key="frame" x="0.0" y="0.0" width="240" height="128"/>
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
<point key="canvasLocation" x="727" y="-15"/>
</imageView>
</objects>
<resources>
<image name="force_update_shield" width="146" height="138"/>
</resources>
</document>
15 changes: 15 additions & 0 deletions PIA VPN/Images.xcassets/force_update_shield.imageset/Contents.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
{
"images" : [
{
"filename" : "shield.pdf",
"idiom" : "universal"
}
],
"info" : {
"author" : "xcode",
"version" : 1
},
"properties" : {
"preserves-vector-representation" : true
}
}
Binary file not shown.
3 changes: 3 additions & 0 deletions PIA VPN/PIAHotspotHelper.swift
Original file line number Diff line number Diff line change
Expand Up @@ -71,6 +71,9 @@ class PIAHotspotHelper {
}
return NEHotspotHelper.register(options: options,
queue: DispatchQueue.main) { [weak self] (cmd: NEHotspotHelperCommand) in

guard !Client.configuration.featureFlags.contains("force_update") else { return }

if let weakSelf = self {
if cmd.commandType == .filterScanList {
log.info("filtering ssid list")
Expand Down
Loading

0 comments on commit 433e8e0

Please sign in to comment.