From df0d40c556bea14cb76269a66d638662375bd630 Mon Sep 17 00:00:00 2001 From: Davide De Rosa Date: Sat, 25 Jun 2022 11:59:32 +0200 Subject: [PATCH] Add launcher target - Launch main app in background then die - Do not launch app if already running - Launch app binary relative to launcher location --- Config.xcconfig | 1 + Passepartout.xcodeproj/project.pbxproj | 162 +++++++++++++++++- .../xcschemes/PassepartoutLauncher.xcscheme | 78 +++++++++ Passepartout/App/Info.plist | 2 +- Passepartout/Launcher/AppDelegate.swift | 52 ++++++ .../Constants/Constants+Launcher.swift | 44 +++++ Passepartout/Launcher/Info.plist | 24 +++ Passepartout/Launcher/Launcher.entitlements | 10 ++ .../Launcher/PassepartoutLauncherApp.swift | 37 ++++ 9 files changed, 403 insertions(+), 7 deletions(-) create mode 100644 Passepartout.xcodeproj/xcshareddata/xcschemes/PassepartoutLauncher.xcscheme create mode 100644 Passepartout/Launcher/AppDelegate.swift create mode 100644 Passepartout/Launcher/Constants/Constants+Launcher.swift create mode 100644 Passepartout/Launcher/Info.plist create mode 100644 Passepartout/Launcher/Launcher.entitlements create mode 100644 Passepartout/Launcher/PassepartoutLauncherApp.swift diff --git a/Config.xcconfig b/Config.xcconfig index d7365b6d..79384feb 100644 --- a/Config.xcconfig +++ b/Config.xcconfig @@ -28,6 +28,7 @@ CFG_TEAM_ID = DTDYD63ZX9 CFG_APP_ID = com.algoritmico.ios.Passepartout +CFG_LAUNCHER_ID = com.algoritmico.ios.PassepartoutLauncher CFG_GROUP_ID = com.algoritmico.Passepartout CFG_APPSTORE_ID = 1433648537 CFG_COPYRIGHT = Copyright © 2022 Davide De Rosa. All rights reserved. diff --git a/Passepartout.xcodeproj/project.pbxproj b/Passepartout.xcodeproj/project.pbxproj index 88a266ec..0eeb95ed 100644 --- a/Passepartout.xcodeproj/project.pbxproj +++ b/Passepartout.xcodeproj/project.pbxproj @@ -40,6 +40,9 @@ 0E3B7FDA27E51A0200C66F13 /* ProfileView+Provider.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E3B7FD927E51A0200C66F13 /* ProfileView+Provider.swift */; }; 0E3CD47F280DA14B007075C0 /* AddProfileMenu.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E3CD47E280DA14B007075C0 /* AddProfileMenu.swift */; }; 0E3CD483280DAE92007075C0 /* ProfileView+MainMenu.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E3CD482280DAE92007075C0 /* ProfileView+MainMenu.swift */; }; + 0E41BD9A286711C3006346B4 /* PassepartoutLauncherApp.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E41BD99286711C3006346B4 /* PassepartoutLauncherApp.swift */; }; + 0E41BDA72867128A006346B4 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E41BDA62867128A006346B4 /* AppDelegate.swift */; }; + 0E41BDA928671356006346B4 /* PassepartoutLauncher.app in Embed Launcher */ = {isa = PBXBuildFile; fileRef = 0E41BD97286711C3006346B4 /* PassepartoutLauncher.app */; platformFilter = maccatalyst; settings = {ATTRIBUTES = (RemoveHeadersOnCopy, ); }; }; 0E44689627B051C300A14CE4 /* ProfileView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E44689527B051C300A14CE4 /* ProfileView.swift */; }; 0E44689C27B11B5300A14CE4 /* AboutView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E44689B27B11B5300A14CE4 /* AboutView.swift */; }; 0E49F6BB27D7638300385834 /* EndpointAdvancedView+OpenVPN.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0E49F6BA27D7638300385834 /* EndpointAdvancedView+OpenVPN.swift */; }; @@ -113,6 +116,8 @@ 0ED30DDD27EA35230057D8A3 /* Constants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0EB17EA127D2263700D473B5 /* Constants.swift */; }; 0ED31C3A20CF39510027975F /* NetworkExtension.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 0ED31C3920CF39510027975F /* NetworkExtension.framework */; }; 0ED7D62F2867328A009F2F8F /* Constants+Library.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0ED7D62E2867328A009F2F8F /* Constants+Library.swift */; }; + 0ED7D632286733AF009F2F8F /* Constants+Launcher.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0ED7D631286733AF009F2F8F /* Constants+Launcher.swift */; }; + 0ED7D633286733D8009F2F8F /* Constants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0EB17EA127D2263700D473B5 /* Constants.swift */; }; 0ED89C1527DE0A0C008B36D6 /* Shortcut.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0ED89C1427DE0A0C008B36D6 /* Shortcut.swift */; }; 0ED89C1727DE0E05008B36D6 /* IntentEditView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0ED89C1627DE0E05008B36D6 /* IntentEditView.swift */; }; 0ED89C1C27DE3ABC008B36D6 /* ShortcutsView+Add.swift in Sources */ = {isa = PBXBuildFile; fileRef = 0ED89C1B27DE3ABC008B36D6 /* ShortcutsView+Add.swift */; }; @@ -131,6 +136,13 @@ /* End PBXBuildFile section */ /* Begin PBXContainerItemProxy section */ + 0E41BDAA286713F6006346B4 /* PBXContainerItemProxy */ = { + isa = PBXContainerItemProxy; + containerPortal = 0E57F63020C83FC5008323CF /* Project object */; + proxyType = 1; + remoteGlobalIDString = 0E41BD96286711C3006346B4; + remoteInfo = PassepartoutLauncher; + }; 0EB2B1492733FB6F007705AB /* PBXContainerItemProxy */ = { isa = PBXContainerItemProxy; containerPortal = 0E57F63020C83FC5008323CF /* Project object */; @@ -162,14 +174,15 @@ /* End PBXContainerItemProxy section */ /* Begin PBXCopyFilesBuildPhase section */ - 0E3152B7223F9EF500F61841 /* Embed Frameworks */ = { + 0E41BDA828671339006346B4 /* Embed Launcher */ = { isa = PBXCopyFilesBuildPhase; buildActionMask = 2147483647; - dstPath = ""; - dstSubfolderSpec = 10; + dstPath = Contents/Library/LoginItems; + dstSubfolderSpec = 1; files = ( + 0E41BDA928671356006346B4 /* PassepartoutLauncher.app in Embed Launcher */, ); - name = "Embed Frameworks"; + name = "Embed Launcher"; runOnlyForDeploymentPostprocessing = 0; }; 0EB2B14B2733FB6F007705AB /* Embed App Extensions */ = { @@ -223,6 +236,11 @@ 0E3B7FD927E51A0200C66F13 /* ProfileView+Provider.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "ProfileView+Provider.swift"; sourceTree = ""; }; 0E3CD47E280DA14B007075C0 /* AddProfileMenu.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AddProfileMenu.swift; sourceTree = ""; }; 0E3CD482280DAE92007075C0 /* ProfileView+MainMenu.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "ProfileView+MainMenu.swift"; sourceTree = ""; }; + 0E41BD97286711C3006346B4 /* PassepartoutLauncher.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = PassepartoutLauncher.app; sourceTree = BUILT_PRODUCTS_DIR; }; + 0E41BD99286711C3006346B4 /* PassepartoutLauncherApp.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = PassepartoutLauncherApp.swift; sourceTree = ""; }; + 0E41BDA2286711C6006346B4 /* Launcher.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Launcher.entitlements; sourceTree = ""; }; + 0E41BDA62867128A006346B4 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; }; + 0E41BDAC286715A7006346B4 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 0E44689527B051C300A14CE4 /* ProfileView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ProfileView.swift; sourceTree = ""; }; 0E44689B27B11B5300A14CE4 /* AboutView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AboutView.swift; sourceTree = ""; }; 0E49F6BA27D7638300385834 /* EndpointAdvancedView+OpenVPN.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "EndpointAdvancedView+OpenVPN.swift"; sourceTree = ""; }; @@ -325,6 +343,7 @@ 0ED31C3920CF39510027975F /* NetworkExtension.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = NetworkExtension.framework; path = System/Library/Frameworks/NetworkExtension.framework; sourceTree = SDKROOT; }; 0ED31C3B20CF39510027975F /* Tunnel.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Tunnel.entitlements; sourceTree = ""; }; 0ED7D62E2867328A009F2F8F /* Constants+Library.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; name = "Constants+Library.swift"; path = "Passepartout/App/Constants/Constants+Library.swift"; sourceTree = SOURCE_ROOT; }; + 0ED7D631286733AF009F2F8F /* Constants+Launcher.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "Constants+Launcher.swift"; sourceTree = ""; }; 0ED89C1427DE0A0C008B36D6 /* Shortcut.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Shortcut.swift; sourceTree = ""; }; 0ED89C1627DE0E05008B36D6 /* IntentEditView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = IntentEditView.swift; sourceTree = ""; }; 0ED89C1B27DE3ABC008B36D6 /* ShortcutsView+Add.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "ShortcutsView+Add.swift"; sourceTree = ""; }; @@ -346,6 +365,13 @@ /* End PBXFileReference section */ /* Begin PBXFrameworksBuildPhase section */ + 0E41BD94286711C3006346B4 /* Frameworks */ = { + isa = PBXFrameworksBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; 0E57F63520C83FC5008323CF /* Frameworks */ = { isa = PBXFrameworksBuildPhase; buildActionMask = 2147483647; @@ -493,6 +519,18 @@ path = Views; sourceTree = ""; }; + 0E41BD98286711C3006346B4 /* Launcher */ = { + isa = PBXGroup; + children = ( + 0ED7D630286733A1009F2F8F /* Constants */, + 0E41BDA2286711C6006346B4 /* Launcher.entitlements */, + 0E41BDAC286715A7006346B4 /* Info.plist */, + 0E41BDA62867128A006346B4 /* AppDelegate.swift */, + 0E41BD99286711C3006346B4 /* PassepartoutLauncherApp.swift */, + ); + path = Launcher; + sourceTree = ""; + }; 0E49F6C927DB398100385834 /* Extensions */ = { isa = PBXGroup; children = ( @@ -522,6 +560,7 @@ 0E57F63820C83FC5008323CF /* Passepartout.app */, 0EDE8DBF20C86910004C739C /* PassepartoutOpenVPNTunnel.appex */, 0ED2B34A27D3C77800FD8EA9 /* PassepartoutWireGuardTunnel.appex */, + 0E41BD97286711C3006346B4 /* PassepartoutLauncher.app */, ); name = Products; sourceTree = ""; @@ -637,6 +676,14 @@ path = Constants; sourceTree = ""; }; + 0ED7D630286733A1009F2F8F /* Constants */ = { + isa = PBXGroup; + children = ( + 0ED7D631286733AF009F2F8F /* Constants+Launcher.swift */, + ); + path = Constants; + sourceTree = ""; + }; 0EDE8DC020C86910004C739C /* Tunnel */ = { isa = PBXGroup; children = ( @@ -686,6 +733,23 @@ /* End PBXLegacyTarget section */ /* Begin PBXNativeTarget section */ + 0E41BD96286711C3006346B4 /* PassepartoutLauncher */ = { + isa = PBXNativeTarget; + buildConfigurationList = 0E41BDA3286711C6006346B4 /* Build configuration list for PBXNativeTarget "PassepartoutLauncher" */; + buildPhases = ( + 0E41BD93286711C3006346B4 /* Sources */, + 0E41BD94286711C3006346B4 /* Frameworks */, + 0E41BD95286711C3006346B4 /* Resources */, + ); + buildRules = ( + ); + dependencies = ( + ); + name = PassepartoutLauncher; + productName = PassepartoutLauncher; + productReference = 0E41BD97286711C3006346B4 /* PassepartoutLauncher.app */; + productType = "com.apple.product-type.application"; + }; 0E57F63720C83FC5008323CF /* Passepartout */ = { isa = PBXNativeTarget; buildConfigurationList = 0E57F65520C83FC7008323CF /* Build configuration list for PBXNativeTarget "Passepartout" */; @@ -694,13 +758,14 @@ 0E57F63420C83FC5008323CF /* Sources */, 0E57F63520C83FC5008323CF /* Frameworks */, 0E57F63620C83FC5008323CF /* Resources */, - 0E3152B7223F9EF500F61841 /* Embed Frameworks */, + 0E41BDA828671339006346B4 /* Embed Launcher */, 0EB2B14B2733FB6F007705AB /* Embed App Extensions */, 0EBEF138274E4C7F00EAC689 /* Drop Extra Frameworks In Extensions */, ); buildRules = ( ); dependencies = ( + 0E41BDAB286713F6006346B4 /* PBXTargetDependency */, 0ECF71FC27B6DA6700CDB528 /* PBXTargetDependency */, 0EB2B14A2733FB6F007705AB /* PBXTargetDependency */, 0ED2B36227D3C99100FD8EA9 /* PBXTargetDependency */, @@ -761,10 +826,13 @@ 0E57F63020C83FC5008323CF /* Project object */ = { isa = PBXProject; attributes = { - LastSwiftUpdateCheck = 1230; + LastSwiftUpdateCheck = 1340; LastUpgradeCheck = 1240; ORGANIZATIONNAME = "Davide De Rosa"; TargetAttributes = { + 0E41BD96286711C3006346B4 = { + CreatedOnToolsVersion = 13.4; + }; 0E57F63720C83FC5008323CF = { CreatedOnToolsVersion = 9.4; LastSwiftMigration = 1020; @@ -828,6 +896,7 @@ projectRoot = ""; targets = ( 0E57F63720C83FC5008323CF /* Passepartout */, + 0E41BD96286711C3006346B4 /* PassepartoutLauncher */, 0EDE8DBE20C86910004C739C /* OpenVPNTunnel */, 0ECF71F327B6D9CD00CDB528 /* WireGuardGo */, 0ED2B33E27D3C77800FD8EA9 /* WireGuardTunnel */, @@ -836,6 +905,13 @@ /* End PBXProject section */ /* Begin PBXResourcesBuildPhase section */ + 0E41BD95286711C3006346B4 /* Resources */ = { + isa = PBXResourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + ); + runOnlyForDeploymentPostprocessing = 0; + }; 0E57F63620C83FC5008323CF /* Resources */ = { isa = PBXResourcesBuildPhase; buildActionMask = 2147483647; @@ -907,6 +983,17 @@ /* End PBXShellScriptBuildPhase section */ /* Begin PBXSourcesBuildPhase section */ + 0E41BD93286711C3006346B4 /* Sources */ = { + isa = PBXSourcesBuildPhase; + buildActionMask = 2147483647; + files = ( + 0ED7D632286733AF009F2F8F /* Constants+Launcher.swift in Sources */, + 0E41BDA72867128A006346B4 /* AppDelegate.swift in Sources */, + 0E41BD9A286711C3006346B4 /* PassepartoutLauncherApp.swift in Sources */, + 0ED7D633286733D8009F2F8F /* Constants.swift in Sources */, + ); + runOnlyForDeploymentPostprocessing = 0; + }; 0E57F63420C83FC5008323CF /* Sources */ = { isa = PBXSourcesBuildPhase; buildActionMask = 2147483647; @@ -1036,6 +1123,12 @@ /* End PBXSourcesBuildPhase section */ /* Begin PBXTargetDependency section */ + 0E41BDAB286713F6006346B4 /* PBXTargetDependency */ = { + isa = PBXTargetDependency; + platformFilter = maccatalyst; + target = 0E41BD96286711C3006346B4 /* PassepartoutLauncher */; + targetProxy = 0E41BDAA286713F6006346B4 /* PBXContainerItemProxy */; + }; 0EB2B14A2733FB6F007705AB /* PBXTargetDependency */ = { isa = PBXTargetDependency; target = 0EDE8DBE20C86910004C739C /* OpenVPNTunnel */; @@ -1120,6 +1213,54 @@ /* End PBXVariantGroup section */ /* Begin XCBuildConfiguration section */ + 0E41BDA4286711C6006346B4 /* Debug */ = { + isa = XCBuildConfiguration; + buildSettings = { + CLANG_CXX_LANGUAGE_STANDARD = "gnu++17"; + CODE_SIGN_ENTITLEMENTS = Passepartout/Launcher/Launcher.entitlements; + CODE_SIGN_STYLE = Manual; + COMBINE_HIDPI_IMAGES = YES; + COPY_PHASE_STRIP = NO; + DEVELOPMENT_TEAM = DTDYD63ZX9; + ENABLE_HARDENED_RUNTIME = YES; + INFOPLIST_FILE = Passepartout/Launcher/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + PRODUCT_BUNDLE_IDENTIFIER = "$(CFG_LAUNCHER_ID)"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SDKROOT = macosx; + SKIP_INSTALL = YES; + SWIFT_EMIT_LOC_STRINGS = YES; + SWIFT_VERSION = 5.0; + }; + name = Debug; + }; + 0E41BDA5286711C6006346B4 /* Release */ = { + isa = XCBuildConfiguration; + buildSettings = { + CLANG_CXX_LANGUAGE_STANDARD = "gnu++17"; + CODE_SIGN_ENTITLEMENTS = Passepartout/Launcher/Launcher.entitlements; + CODE_SIGN_STYLE = Manual; + COMBINE_HIDPI_IMAGES = YES; + COPY_PHASE_STRIP = NO; + DEVELOPMENT_TEAM = DTDYD63ZX9; + ENABLE_HARDENED_RUNTIME = YES; + INFOPLIST_FILE = Passepartout/Launcher/Info.plist; + LD_RUNPATH_SEARCH_PATHS = ( + "$(inherited)", + "@executable_path/../Frameworks", + ); + PRODUCT_BUNDLE_IDENTIFIER = "$(CFG_LAUNCHER_ID)"; + PRODUCT_NAME = "$(TARGET_NAME)"; + SDKROOT = macosx; + SKIP_INSTALL = YES; + SWIFT_EMIT_LOC_STRINGS = YES; + SWIFT_VERSION = 5.0; + }; + name = Release; + }; 0E57F65320C83FC7008323CF /* Debug */ = { isa = XCBuildConfiguration; baseConfigurationReference = 0E23B4A12298559800304C30 /* Config.xcconfig */; @@ -1421,6 +1562,15 @@ /* End XCBuildConfiguration section */ /* Begin XCConfigurationList section */ + 0E41BDA3286711C6006346B4 /* Build configuration list for PBXNativeTarget "PassepartoutLauncher" */ = { + isa = XCConfigurationList; + buildConfigurations = ( + 0E41BDA4286711C6006346B4 /* Debug */, + 0E41BDA5286711C6006346B4 /* Release */, + ); + defaultConfigurationIsVisible = 0; + defaultConfigurationName = Release; + }; 0E57F63320C83FC5008323CF /* Build configuration list for PBXProject "Passepartout" */ = { isa = XCConfigurationList; buildConfigurations = ( diff --git a/Passepartout.xcodeproj/xcshareddata/xcschemes/PassepartoutLauncher.xcscheme b/Passepartout.xcodeproj/xcshareddata/xcschemes/PassepartoutLauncher.xcscheme new file mode 100644 index 00000000..c7e34cc8 --- /dev/null +++ b/Passepartout.xcodeproj/xcshareddata/xcschemes/PassepartoutLauncher.xcscheme @@ -0,0 +1,78 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Passepartout/App/Info.plist b/Passepartout/App/Info.plist index 94a84732..325893cb 100644 --- a/Passepartout/App/Info.plist +++ b/Passepartout/App/Info.plist @@ -24,7 +24,7 @@ CFBundleExecutable $(EXECUTABLE_NAME) CFBundleIdentifier - $(PRODUCT_BUNDLE_IDENTIFIER) + $(CFG_APP_ID) CFBundleInfoDictionaryVersion 6.0 CFBundleName diff --git a/Passepartout/Launcher/AppDelegate.swift b/Passepartout/Launcher/AppDelegate.swift new file mode 100644 index 00000000..7aaf165d --- /dev/null +++ b/Passepartout/Launcher/AppDelegate.swift @@ -0,0 +1,52 @@ +// +// AppDelegate.swift +// Passepartout +// +// Created by Davide De Rosa on 6/25/22. +// Copyright (c) 2022 Davide De Rosa. All rights reserved. +// +// https://github.com/passepartoutvpn +// +// This file is part of Passepartout. +// +// Passepartout is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Passepartout is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with Passepartout. If not, see . +// + +import Foundation +import AppKit + +class AppDelegate: NSObject, NSApplicationDelegate, ObservableObject { + private let appURL = Constants.Launcher.appURL + + private var isAppRunning: Bool { + NSWorkspace.shared.runningApplications.contains { + $0.bundleIdentifier == Constants.Launcher.appId + } + } + + func applicationDidFinishLaunching(_ notification: Notification) { + guard !isAppRunning else { + NSApp.terminate(nil) + return + } + Task { + do { + try await NSWorkspace.shared.openApplication(at: appURL, configuration: .init()) + } catch { + NSLog("Unable to launch main app: \(error)") + } + await NSApp.terminate(nil) + } + } +} diff --git a/Passepartout/Launcher/Constants/Constants+Launcher.swift b/Passepartout/Launcher/Constants/Constants+Launcher.swift new file mode 100644 index 00000000..a38e1f60 --- /dev/null +++ b/Passepartout/Launcher/Constants/Constants+Launcher.swift @@ -0,0 +1,44 @@ +// +// Constants+Launcher.swift +// Passepartout +// +// Created by Davide De Rosa on 6/25/22. +// Copyright (c) 2022 Davide De Rosa. All rights reserved. +// +// https://github.com/passepartoutvpn +// +// This file is part of Passepartout. +// +// Passepartout is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Passepartout is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with Passepartout. If not, see . +// + +import Foundation + +extension Constants { + enum Launcher { + static let appId = "com.algoritmico.ios.Passepartout" + + static let appURL: URL = { + let url = URL(fileURLWithPath: Bundle.main.bundlePath) + var components = url.pathComponents + components.removeLast() + components.removeLast() + components.removeLast() + components.append("MacOS") + components.append(Constants.Global.appName) + let newPath = NSString.path(withComponents: components) + return URL(fileURLWithPath: newPath) + }() + } +} diff --git a/Passepartout/Launcher/Info.plist b/Passepartout/Launcher/Info.plist new file mode 100644 index 00000000..c4ed38c8 --- /dev/null +++ b/Passepartout/Launcher/Info.plist @@ -0,0 +1,24 @@ + + + + + CFBundleShortVersionString + 2.0.0 + CFBundleVersion + 3240 + LSBackgroundOnly + + CFBundleIdentifier + $(PRODUCT_BUNDLE_IDENTIFIER) + CFBundleName + $(PRODUCT_NAME) + CFBundleDevelopmentRegion + $(DEVELOPMENT_LANGUAGE) + CFBundleInfoDictionaryVersion + 6.0 + CFBundleExecutable + $(EXECUTABLE_NAME) + CFBundlePackageType + $(PRODUCT_BUNDLE_PACKAGE_TYPE) + + diff --git a/Passepartout/Launcher/Launcher.entitlements b/Passepartout/Launcher/Launcher.entitlements new file mode 100644 index 00000000..f2ef3ae0 --- /dev/null +++ b/Passepartout/Launcher/Launcher.entitlements @@ -0,0 +1,10 @@ + + + + + com.apple.security.app-sandbox + + com.apple.security.files.user-selected.read-only + + + diff --git a/Passepartout/Launcher/PassepartoutLauncherApp.swift b/Passepartout/Launcher/PassepartoutLauncherApp.swift new file mode 100644 index 00000000..6233c4e6 --- /dev/null +++ b/Passepartout/Launcher/PassepartoutLauncherApp.swift @@ -0,0 +1,37 @@ +// +// PassepartoutLauncherApp.swift +// Passepartout +// +// Created by Davide De Rosa on 6/25/22. +// Copyright (c) 2022 Davide De Rosa. All rights reserved. +// +// https://github.com/passepartoutvpn +// +// This file is part of Passepartout. +// +// Passepartout is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Passepartout is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with Passepartout. If not, see . +// + +import SwiftUI + +@main +struct PassepartoutLauncherApp: App { + @NSApplicationDelegateAdaptor(AppDelegate.self) private var appDelegate + + var body: some Scene { + WindowGroup { + EmptyView() + } + } +}