Release 1.0.0 !51

merged merged by cmc on 2026-10-19 06:46 UTC · krz/moonrise:release-1.0.0 into main

6 files changed, +95 −15

Layout: unified · split

App/README.org +14
@@ -15,3 +15,17 @@ subsystem =sh.krz.moonrise=.
15Backend: both configurations use https://moonrise-server.audit-labs.workers.dev 15Backend: both configurations use https://moonrise-server.audit-labs.workers.dev
16(=MOONRISE_API_URL= in =project.yml=). For a local Worker, set it to 16(=MOONRISE_API_URL= in =project.yml=). For a local Worker, set it to
17=http://localhost:8787= and regenerate. 17=http://localhost:8787= and regenerate.
18
19* Release
20
21#+begin_src sh
22scripts/release-ios.sh
23#+end_src
24
25Run from a clean =main=. It regenerates the project, archives the iPhone
26app with its widgets and the Watch app, and uploads it to App Store
27Connect, signed through the Apple ID in Xcode. The version is
28=MARKETING_VERSION= in =project.yml=; the build number is
29=git rev-list --count HEAD=, so each build maps to a commit.
30=MOONRISE_PUBLISH=0= exports the =.ipa= to =.build/ios-release= without
31uploading. The visionOS app is a separate product and is not uploaded.
App/Sources/InAppBrowser.swift −1
@@ -9,7 +9,6 @@ enum InAppBrowser {
9 static let action = OpenURLAction { url in 9 static let action = OpenURLAction { url in
10 guard url.scheme == "https" || url.scheme == "http", let top = topViewController() else { return .systemAction } 10 guard url.scheme == "https" || url.scheme == "http", let top = topViewController() else { return .systemAction }
11 let safari = SFSafariViewController(url: url) 11 let safari = SFSafariViewController(url: url)
12 safari.preferredControlTintColor = UIColor(red: 0.88, green: 0.24, blue: 0.19, alpha: 1)
13 safari.dismissButtonStyle = .done 12 safari.dismissButtonStyle = .done
14 top.present(safari, animated: true) 13 top.present(safari, animated: true)
15 return .handled 14 return .handled
App/Watch/Widgets-Info.plist +2 −2
@@ -17,9 +17,9 @@
17 <key>CFBundlePackageType</key> 17 <key>CFBundlePackageType</key>
18 <string>XPC!</string> 18 <string>XPC!</string>
19 <key>CFBundleShortVersionString</key> 19 <key>CFBundleShortVersionString</key>
20 <string>1.0</string> 20 <string>$(MARKETING_VERSION)</string>
21 <key>CFBundleVersion</key> 21 <key>CFBundleVersion</key>
22 <string>1</string> 22 <string>$(CURRENT_PROJECT_VERSION)</string>
23 <key>NSExtension</key> 23 <key>NSExtension</key>
24 <dict> 24 <dict>
25 <key>NSExtensionPointIdentifier</key> 25 <key>NSExtensionPointIdentifier</key>
App/Widgets/Info.plist +2 −2
@@ -17,9 +17,9 @@
17 <key>CFBundlePackageType</key> 17 <key>CFBundlePackageType</key>
18 <string>XPC!</string> 18 <string>XPC!</string>
19 <key>CFBundleShortVersionString</key> 19 <key>CFBundleShortVersionString</key>
20 <string>1.0</string> 20 <string>$(MARKETING_VERSION)</string>
21 <key>CFBundleVersion</key> 21 <key>CFBundleVersion</key>
22 <string>1</string> 22 <string>$(CURRENT_PROJECT_VERSION)</string>
23 <key>NSExtension</key> 23 <key>NSExtension</key>
24 <dict> 24 <dict>
25 <key>NSExtensionPointIdentifier</key> 25 <key>NSExtensionPointIdentifier</key>
App/project.yml +14 −10
@@ -54,8 +54,8 @@ targets:
54 CODE_SIGN_STYLE: Automatic 54 CODE_SIGN_STYLE: Automatic
55 SWIFT_VERSION: "6.0" 55 SWIFT_VERSION: "6.0"
56 TARGETED_DEVICE_FAMILY: "1,2" 56 TARGETED_DEVICE_FAMILY: "1,2"
57 MARKETING_VERSION: "1.0" 57 MARKETING_VERSION: "1.0.0"
58 CURRENT_PROJECT_VERSION: "1" 58 CURRENT_PROJECT_VERSION: "52"
59 GENERATE_INFOPLIST_FILE: YES 59 GENERATE_INFOPLIST_FILE: YES
60 INFOPLIST_KEY_CFBundleDisplayName: Moonrise 60 INFOPLIST_KEY_CFBundleDisplayName: Moonrise
61 INFOPLIST_KEY_NSSupportsLiveActivities: YES 61 INFOPLIST_KEY_NSSupportsLiveActivities: YES
@@ -83,6 +83,8 @@ targets:
83 path: Widgets/Info.plist 83 path: Widgets/Info.plist
84 properties: 84 properties:
85 CFBundleDisplayName: Moonrise 85 CFBundleDisplayName: Moonrise
86 CFBundleShortVersionString: $(MARKETING_VERSION)
87 CFBundleVersion: $(CURRENT_PROJECT_VERSION)
86 NSWidgetWantsLocation: true 88 NSWidgetWantsLocation: true
87 NSExtension: 89 NSExtension:
88 NSExtensionPointIdentifier: com.apple.widgetkit-extension 90 NSExtensionPointIdentifier: com.apple.widgetkit-extension
@@ -93,8 +95,8 @@ targets:
93 CODE_SIGN_STYLE: Automatic 95 CODE_SIGN_STYLE: Automatic
94 SWIFT_VERSION: "6.0" 96 SWIFT_VERSION: "6.0"
95 TARGETED_DEVICE_FAMILY: "1,2" 97 TARGETED_DEVICE_FAMILY: "1,2"
96 MARKETING_VERSION: "1.0" 98 MARKETING_VERSION: "1.0.0"
97 CURRENT_PROJECT_VERSION: "1" 99 CURRENT_PROJECT_VERSION: "52"
98 MoonriseWatch: 100 MoonriseWatch:
99 type: application 101 type: application
100 platform: watchOS 102 platform: watchOS
@@ -111,8 +113,8 @@ targets:
111 DEVELOPMENT_TEAM: ZCNAX3VL9D 113 DEVELOPMENT_TEAM: ZCNAX3VL9D
112 CODE_SIGN_STYLE: Automatic 114 CODE_SIGN_STYLE: Automatic
113 SWIFT_VERSION: "6.0" 115 SWIFT_VERSION: "6.0"
114 MARKETING_VERSION: "1.0" 116 MARKETING_VERSION: "1.0.0"
115 CURRENT_PROJECT_VERSION: "1" 117 CURRENT_PROJECT_VERSION: "52"
116 GENERATE_INFOPLIST_FILE: YES 118 GENERATE_INFOPLIST_FILE: YES
117 INFOPLIST_KEY_CFBundleDisplayName: Moonrise 119 INFOPLIST_KEY_CFBundleDisplayName: Moonrise
118 INFOPLIST_KEY_WKCompanionAppBundleIdentifier: sh.krz.moonrise 120 INFOPLIST_KEY_WKCompanionAppBundleIdentifier: sh.krz.moonrise
@@ -135,6 +137,8 @@ targets:
135 path: Watch/Widgets-Info.plist 137 path: Watch/Widgets-Info.plist
136 properties: 138 properties:
137 CFBundleDisplayName: Moonrise 139 CFBundleDisplayName: Moonrise
140 CFBundleShortVersionString: $(MARKETING_VERSION)
141 CFBundleVersion: $(CURRENT_PROJECT_VERSION)
138 NSWidgetWantsLocation: true 142 NSWidgetWantsLocation: true
139 NSExtension: 143 NSExtension:
140 NSExtensionPointIdentifier: com.apple.widgetkit-extension 144 NSExtensionPointIdentifier: com.apple.widgetkit-extension
@@ -144,8 +148,8 @@ targets:
144 DEVELOPMENT_TEAM: ZCNAX3VL9D 148 DEVELOPMENT_TEAM: ZCNAX3VL9D
145 CODE_SIGN_STYLE: Automatic 149 CODE_SIGN_STYLE: Automatic
146 SWIFT_VERSION: "6.0" 150 SWIFT_VERSION: "6.0"
147 MARKETING_VERSION: "1.0" 151 MARKETING_VERSION: "1.0.0"
148 CURRENT_PROJECT_VERSION: "1" 152 CURRENT_PROJECT_VERSION: "52"
149 MoonriseVision: 153 MoonriseVision:
150 type: application 154 type: application
151 platform: visionOS 155 platform: visionOS
@@ -169,8 +173,8 @@ targets:
169 DEVELOPMENT_TEAM: ZCNAX3VL9D 173 DEVELOPMENT_TEAM: ZCNAX3VL9D
170 CODE_SIGN_STYLE: Automatic 174 CODE_SIGN_STYLE: Automatic
171 SWIFT_VERSION: "6.0" 175 SWIFT_VERSION: "6.0"
172 MARKETING_VERSION: "1.0" 176 MARKETING_VERSION: "1.0.0"
173 CURRENT_PROJECT_VERSION: "1" 177 CURRENT_PROJECT_VERSION: "52"
174 GENERATE_INFOPLIST_FILE: YES 178 GENERATE_INFOPLIST_FILE: YES
175 INFOPLIST_KEY_CFBundleDisplayName: Moonrise 179 INFOPLIST_KEY_CFBundleDisplayName: Moonrise
176 INFOPLIST_KEY_UIApplicationSceneManifest_Generation: YES 180 INFOPLIST_KEY_UIApplicationSceneManifest_Generation: YES
scripts/release-ios.sh added +63
@@ -0,0 +1,63 @@
1#!/bin/sh
2# Archives the iOS app (with its widgets and the watch app) and uploads it to App Store Connect,
3# signed automatically with the team's distribution certificate through the Apple ID signed in
4# to Xcode. The version is MARKETING_VERSION in App/project.yml; the build number is the commit
5# count on main, so every upload can be traced to a commit. The upload then shows in TestFlight
6# and can be picked for an App Store submission.
7# Usage: scripts/release-ios.sh
8# MOONRISE_PUBLISH 0 archives and exports the .ipa to .build/ios-release without uploading
9set -eu
10
11cd "$(dirname "$0")/.."
12publish="${MOONRISE_PUBLISH:-1}"
13team=ZCNAX3VL9D
14
15if [ "$publish" != 0 ]; then
16 [ -z "$(git status --porcelain)" ] || { echo "The working tree has changes." >&2; exit 1; }
17 [ "$(git branch --show-current)" = main ] || { echo "Release from main." >&2; exit 1; }
18fi
19
20version="$(sed -n 's/.*MARKETING_VERSION: "\(.*\)"/\1/p' App/project.yml | sort -u)"
21[ "$(printf '%s\n' "$version" | wc -l | tr -d ' ')" = 1 ] || { echo "The targets' MARKETING_VERSION differ: $version" >&2; exit 1; }
22build="$(git rev-list --count HEAD)"
23
24command -v xcodegen >/dev/null || { echo "Install XcodeGen: brew install xcodegen" >&2; exit 1; }
25(cd App && xcodegen generate --quiet)
26
27out=.build/ios-release
28rm -rf "${out:?}"
29mkdir -p "$out"
30archive="$out/moonrise.xcarchive"
31xcodebuild archive -project App/Moonrise.xcodeproj -scheme Moonrise -configuration Release \
32 -destination 'generic/platform=iOS' -archivePath "$archive" -allowProvisioningUpdates -quiet \
33 MARKETING_VERSION="$version" CURRENT_PROJECT_VERSION="$build"
34
35if [ "$publish" = 0 ]; then destination=export; else destination=upload; fi
36cat > "$out/ExportOptions.plist" <<PLIST
37<?xml version="1.0" encoding="UTF-8"?>
38<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
39<plist version="1.0">
40<dict>
41 <key>method</key>
42 <string>app-store-connect</string>
43 <key>destination</key>
44 <string>$destination</string>
45 <key>teamID</key>
46 <string>$team</string>
47 <key>signingStyle</key>
48 <string>automatic</string>
49 <key>manageAppVersionAndBuildNumber</key>
50 <false/>
51 <key>uploadSymbols</key>
52 <true/>
53</dict>
54</plist>
55PLIST
56xcodebuild -exportArchive -archivePath "$archive" -exportOptionsPlist "$out/ExportOptions.plist" \
57 -exportPath "$out/export" -allowProvisioningUpdates -quiet
58
59if [ "$publish" = 0 ]; then
60 echo "Exported $(ls "$out"/export/*.ipa): $version ($build), not uploaded"
61else
62 echo "Uploaded Moonrise $version ($build) to App Store Connect; it shows in TestFlight once processed"
63fi