Simplify development and maintenance immensely by making this a
monorepository:
- Convert PassepartoutKit and VPN bindings to local packages
- OpenVPN/OpenSSL
- WireGuard/Go
- Make PassepartoutKit available via
- Source submodule for production (private)
- [Binary XCFramework for
development](https://github.com/passepartoutvpn/passepartoutkit)
- Add PassepartoutKit Demo in root
- Deploy package later
The entitlement "clean-up" was pushed by the App Review, but this had
horrible consequences apparently.
In fact, the WireGuard Go adapter is unable to bind the UDP socket
without the "server" entitlement, making WireGuard on macOS silently
broken:
```
Unable to update bind: listen udp4 :0: bind: operation not permitted
```
Regression in #1042
Rather than redoing ProfileManager.observeLocal() altogether:
- Keep the existing profiles subscription (localSubscription)
- Reload ALL local profiles on NE notifications
The reload is "heavy" because each profile save causes a reload of ALL
profiles, but it's the most reliable approach and in the end, it only
takes 1-2msec. It can be improved later.
Partially reverts #1049, because the app did not sync when a VPN
configuration was deleted from the OS settings.
A tolerant way to cope with scattered approvals. That is, if a
platform build fails to upload, it will not prevent other
platforms from being sent to public_beta/app_review.
The app_store environment is also allowed despite errors, as the
platform builds may have been approved at different times.
This somehow deals with the lottery of getting an approval for
multiple platforms at the same time.
Fixes#1043
Especially useful on macOS and tvOS where Network Extension does not
retain this information when the profile is disabled. On these
platforms, there's no native way to tell the last used profile, so save
it to UserDefaults and fall back to it when tunnel.currentProfile is
nil.
This was not apparent on TestFlight, but features from single iOS and
macOS "Full version" purchases were not being credited on the Apple TV
because of the incomplete `#if` conditionals.
When level is .beta, it was relying on beta receipt exclusively without
falling back to production receipt.
This was preventing the sandbox receipt ("production" in TestFlight)
from being read unless the AppUserLevel was explicitly set to .freemium
(0).
The remote container is shared by ProfileManager and
PreferencesManager, but it must be the same for CloudKit sync
to work properly.
Externalize the logic of onEligibleFeatures() so that the
AppContext singleton can update the managers (and their
repositories) with the new remote store.
Now that the remote profile repository is reloaded every time that
eligible features change, the .removeDuplicates() may also be
restored. Just add a .dropFirst() to skip the initially empty
value of eligible features. Even when features are eventually empty,
a value is always emitted after IAPManager.reloadReceipt()
Lastly, enable Core Data lightweight migration.
Regressions from #1017
Only offer compensations to former purchasers:
- .appleTV to .full purchasers
- .full to .appleTV purchasers
Always suggest .fullTV to new purchasers.
Finally rename:
- .full to .iOS_macOS
- .fullTV to .allFeatures (lifetime)