Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 40 additions & 6 deletions ApertureTokensManager.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@
objects = {

/* Begin PBXBuildFile section */
18CCDEB42F3E30D3006FEB50 /* Sparkle in Frameworks */ = {isa = PBXBuildFile; productRef = 18CCDEB32F3E30D3006FEB50 /* Sparkle */; };
18D87B2B2F28C30100D76485 /* ComposableArchitecture in Frameworks */ = {isa = PBXBuildFile; productRef = 18D87B2A2F28C30100D76485 /* ComposableArchitecture */; };
/* End PBXBuildFile section */

Expand All @@ -25,6 +26,16 @@
18D87B1B2F28C2CF00D76485 /* ApertureTokensManager.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = ApertureTokensManager.app; sourceTree = BUILT_PRODUCTS_DIR; };
/* End PBXFileReference section */

/* Begin PBXFileSystemSynchronizedBuildFileExceptionSet section */
18CCDEB62F3E3432006FEB50 /* Exceptions for "ApertureTokensManager" folder in "ApertureTokensManager" target */ = {
isa = PBXFileSystemSynchronizedBuildFileExceptionSet;
membershipExceptions = (
Info.plist,
);
target = 18D87B1A2F28C2CF00D76485 /* ApertureTokensManager */;
};
/* End PBXFileSystemSynchronizedBuildFileExceptionSet section */

/* Begin PBXFileSystemSynchronizedRootGroup section */
18610F382F337400005F2E4D /* ApertureTokensManagerTests */ = {
isa = PBXFileSystemSynchronizedRootGroup;
Expand All @@ -33,6 +44,9 @@
};
18D87B1D2F28C2CF00D76485 /* ApertureTokensManager */ = {
isa = PBXFileSystemSynchronizedRootGroup;
exceptions = (
18CCDEB62F3E3432006FEB50 /* Exceptions for "ApertureTokensManager" folder in "ApertureTokensManager" target */,
);
path = ApertureTokensManager;
sourceTree = "<group>";
};
Expand All @@ -51,6 +65,7 @@
buildActionMask = 2147483647;
files = (
18D87B2B2F28C30100D76485 /* ComposableArchitecture in Frameworks */,
18CCDEB42F3E30D3006FEB50 /* Sparkle in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
Expand Down Expand Up @@ -119,6 +134,7 @@
name = ApertureTokensManager;
packageProductDependencies = (
18D87B2A2F28C30100D76485 /* ComposableArchitecture */,
18CCDEB32F3E30D3006FEB50 /* Sparkle */,
);
productName = "Aperture Tokens Importer";
productReference = 18D87B1B2F28C2CF00D76485 /* ApertureTokensManager.app */;
Expand Down Expand Up @@ -154,6 +170,7 @@
minimizedProjectReferenceProxies = 1;
packageReferences = (
18D87B292F28C30100D76485 /* XCRemoteSwiftPackageReference "swift-composable-architecture" */,
18CCDEB22F3E30D3006FEB50 /* XCRemoteSwiftPackageReference "Sparkle" */,
);
preferredProjectObjectVersion = 77;
productRefGroup = 18D87B1C2F28C2CF00D76485 /* Products */;
Expand Down Expand Up @@ -391,15 +408,16 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
ASSETCATALOG_COMPILER_INCLUDE_ALL_APPICON_ASSETS = YES;
CODE_SIGN_ENTITLEMENTS = ApertureTokensManager/ApertureTokensManager.entitlements;
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 1;
CURRENT_PROJECT_VERSION = 2;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_TEAM = JFTEHE2V9R;
ENABLE_APP_SANDBOX = YES;
ENABLE_HARDENED_RUNTIME = YES;
ENABLE_INCOMING_NETWORK_CONNECTIONS = NO;
ENABLE_OUTGOING_NETWORK_CONNECTIONS = NO;
ENABLE_OUTGOING_NETWORK_CONNECTIONS = YES;
ENABLE_PREVIEWS = YES;
ENABLE_RESOURCE_ACCESS_AUDIO_INPUT = NO;
ENABLE_RESOURCE_ACCESS_BLUETOOTH = NO;
Expand All @@ -411,6 +429,7 @@
ENABLE_RESOURCE_ACCESS_USB = NO;
ENABLE_USER_SELECTED_FILES = readwrite;
GENERATE_INFOPLIST_FILE = YES;
INFOPLIST_FILE = ApertureTokensManager/Info.plist;
INFOPLIST_KEY_CFBundleDisplayName = "Aperture Tokens Manager";
"INFOPLIST_KEY_UIApplicationSceneManifest_Generation[sdk=iphoneos*]" = YES;
"INFOPLIST_KEY_UIApplicationSceneManifest_Generation[sdk=iphonesimulator*]" = YES;
Expand All @@ -426,7 +445,7 @@
LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks";
"LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks";
MACOSX_DEPLOYMENT_TARGET = 15.0;
MARKETING_VERSION = 1.0;
MARKETING_VERSION = 1.0.1;
PRODUCT_BUNDLE_IDENTIFIER = "com.looping-studio.ApertureTokensManager";
PRODUCT_NAME = "$(TARGET_NAME)";
REGISTER_APP_GROUPS = YES;
Expand All @@ -449,15 +468,16 @@
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
ASSETCATALOG_COMPILER_GLOBAL_ACCENT_COLOR_NAME = AccentColor;
ASSETCATALOG_COMPILER_INCLUDE_ALL_APPICON_ASSETS = YES;
CODE_SIGN_ENTITLEMENTS = ApertureTokensManager/ApertureTokensManager.entitlements;
"CODE_SIGN_IDENTITY[sdk=macosx*]" = "Apple Development";
CODE_SIGN_STYLE = Automatic;
CURRENT_PROJECT_VERSION = 1;
CURRENT_PROJECT_VERSION = 2;
DEAD_CODE_STRIPPING = YES;
DEVELOPMENT_TEAM = JFTEHE2V9R;
ENABLE_APP_SANDBOX = YES;
ENABLE_HARDENED_RUNTIME = YES;
ENABLE_INCOMING_NETWORK_CONNECTIONS = NO;
ENABLE_OUTGOING_NETWORK_CONNECTIONS = NO;
ENABLE_OUTGOING_NETWORK_CONNECTIONS = YES;
ENABLE_PREVIEWS = YES;
ENABLE_RESOURCE_ACCESS_AUDIO_INPUT = NO;
ENABLE_RESOURCE_ACCESS_BLUETOOTH = NO;
Expand All @@ -469,6 +489,7 @@
ENABLE_RESOURCE_ACCESS_USB = NO;
ENABLE_USER_SELECTED_FILES = readwrite;
GENERATE_INFOPLIST_FILE = YES;
INFOPLIST_FILE = ApertureTokensManager/Info.plist;
INFOPLIST_KEY_CFBundleDisplayName = "Aperture Tokens Manager";
"INFOPLIST_KEY_UIApplicationSceneManifest_Generation[sdk=iphoneos*]" = YES;
"INFOPLIST_KEY_UIApplicationSceneManifest_Generation[sdk=iphonesimulator*]" = YES;
Expand All @@ -484,7 +505,7 @@
LD_RUNPATH_SEARCH_PATHS = "@executable_path/Frameworks";
"LD_RUNPATH_SEARCH_PATHS[sdk=macosx*]" = "@executable_path/../Frameworks";
MACOSX_DEPLOYMENT_TARGET = 15.0;
MARKETING_VERSION = 1.0;
MARKETING_VERSION = 1.0.1;
PRODUCT_BUNDLE_IDENTIFIER = "com.looping-studio.ApertureTokensManager";
PRODUCT_NAME = "$(TARGET_NAME)";
REGISTER_APP_GROUPS = YES;
Expand Down Expand Up @@ -534,6 +555,14 @@
/* End XCConfigurationList section */

/* Begin XCRemoteSwiftPackageReference section */
18CCDEB22F3E30D3006FEB50 /* XCRemoteSwiftPackageReference "Sparkle" */ = {
isa = XCRemoteSwiftPackageReference;
repositoryURL = "https://github.com/sparkle-project/Sparkle";
requirement = {
kind = upToNextMajorVersion;
minimumVersion = 2.8.1;
};
};
18D87B292F28C30100D76485 /* XCRemoteSwiftPackageReference "swift-composable-architecture" */ = {
isa = XCRemoteSwiftPackageReference;
repositoryURL = "https://github.com/pointfreeco/swift-composable-architecture";
Expand All @@ -545,6 +574,11 @@
/* End XCRemoteSwiftPackageReference section */

/* Begin XCSwiftPackageProductDependency section */
18CCDEB32F3E30D3006FEB50 /* Sparkle */ = {
isa = XCSwiftPackageProductDependency;
package = 18CCDEB22F3E30D3006FEB50 /* XCRemoteSwiftPackageReference "Sparkle" */;
productName = Sparkle;
};
18D87B2A2F28C30100D76485 /* ComposableArchitecture */ = {
isa = XCSwiftPackageProductDependency;
package = 18D87B292F28C30100D76485 /* XCRemoteSwiftPackageReference "swift-composable-architecture" */;
Expand Down

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

11 changes: 11 additions & 0 deletions ApertureTokensManager/ApertureTokensManager.entitlements
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>com.apple.security.temporary-exception.mach-lookup.global-name</key>
<array>
<string>$(PRODUCT_BUNDLE_IDENTIFIER)-spks</string>
<string>$(PRODUCT_BUNDLE_IDENTIFIER)-spki</string>
</array>
</dict>
</plist>
44 changes: 44 additions & 0 deletions ApertureTokensManager/App/ApertureTokensManagerApp.swift
Original file line number Diff line number Diff line change
@@ -1,8 +1,47 @@
import Combine
import SwiftUI
import ComposableArchitecture

import Sparkle

// This view model class publishes when new updates can be checked by the user
final class CheckForUpdatesViewModel: ObservableObject {
@Published var canCheckForUpdates = false

init(updater: SPUUpdater) {
updater.publisher(for: \.canCheckForUpdates)
.assign(to: &$canCheckForUpdates)
}
}

// This is the view for the Check for Updates menu item
// Note this intermediate view is necessary for the disabled state on the menu item to work properly before Monterey.
// See https://stackoverflow.com/questions/68553092/menu-not-updating-swiftui-bug for more info
struct CheckForUpdatesView: View {
@ObservedObject private var checkForUpdatesViewModel: CheckForUpdatesViewModel
private let updater: SPUUpdater

init(updater: SPUUpdater) {
self.updater = updater

// Create our view model for our CheckForUpdatesView
self.checkForUpdatesViewModel = CheckForUpdatesViewModel(updater: updater)
}

var body: some View {
Button("Check for Updates…", action: updater.checkForUpdates)
.disabled(!checkForUpdatesViewModel.canCheckForUpdates)
}
}

@main
struct ApertureTokensManagerApp: App {
private let updaterController: SPUStandardUpdaterController
init() {
// If you want to start the updater manually, pass false to startingUpdater and call .startUpdater() later
// This is where you can also pass an updater delegate if you need one
updaterController = SPUStandardUpdaterController(startingUpdater: true, updaterDelegate: nil, userDriverDelegate: nil)
}
var body: some Scene {
WindowGroup {
AppView(
Expand All @@ -12,6 +51,11 @@ struct ApertureTokensManagerApp: App {
)
.frame(minWidth: 900, minHeight: 650)
}
.commands {
CommandGroup(after: .appInfo) {
CheckForUpdatesView(updater: updaterController.updater)
}
}
.defaultSize(width: 1100, height: 750)
}
}
12 changes: 12 additions & 0 deletions ApertureTokensManager/Info.plist
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>SUEnableInstallerLauncherService</key>
<true/>
<key>SUFeedURL</key>
<string>https://loopingstudio.github.io/ApertureTokenManager/appcast.xml</string>
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The URLs use "ApertureTokenManager" (without 's') while the app is named "ApertureTokensManager" (with 's'). Ensure that the GitHub repository name is actually "ApertureTokenManager" and that GitHub Pages is correctly configured at this URL, otherwise update checks will fail.

Suggested change
<string>https://loopingstudio.github.io/ApertureTokenManager/appcast.xml</string>
<string>https://loopingstudio.github.io/ApertureTokensManager/appcast.xml</string>

Copilot uses AI. Check for mistakes.
<key>SUPublicEDKey</key>
<string>AO8KvH4ISg6LNcdRlUJCjRYzHasX7GEhSPee9Y8GA8I=</string>
</dict>
</plist>
22 changes: 22 additions & 0 deletions appcast.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
<?xml version="1.0" standalone="yes"?>
<rss xmlns:sparkle="http://www.andymatuschak.org/xml-namespaces/sparkle" version="2.0">
<channel>
<title>ApertureTokensManager</title>
<item>
<title>1.0.1</title>
<pubDate>Fri, 16 Feb 2026 10:19:35 +0100</pubDate>
<sparkle:version>1</sparkle:version>
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The sparkle:version is set to "1" but the CURRENT_PROJECT_VERSION in the Xcode project is set to "2". These values should match to ensure Sparkle can properly compare version numbers. The sparkle:version should be "2" to match the build number in the project configuration.

Suggested change
<sparkle:version>1</sparkle:version>
<sparkle:version>2</sparkle:version>

Copilot uses AI. Check for mistakes.
<sparkle:shortVersionString>1.0.1</sparkle:shortVersionString>
<sparkle:minimumSystemVersion>15.0</sparkle:minimumSystemVersion>
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The minimum system version is set to 15.0, but this should be aligned with the actual deployment target. The Xcode project sets MACOSX_DEPLOYMENT_TARGET = 15.0, so this is consistent. However, ensure that Sparkle 2.8.1 supports macOS 15.0 as the minimum version.

Copilot uses AI. Check for mistakes.
<description><![CDATA[
<h2>What's New</h2>
<ul>
<li>Initial release of Aperture Tokens Manager.</li>
<li>Enjoy the first version of the app !</li>
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's an extra space before the exclamation mark in "the app !". In English, punctuation should typically be placed directly after the last word without a preceding space.

Suggested change
<li>Enjoy the first version of the app !</li>
<li>Enjoy the first version of the app!</li>

Copilot uses AI. Check for mistakes.
Comment on lines +14 to +15
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The release notes describe this as the "Initial release" which is inconsistent with the version number 1.0.1. An initial release should typically be version 1.0.0, or if this is version 1.0.1, the release notes should describe what's new in this update compared to 1.0.0.

Copilot uses AI. Check for mistakes.
</ul>
]]>
</description>
<enclosure url="https://github.com/LoopingStudio/ApertureTokenManager/releases/download/1.0.1/ApertureTokensManager.zip" length="7253356" type="application/octet-stream" sparkle:edSignature="pPTbrV1VW8MjuWMyeQxQh8MsYUYOaiX/qTw8WFdjmE1nzTgUy3QirBKVPenqXDifibe5BhosHD6XFsRvkn0xCQ=="/>
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The enclosure URL points to a GitHub release (1.0.1) that may not exist yet if this is the initial release adding Sparkle functionality. Ensure the release is created and the ZIP file is uploaded to GitHub releases before this version is distributed, otherwise update checks will fail.

Copilot uses AI. Check for mistakes.
Copy link

Copilot AI Feb 16, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The enclosure element is missing the required sparkle:version attribute. According to Sparkle 2.x documentation, the enclosure tag should include sparkle:version to specify the build number for the update package.

Suggested change
<enclosure url="https://github.com/LoopingStudio/ApertureTokenManager/releases/download/1.0.1/ApertureTokensManager.zip" length="7253356" type="application/octet-stream" sparkle:edSignature="pPTbrV1VW8MjuWMyeQxQh8MsYUYOaiX/qTw8WFdjmE1nzTgUy3QirBKVPenqXDifibe5BhosHD6XFsRvkn0xCQ=="/>
<enclosure url="https://github.com/LoopingStudio/ApertureTokenManager/releases/download/1.0.1/ApertureTokensManager.zip" length="7253356" type="application/octet-stream" sparkle:version="1" sparkle:edSignature="pPTbrV1VW8MjuWMyeQxQh8MsYUYOaiX/qTw8WFdjmE1nzTgUy3QirBKVPenqXDifibe5BhosHD6XFsRvkn0xCQ=="/>

Copilot uses AI. Check for mistakes.
</item>
</channel>
</rss>