@mpgd/cli 0.57.0 → 0.58.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (46) hide show
  1. package/dist/capacitor-shell-starter.d.ts +30 -0
  2. package/dist/capacitor-shell-starter.js +243 -11
  3. package/dist/index.js +170 -11
  4. package/dist/legal-site-output.d.ts +18 -0
  5. package/dist/legal-site-output.js +46 -1
  6. package/dist/native-build-info.json +2 -2
  7. package/dist/native-build-target.js +1663 -899
  8. package/dist/native-deploy-run.js +4 -0
  9. package/dist/native-shell-store-policy.d.ts +123 -0
  10. package/dist/native-shell-store-policy.js +816 -0
  11. package/dist/release-state.d.ts +2 -0
  12. package/dist/release-state.js +4 -2
  13. package/dist/testflight-submission.d.ts +9 -0
  14. package/dist/testflight-submission.js +69 -0
  15. package/package.json +17 -17
  16. package/templates/lite-overlay/agent/acceptance.md +1 -1
  17. package/templates/lite-overlay/agent/brief.md +1 -1
  18. package/templates/lite-overlay/src/lite/deleteAccountButton.ts +173 -0
  19. package/templates/lite-overlay/src/lite/restorePurchasesButton.ts +63 -0
  20. package/templates/lite-overlay/src/runtime/createGame.ts +8 -0
  21. package/templates/notifications-overlay/common/docs/NOTIFICATIONS.md +12 -6
  22. package/templates/notifications-overlay/common/notifications/deployment.json +2 -1
  23. package/templates/notifications-overlay/common/notifications/topics.json +3 -0
  24. package/templates/notifications-overlay/common/src/platform/capacitorNotifications.ts +8 -3
  25. package/templates/notifications-overlay/common/src/platform/notifications.ts +17 -3
  26. package/templates/phaser-game/README.md +72 -0
  27. package/templates/phaser-game/agent/acceptance.md +4 -1
  28. package/templates/phaser-game/agent/brief.md +14 -4
  29. package/templates/phaser-game/gitignore +11 -0
  30. package/templates/phaser-game/legal/delete-account.html +133 -0
  31. package/templates/phaser-game/legal/privacy.html +111 -12
  32. package/templates/phaser-game/legal/support.html +1 -0
  33. package/templates/phaser-game/legal/terms.html +1 -0
  34. package/templates/phaser-game/mpgd.game.json +3 -0
  35. package/templates/phaser-game/src/env.d.ts +6 -0
  36. package/templates/phaser-game/src/i18n/messages.ts +86 -1
  37. package/templates/phaser-game/src/main.ts +69 -8
  38. package/templates/phaser-game/src/platform/commerceAccountBinding.ts +39 -10
  39. package/templates/phaser-game/src/platform/deleteAccount.ts +334 -0
  40. package/templates/phaser-game/src/platform/gameServices.ts +55 -10
  41. package/templates/phaser-game/src/platform/guestIdentity.ts +301 -0
  42. package/templates/phaser-game/src/platform/restorePurchases.ts +205 -0
  43. package/templates/phaser-game/src/platform/serverSession.ts +8 -0
  44. package/templates/phaser-game/src/platform/sessionGatedServices.ts +217 -0
  45. package/templates/phaser-game/src/scenes/LobbyScene.ts +254 -1
  46. package/templates/phaser-game/src/scenes/PlayScene.ts +16 -6
@@ -187,6 +187,10 @@ async function buildAndRecordTarget(input, workspace, target, reserved, environm
187
187
  BUILD_ID: reserved.buildId,
188
188
  MPGD_RELEASE_REVISION: String(reserved.releaseRevision),
189
189
  MPGD_RELEASE_LABEL: reserved.releaseLabel,
190
+ // The reserved numbers are stamped into the build's staged shell copy, so
191
+ // a release does not need a hand commit of versionCode/build number; the
192
+ // signed-artifact inspection still compares the emitted values with them.
193
+ MPGD_NATIVE_VERSION_STAMP: '1',
190
194
  ...(target === 'android' ? {
191
195
  MPGD_TARGET_VERSION_CODE: String(version.versionCode),
192
196
  MPGD_TARGET_VERSION_NAME: String(version.versionName),
@@ -0,0 +1,123 @@
1
+ /**
2
+ * Store-facing settings of the game-owned Capacitor shell: the iOS
3
+ * Info.plist keys App Store Connect reads (export compliance, device
4
+ * capabilities). The starter writes them into a newly generated project;
5
+ * a production build only reports what an existing shell still lacks, so
6
+ * game-owned native files are never rewritten behind the game's back.
7
+ */
8
+ export interface NativeShellPolicyIssue {
9
+ /** `error` fails a production build; `warning` is printed. */
10
+ readonly level: 'error' | 'warning';
11
+ readonly message: string;
12
+ }
13
+ /**
14
+ * Adds the iOS keys every kit shell should ship with, keeping any value the
15
+ * game already set:
16
+ * - `ITSAppUsesNonExemptEncryption` = false. The kit itself only uses HTTPS
17
+ * through the OS and OS crypto, which Apple's export rules exempt, so
18
+ * App Store Connect does not ask the export-compliance question per build.
19
+ * A game that adds its own encryption sets the key to true and answers it.
20
+ * - `UIRequiredDeviceCapabilities` lists `arm64` instead of the 32-bit
21
+ * `armv7` left over from the Capacitor template.
22
+ */
23
+ export declare function applyIosInfoPlistStorePolicy(plist: string): string;
24
+ /** What a shell's release Info.plist still lacks compared with `applyIosInfoPlistStorePolicy`. */
25
+ export declare function inspectIosInfoPlistStorePolicy(plist: string): readonly NativeShellPolicyIssue[];
26
+ export interface PlistValue {
27
+ readonly start: number;
28
+ readonly end: number;
29
+ readonly xml: string;
30
+ }
31
+ /**
32
+ * The value element following `<key>name</key>` (first occurrence), or
33
+ * undefined. Only for keys that appear once in the document, such as the
34
+ * top-level Info.plist keys this module manages.
35
+ */
36
+ export declare function readPlistTopLevelValue(plist: string, key: string): PlistValue | undefined;
37
+ /** Replaces the value of `key`, or appends the entry to the root dictionary. */
38
+ export declare function setPlistTopLevelValue(plist: string, key: string, valueXml: string): string;
39
+ /** The game's design orientation (`mpgd.game.json` `native.orientation`). */
40
+ export type NativeShellOrientation = 'portrait' | 'landscape' | 'any';
41
+ /** iOS devices the App Store offers the game on (`mpgd.targets.json` ios `metadata.iosDeviceFamily`). */
42
+ export type IosDeviceFamily = 'universal' | 'iphone';
43
+ /**
44
+ * Reads `native.orientation` from a parsed `mpgd.game.json`; undefined when
45
+ * the game has not chosen one, in which case nothing is enforced.
46
+ */
47
+ export declare function readGameNativeOrientation(gameConfig: unknown): NativeShellOrientation | undefined;
48
+ /** Reads `metadata.iosDeviceFamily` of the ios target; undefined when not chosen. */
49
+ export declare function readIosDeviceFamily(metadata: unknown): IosDeviceFamily | undefined;
50
+ /** iPhone orientations for a design orientation (upside-down portrait stays off, as in Xcode's template). */
51
+ export declare function iosIphoneOrientations(orientation: NativeShellOrientation): readonly string[];
52
+ /**
53
+ * iPad always lists all four orientations. Apple deprecated
54
+ * `UIRequiresFullScreen` in iPadOS 26 and asks apps to support every
55
+ * orientation (TN3192); iPadOS keeps a game that prefers one orientation at a
56
+ * consistent scene size, and the kit's runtime orientation policy letterboxes
57
+ * or asks the player to rotate.
58
+ */
59
+ export declare const iosIpadOrientations: readonly string[];
60
+ /** Writes the iPhone and iPad orientation lists for the game's design orientation. */
61
+ export declare function applyIosInfoPlistOrientation(plist: string, orientation: NativeShellOrientation): string;
62
+ export declare function inspectIosInfoPlistOrientation(plist: string, orientation: NativeShellOrientation | undefined, deviceFamily: IosDeviceFamily): readonly NativeShellPolicyIssue[];
63
+ /** `TARGETED_DEVICE_FAMILY` value: 1 = iPhone, 2 = iPad. */
64
+ export declare function iosTargetedDeviceFamily(family: IosDeviceFamily): string;
65
+ /** Sets `TARGETED_DEVICE_FAMILY` in every build configuration of the App target. */
66
+ export declare function applyIosProjectDeviceFamily(project: string, family: IosDeviceFamily): string;
67
+ /** The App target's Release `TARGETED_DEVICE_FAMILY`, without quotes, or undefined. */
68
+ export declare function readIosAppReleaseDeviceFamily(project: string): string | undefined;
69
+ export declare function inspectIosProjectDeviceFamily(project: string, family: IosDeviceFamily | undefined): readonly NativeShellPolicyIssue[];
70
+ /**
71
+ * Sets the launcher activity's `android:screenOrientation` (`portrait`,
72
+ * `sensorLandscape`, or none for `any`) and marks the application
73
+ * `android:appCategory="game"`. Android 16 ignores orientation restrictions
74
+ * on large screens for apps targeting API 36 unless the app is a game.
75
+ */
76
+ export declare function applyAndroidManifestOrientation(manifest: string, orientation: NativeShellOrientation): string;
77
+ export declare function inspectAndroidManifestOrientation(manifest: string, orientation: NativeShellOrientation | undefined): readonly NativeShellPolicyIssue[];
78
+ export declare function isRecord(value: unknown): value is Record<string, unknown>;
79
+ export declare const iosAppPrivacyManifestFile = "PrivacyInfo.xcprivacy";
80
+ /**
81
+ * App-level privacy manifest of a kit shell. The App target's own code
82
+ * (AppDelegate, SceneDelegate) calls no required-reason API and the kit does
83
+ * no tracking; Capacitor core and the kit's game-services plugin ship their
84
+ * own manifests (the plugin declares UserDefaults CA92.1). The collected
85
+ * data array is empty only because the kit-owned shell code collects
86
+ * nothing: a game adds the required-reason APIs its own native code uses
87
+ * and an entry for each data type it collects
88
+ * (docs/STORE_PRIVACY_DISCLOSURES.md).
89
+ */
90
+ export declare const iosAppPrivacyManifestXml: string;
91
+ /**
92
+ * Adds a file in the App group to the App target's Resources phase of a
93
+ * Capacitor-generated project. Returns undefined when the project does not
94
+ * have that layout (an App group with `path = App`, a Resources phase, the
95
+ * PBXBuildFile/PBXFileReference section markers), so the caller can leave the
96
+ * project alone. A project whose Resources phase already bundles the file is
97
+ * returned unchanged; one whose App group references it without bundling it
98
+ * is left to the game (undefined).
99
+ */
100
+ export declare function addIosAppResource(project: string, fileName: string): string | undefined;
101
+ /** Whether the App target's Resources phase bundles `fileName`. */
102
+ export declare function iosAppBundlesResource(project: string, fileName: string): boolean;
103
+ export declare function inspectIosAppPrivacyManifest(project: string): readonly NativeShellPolicyIssue[];
104
+ export declare const admobCapacitorPlugin = "@capacitor-community/admob";
105
+ export declare const androidAdIdPermission = "com.google.android.gms.permission.AD_ID";
106
+ /** Whether the shell's package.json installs the AdMob Capacitor plugin. */
107
+ export declare function shellUsesAdMob(shellPackage: unknown): boolean;
108
+ /** `declared`, `removed` (tools:node="remove"), or `absent` from the app manifest. */
109
+ export declare function readAndroidAdIdDeclaration(manifest: string): 'declared' | 'removed' | 'absent';
110
+ /**
111
+ * Declares the advertising ID permission when the game shows AdMob ads
112
+ * (Google Mobile Ads also merges it) and removes it from the merged manifest
113
+ * otherwise, so the Play Console advertising ID answer matches the binary.
114
+ */
115
+ export declare function applyAndroidManifestAdId(manifest: string, usesAds: boolean): string;
116
+ /**
117
+ * `ads.admob.advertisingId` in `mpgd.game.json`: `removed` records a
118
+ * deliberate no-advertising-ID policy (for example a child-directed game)
119
+ * for a shell that installs AdMob; anything else expects the permission.
120
+ */
121
+ export declare function readGameAdvertisingIdPolicy(gameConfig: unknown): 'declared' | 'removed';
122
+ export declare function inspectAndroidManifestAds(manifest: string, usesAds: boolean, advertisingIdPolicy?: 'declared' | 'removed'): readonly NativeShellPolicyIssue[];
123
+ export declare function inspectIosInfoPlistAds(plist: string, usesAds: boolean): readonly NativeShellPolicyIssue[];