@invarn/cibuild 2.7.9 → 2.8.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.
- package/dist/cli.cjs +143 -10
- package/dist/src/commands/android-java-version.test.js +93 -10
- package/dist/src/commands/android-scanner.d.ts +87 -8
- package/dist/src/commands/android-scanner.d.ts.map +1 -1
- package/dist/src/commands/android-scanner.js +133 -27
- package/dist/src/commands/build.d.ts +8 -0
- package/dist/src/commands/build.d.ts.map +1 -1
- package/dist/src/commands/build.js +17 -3
- package/dist/src/yaml/steps/xcode-app-product.d.ts +90 -0
- package/dist/src/yaml/steps/xcode-app-product.d.ts.map +1 -0
- package/dist/src/yaml/steps/xcode-app-product.js +247 -0
- package/dist/src/yaml/steps/xcode-app-product.test.d.ts +2 -0
- package/dist/src/yaml/steps/xcode-app-product.test.d.ts.map +1 -0
- package/dist/src/yaml/steps/xcode-app-product.test.js +202 -0
- package/dist/src/yaml/steps/xcode-derived-data.test.js +66 -1
- package/dist/src/yaml/steps/xcode.d.ts.map +1 -1
- package/dist/src/yaml/steps/xcode.js +50 -3
- package/package.json +1 -1
|
@@ -63,8 +63,14 @@ describe('runnableJavaVersion', () => {
|
|
|
63
63
|
expect(runnableJavaVersion(17)).toBe(25);
|
|
64
64
|
expect(runnableJavaVersion(25)).toBe(25);
|
|
65
65
|
});
|
|
66
|
-
|
|
67
|
-
|
|
66
|
+
// Nothing declared and no wrapper to read is nothing to go on. It used to
|
|
67
|
+
// answer 25 anyway, which is a guess wearing a number; the generator's own
|
|
68
|
+
// default stands instead, and that is not news worth a warning.
|
|
69
|
+
test('abstains when there is nothing to go on', () => {
|
|
70
|
+
expect(runnableJavaVersion(undefined)).toBeUndefined();
|
|
71
|
+
});
|
|
72
|
+
test('still answers from the wrapper alone, with nothing declared', () => {
|
|
73
|
+
expect(runnableJavaVersion(undefined, '8.9')).toBe(21);
|
|
68
74
|
});
|
|
69
75
|
// 8 joined the images on 2026-09-07 and must stay unreachable except where
|
|
70
76
|
// a wrapper ceiling forces it: a project declaring `sourceCompatibility 1.8`
|
|
@@ -84,17 +90,58 @@ describe('runnableJavaVersion', () => {
|
|
|
84
90
|
expect(runnableJavaVersion(11, '5.2.1')).toBe(11);
|
|
85
91
|
expect(runnableJavaVersion(undefined, '6.9')).toBe(11);
|
|
86
92
|
});
|
|
93
|
+
// No answer is ever a JDK the build machines lack.
|
|
87
94
|
test('never names a JDK no build machine has', () => {
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
95
|
+
for (const answer of [runnableJavaVersion(23), runnableJavaVersion(25, '8.9')]) {
|
|
96
|
+
if (answer !== undefined)
|
|
97
|
+
expect(AVAILABLE_JAVA_VERSIONS).toContain(answer);
|
|
98
|
+
}
|
|
99
|
+
});
|
|
100
|
+
/**
|
|
101
|
+
* And no answer is ever above the wrapper's own ceiling.
|
|
102
|
+
*
|
|
103
|
+
* This is the defect. Nothing satisfied both the declaration and the
|
|
104
|
+
* ceiling, so the chooser fell back to the newest installed JDK — which is
|
|
105
|
+
* *above* the ceiling by construction, because the ceiling is why nothing
|
|
106
|
+
* fitted. The build then died selecting the JDK, exactly as a too-new JDK
|
|
107
|
+
* always does, and `javaVersionProblem` had no branch for the shape so
|
|
108
|
+
* nothing anywhere said a choice had been made.
|
|
109
|
+
*
|
|
110
|
+
* The ceiling is hard: Gradle starts before it reads a single
|
|
111
|
+
* `sourceCompatibility`. The declaration is a floor. So where they conflict
|
|
112
|
+
* the ceiling wins, and the caller says so.
|
|
113
|
+
*/
|
|
114
|
+
test('never answers above the wrapper ceiling', () => {
|
|
115
|
+
// Gradle 7.x tops out at 17. Declaring 21 cannot raise that.
|
|
116
|
+
expect(runnableJavaVersion(21, '7.6.1')).toBe(17);
|
|
96
117
|
expect(runnableJavaVersion(17, '7.6.1')).toBe(17);
|
|
97
118
|
});
|
|
119
|
+
// Gradle 6.5 runs on Java 11 at most, and a workflow pins java-version 12.
|
|
120
|
+
// The old chooser answered 25 and said nothing.
|
|
121
|
+
test('caps a modern declaration under an old wrapper', () => {
|
|
122
|
+
expect(runnableJavaVersion(12, '6.5')).toBe(11);
|
|
123
|
+
});
|
|
124
|
+
// Every shape the corpus has, held to both properties at once: the answer
|
|
125
|
+
// is installed, and it is not above the ceiling.
|
|
126
|
+
test.each([
|
|
127
|
+
[8, '4.10.2'],
|
|
128
|
+
[11, '5.2.1'],
|
|
129
|
+
[12, '6.5'],
|
|
130
|
+
[17, '7.6.1'],
|
|
131
|
+
[21, '7.6.1'],
|
|
132
|
+
[8, '9.0'],
|
|
133
|
+
[30, '8.9'],
|
|
134
|
+
[25, '9.1'],
|
|
135
|
+
[undefined, '6.9'],
|
|
136
|
+
])('declared %s on Gradle %s answers within both bounds', (declared, gradle) => {
|
|
137
|
+
const answer = runnableJavaVersion(declared, gradle);
|
|
138
|
+
if (answer === undefined)
|
|
139
|
+
return; // abstention is always allowed
|
|
140
|
+
expect(AVAILABLE_JAVA_VERSIONS).toContain(answer);
|
|
141
|
+
const ceiling = gradleJavaCeiling(gradle);
|
|
142
|
+
if (ceiling !== undefined)
|
|
143
|
+
expect(answer).toBeLessThanOrEqual(ceiling);
|
|
144
|
+
});
|
|
98
145
|
test('honours the Gradle 9 floor of 17', () => {
|
|
99
146
|
// The floor rules 11 out; the newest above it is what gets written.
|
|
100
147
|
expect(runnableJavaVersion(8, '9.0')).toBe(21);
|
|
@@ -122,5 +169,41 @@ describe('javaVersionProblem', () => {
|
|
|
122
169
|
// Nor is 4.10.2, since the images carry 8.
|
|
123
170
|
expect(javaVersionProblem(undefined, '4.10.2')).toBeUndefined();
|
|
124
171
|
});
|
|
172
|
+
/**
|
|
173
|
+
* The shape that used to fall through every branch, and the reason this
|
|
174
|
+
* function is resolved from the same place as the answer.
|
|
175
|
+
*
|
|
176
|
+
* A wrapper on Gradle 6.5 under a workflow pinning java-version 12: the
|
|
177
|
+
* ceiling is not below every installed JDK and the declaration is not above
|
|
178
|
+
* every installed JDK, so neither old branch fired. The chooser answered 25
|
|
179
|
+
* — above the ceiling — and nothing said the project had asked for something
|
|
180
|
+
* else and been overruled.
|
|
181
|
+
*/
|
|
182
|
+
test('speaks when an old wrapper overrules a newer declaration', () => {
|
|
183
|
+
const problem = javaVersionProblem(12, '6.5');
|
|
184
|
+
expect(problem).toContain('Java 12');
|
|
185
|
+
expect(problem).toContain('Gradle 6.5');
|
|
186
|
+
expect(problem).toContain('Java 11 at most');
|
|
187
|
+
expect(problem).toContain('Building on 11');
|
|
188
|
+
});
|
|
189
|
+
// An answer that is not what was asked for always speaks, whichever
|
|
190
|
+
// constraint did the overruling.
|
|
191
|
+
test.each([
|
|
192
|
+
[12, '6.5'],
|
|
193
|
+
[21, '7.6.1'],
|
|
194
|
+
[30, '8.9'],
|
|
195
|
+
])('declared %s on Gradle %s never passes silently', (declared, gradle) => {
|
|
196
|
+
expect(javaVersionProblem(declared, gradle)).toBeDefined();
|
|
197
|
+
});
|
|
198
|
+
// Naming a version with no provenance sends a reader through every Gradle
|
|
199
|
+
// file looking for a number that is in none of them. The scan knows which
|
|
200
|
+
// file asked, so the sentence can say.
|
|
201
|
+
test('names the file that asked, when it is known', () => {
|
|
202
|
+
const problem = javaVersionProblem(12, '6.5', '.github/workflows/Build.yml');
|
|
203
|
+
expect(problem).toContain('Java 12 (.github/workflows/Build.yml)');
|
|
204
|
+
});
|
|
205
|
+
test('reads correctly without a source', () => {
|
|
206
|
+
expect(javaVersionProblem(12, '6.5')).not.toContain('(');
|
|
207
|
+
});
|
|
125
208
|
});
|
|
126
209
|
//# sourceMappingURL=android-java-version.test.js.map
|
|
@@ -11,6 +11,16 @@ export interface ScanResult {
|
|
|
11
11
|
warnings: BuildWarning[];
|
|
12
12
|
/** Highest Java version requirement detected in Gradle files (e.g. 17, 21). */
|
|
13
13
|
detectedJavaVersion?: number;
|
|
14
|
+
/**
|
|
15
|
+
* The file that asked for it, when the level came from outside Gradle —
|
|
16
|
+
* `.github/workflows/Build.yml`, `.java-version`, `.tool-versions`.
|
|
17
|
+
*
|
|
18
|
+
* The scan computed this and dropped it, so a warning could name a version
|
|
19
|
+
* with no provenance and send a reader looking through every Gradle file for
|
|
20
|
+
* a number that is not in any of them. Undefined when the level came from a
|
|
21
|
+
* Gradle file, or when a Gradle file asked for at least as much.
|
|
22
|
+
*/
|
|
23
|
+
detectedJavaVersionSource?: string;
|
|
14
24
|
/** Gradle version the wrapper pins, e.g. "8.9". Undefined when there is no wrapper. */
|
|
15
25
|
detectedGradleVersion?: string;
|
|
16
26
|
/** Build types, product flavors, and all variant combinations detected in Gradle files. */
|
|
@@ -102,12 +112,71 @@ export declare function gradleJavaFloor(gradleVersion: string | undefined): numb
|
|
|
102
112
|
*/
|
|
103
113
|
export declare const AVAILABLE_JAVA_VERSIONS: number[];
|
|
104
114
|
/**
|
|
105
|
-
* The newest JDK a build machine carries.
|
|
106
|
-
*
|
|
107
|
-
*
|
|
108
|
-
*
|
|
115
|
+
* The newest JDK a build machine carries.
|
|
116
|
+
*
|
|
117
|
+
* It is no longer what the chooser falls back to. It used to be: with no JDK
|
|
118
|
+
* satisfying both the sources and the wrapper, `runnableJavaVersion` returned
|
|
119
|
+
* this — which on a project pinning a modern Java level under an old Gradle
|
|
120
|
+
* wrapper is a JDK **above** that wrapper's ceiling, and the build dies at
|
|
121
|
+
* `:app:processDebugMainManifest` with "module java.base does not opens
|
|
122
|
+
* java.io to unnamed module". A number above the ceiling is not a fallback;
|
|
123
|
+
* it is the failure, chosen deliberately and reported as success.
|
|
109
124
|
*/
|
|
110
125
|
export declare const NEWEST_AVAILABLE_JAVA_VERSION: number;
|
|
126
|
+
/** Why the chooser answered as it did. See {@link chooseJavaVersion}. */
|
|
127
|
+
export type JavaVersionKind = "unknown" | "satisfies" | "capped-by-wrapper" | "above-runners" | "wrapper-below-runners";
|
|
128
|
+
/** The JDK choice and the reason for it, resolved together. */
|
|
129
|
+
export interface JavaVersionChoice {
|
|
130
|
+
/** The JDK to write, or undefined where no answer exists. */
|
|
131
|
+
version: number | undefined;
|
|
132
|
+
kind: JavaVersionKind;
|
|
133
|
+
/** The highest level the project asked for, or 0 if it asked for none. */
|
|
134
|
+
declared: number;
|
|
135
|
+
/** The newest JDK the wrapper can start on, or undefined if unreadable. */
|
|
136
|
+
ceiling: number | undefined;
|
|
137
|
+
installed: number[];
|
|
138
|
+
}
|
|
139
|
+
/**
|
|
140
|
+
* The JDK to build on, with the reason attached — one place where the
|
|
141
|
+
* constraints are resolved, so the answer and the explanation cannot disagree.
|
|
142
|
+
*
|
|
143
|
+
* They used to. The chooser fell back to the newest installed JDK whenever
|
|
144
|
+
* nothing satisfied both constraints, and the sentence beside it had two
|
|
145
|
+
* branches — a ceiling below every installed JDK, and a declaration above
|
|
146
|
+
* every installed JDK — so the commonest shape of all fell through both and
|
|
147
|
+
* said nothing at all. A project pinning Java 12 against a Gradle wrapper that
|
|
148
|
+
* runs on 11 at most got Java 25 and silence.
|
|
149
|
+
*
|
|
150
|
+
* Three facts decide it:
|
|
151
|
+
*
|
|
152
|
+
* - **What the build machine has.** Only `AVAILABLE_JAVA_VERSIONS` exist, so
|
|
153
|
+
* a project declaring 30 cannot simply be given 30.
|
|
154
|
+
* - **What Gradle can run on.** The wrapper sets a ceiling that source
|
|
155
|
+
* compatibility cannot raise: Gradle starts before it reads a single
|
|
156
|
+
* `sourceCompatibility`.
|
|
157
|
+
* - **What the sources ask for.** A declaration is a floor, not an exact
|
|
158
|
+
* request — a project declaring 11 compiles fine on 21.
|
|
159
|
+
*
|
|
160
|
+
* `kind` distinguishes the five outcomes:
|
|
161
|
+
*
|
|
162
|
+
* - `unknown` — nothing declared and no readable wrapper. Nothing to go on
|
|
163
|
+
* and nothing to say.
|
|
164
|
+
* - `satisfies` — an installed JDK meets both the floor and the ceiling.
|
|
165
|
+
* - `capped-by-wrapper` — nothing meets both, and the wrapper is why. The
|
|
166
|
+
* ceiling is hard and the declaration is a preference, so the newest JDK
|
|
167
|
+
* the wrapper *can* run is the answer, and the caller says so.
|
|
168
|
+
* - `above-runners` — the declaration is above every installed JDK, and that
|
|
169
|
+
* rather than the wrapper is what binds. **No answer**: asking for it would
|
|
170
|
+
* fail when the JDK is selected, and quietly picking a lower one would be
|
|
171
|
+
* the guess this exists to avoid.
|
|
172
|
+
* - `wrapper-below-runners` — the ceiling is below every installed JDK. No
|
|
173
|
+
* answer exists.
|
|
174
|
+
*
|
|
175
|
+
* `above-runners` is checked before `capped-by-wrapper` so a project declaring
|
|
176
|
+
* 99 against a modern wrapper is told about the machines rather than about its
|
|
177
|
+
* wrapper: both bind, and the one it can act on is the one worth naming.
|
|
178
|
+
*/
|
|
179
|
+
export declare function chooseJavaVersion(detectedJavaVersion: number | undefined, gradleVersion?: string): JavaVersionChoice;
|
|
111
180
|
/**
|
|
112
181
|
* The Java version to write into a generated pipeline: the **newest**
|
|
113
182
|
* available JDK that satisfies both what the sources declare and what the
|
|
@@ -125,12 +194,22 @@ export declare const NEWEST_AVAILABLE_JAVA_VERSION: number;
|
|
|
125
194
|
* caps the JDK no matter what the sources say — which is why the ceiling
|
|
126
195
|
* above had to learn minor versions before this could ship.
|
|
127
196
|
*/
|
|
128
|
-
export declare function runnableJavaVersion(detectedJavaVersion: number | undefined, gradleVersion?: string): number;
|
|
197
|
+
export declare function runnableJavaVersion(detectedJavaVersion: number | undefined, gradleVersion?: string): number | undefined;
|
|
129
198
|
/**
|
|
130
|
-
* What
|
|
131
|
-
*
|
|
199
|
+
* What the choice could not honour, as a sentence, or undefined when it
|
|
200
|
+
* honoured everything.
|
|
201
|
+
*
|
|
202
|
+
* Silence is the failure this exists to prevent: a pipeline that quietly
|
|
203
|
+
* overruled what a project asked for reads as the project's own problem, and
|
|
204
|
+
* the commonest shape of all — an old wrapper under a modern declaration — was
|
|
205
|
+
* the one that used to fall through every branch.
|
|
206
|
+
*
|
|
207
|
+
* `source` names the file that asked, when the caller knows it. The scan now
|
|
208
|
+
* returns it, so "asks for Java 12" can become "asks for Java 12
|
|
209
|
+
* (.github/workflows/Build.yml)" — a version with no provenance sends a reader
|
|
210
|
+
* looking through every Gradle file for a number that is not in any of them.
|
|
132
211
|
*/
|
|
133
|
-
export declare function javaVersionProblem(detectedJavaVersion: number | undefined, gradleVersion?: string): string | undefined;
|
|
212
|
+
export declare function javaVersionProblem(detectedJavaVersion: number | undefined, gradleVersion?: string, source?: string): string | undefined;
|
|
134
213
|
/**
|
|
135
214
|
* Detects build types and product flavors from Gradle files by static parsing,
|
|
136
215
|
* falling back to the module's source sets for the flavors when no Gradle file
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"android-scanner.d.ts","sourceRoot":"","sources":["../../../src/commands/android-scanner.ts"],"names":[],"mappings":"AAIA,MAAM,MAAM,eAAe,GAAG,SAAS,GAAG,MAAM,CAAC;AAEjD,MAAM,MAAM,eAAe,GACvB,cAAc,GACd,SAAS,GACT,iBAAiB,GACjB,gBAAgB,GAChB,cAAc,GACd,UAAU,GACV,gBAAgB,CAAC;AAErB,MAAM,WAAW,YAAY;IAC3B,QAAQ,EAAE,eAAe,CAAC;IAC1B,QAAQ,EAAE,eAAe,CAAC;IAC1B,OAAO,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,MAAM,WAAW,UAAU;IACzB,QAAQ,EAAE,YAAY,EAAE,CAAC;IACzB,+EAA+E;IAC/E,mBAAmB,CAAC,EAAE,MAAM,CAAC;IAC7B,uFAAuF;IACvF,qBAAqB,CAAC,EAAE,MAAM,CAAC;IAC/B,2FAA2F;IAC3F,aAAa,EAAE,aAAa,CAAC;CAC9B;AAED,MAAM,WAAW,aAAa;IAC5B,gGAAgG;IAChG,UAAU,EAAE,MAAM,EAAE,CAAC;IACrB,wFAAwF;IACxF,cAAc,EAAE,MAAM,EAAE,CAAC;IACzB,uFAAuF;IACvF,QAAQ,EAAE,MAAM,EAAE,CAAC;CACpB;AAwKD;;;;;;;;;;;;;;;;;;GAkBG;AACH,wBAAgB,2BAA2B,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAcnE;AAyKD,kFAAkF;AAClF,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,EAAE,CAO7D;AAED;;;;;;;;;;;;;GAaG;AACH,wBAAgB,uBAAuB,CACrC,IAAI,EAAE,MAAM,GACX;IAAE,OAAO,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,GAAG,SAAS,CA8CjD;AA2BD;;;;;;;;;;;GAWG;AACH,wBAAgB,yBAAyB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,GAAG,SAAS,CAG7E;AAQD;;;GAGG;AACH,wBAAgB,iBAAiB,CAAC,aAAa,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,CAsBvF;AAED,oEAAoE;AACpE,wBAAgB,eAAe,CAAC,aAAa,EAAE,MAAM,GAAG,SAAS,GAAG,MAAM,GAAG,SAAS,CAIrF;AAED;;;;;;;;;;;;;;;GAeG;AACH,eAAO,MAAM,uBAAuB,UAAsB,CAAC;AAE3D
|
|
1
|
+
{"version":3,"file":"android-scanner.d.ts","sourceRoot":"","sources":["../../../src/commands/android-scanner.ts"],"names":[],"mappings":"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"}
|
|
@@ -518,12 +518,87 @@ export function gradleJavaFloor(gradleVersion) {
|
|
|
518
518
|
*/
|
|
519
519
|
export const AVAILABLE_JAVA_VERSIONS = [8, 11, 17, 21, 25];
|
|
520
520
|
/**
|
|
521
|
-
* The newest JDK a build machine carries.
|
|
522
|
-
*
|
|
523
|
-
*
|
|
524
|
-
*
|
|
521
|
+
* The newest JDK a build machine carries.
|
|
522
|
+
*
|
|
523
|
+
* It is no longer what the chooser falls back to. It used to be: with no JDK
|
|
524
|
+
* satisfying both the sources and the wrapper, `runnableJavaVersion` returned
|
|
525
|
+
* this — which on a project pinning a modern Java level under an old Gradle
|
|
526
|
+
* wrapper is a JDK **above** that wrapper's ceiling, and the build dies at
|
|
527
|
+
* `:app:processDebugMainManifest` with "module java.base does not opens
|
|
528
|
+
* java.io to unnamed module". A number above the ceiling is not a fallback;
|
|
529
|
+
* it is the failure, chosen deliberately and reported as success.
|
|
525
530
|
*/
|
|
526
531
|
export const NEWEST_AVAILABLE_JAVA_VERSION = Math.max(...AVAILABLE_JAVA_VERSIONS);
|
|
532
|
+
/**
|
|
533
|
+
* The JDK to build on, with the reason attached — one place where the
|
|
534
|
+
* constraints are resolved, so the answer and the explanation cannot disagree.
|
|
535
|
+
*
|
|
536
|
+
* They used to. The chooser fell back to the newest installed JDK whenever
|
|
537
|
+
* nothing satisfied both constraints, and the sentence beside it had two
|
|
538
|
+
* branches — a ceiling below every installed JDK, and a declaration above
|
|
539
|
+
* every installed JDK — so the commonest shape of all fell through both and
|
|
540
|
+
* said nothing at all. A project pinning Java 12 against a Gradle wrapper that
|
|
541
|
+
* runs on 11 at most got Java 25 and silence.
|
|
542
|
+
*
|
|
543
|
+
* Three facts decide it:
|
|
544
|
+
*
|
|
545
|
+
* - **What the build machine has.** Only `AVAILABLE_JAVA_VERSIONS` exist, so
|
|
546
|
+
* a project declaring 30 cannot simply be given 30.
|
|
547
|
+
* - **What Gradle can run on.** The wrapper sets a ceiling that source
|
|
548
|
+
* compatibility cannot raise: Gradle starts before it reads a single
|
|
549
|
+
* `sourceCompatibility`.
|
|
550
|
+
* - **What the sources ask for.** A declaration is a floor, not an exact
|
|
551
|
+
* request — a project declaring 11 compiles fine on 21.
|
|
552
|
+
*
|
|
553
|
+
* `kind` distinguishes the five outcomes:
|
|
554
|
+
*
|
|
555
|
+
* - `unknown` — nothing declared and no readable wrapper. Nothing to go on
|
|
556
|
+
* and nothing to say.
|
|
557
|
+
* - `satisfies` — an installed JDK meets both the floor and the ceiling.
|
|
558
|
+
* - `capped-by-wrapper` — nothing meets both, and the wrapper is why. The
|
|
559
|
+
* ceiling is hard and the declaration is a preference, so the newest JDK
|
|
560
|
+
* the wrapper *can* run is the answer, and the caller says so.
|
|
561
|
+
* - `above-runners` — the declaration is above every installed JDK, and that
|
|
562
|
+
* rather than the wrapper is what binds. **No answer**: asking for it would
|
|
563
|
+
* fail when the JDK is selected, and quietly picking a lower one would be
|
|
564
|
+
* the guess this exists to avoid.
|
|
565
|
+
* - `wrapper-below-runners` — the ceiling is below every installed JDK. No
|
|
566
|
+
* answer exists.
|
|
567
|
+
*
|
|
568
|
+
* `above-runners` is checked before `capped-by-wrapper` so a project declaring
|
|
569
|
+
* 99 against a modern wrapper is told about the machines rather than about its
|
|
570
|
+
* wrapper: both bind, and the one it can act on is the one worth naming.
|
|
571
|
+
*/
|
|
572
|
+
export function chooseJavaVersion(detectedJavaVersion, gradleVersion) {
|
|
573
|
+
const declared = Number(detectedJavaVersion) || 0;
|
|
574
|
+
const ceiling = gradleJavaCeiling(gradleVersion);
|
|
575
|
+
const floor = gradleJavaFloor(gradleVersion);
|
|
576
|
+
const installed = [...AVAILABLE_JAVA_VERSIONS].sort((a, b) => a - b);
|
|
577
|
+
const base = { declared, ceiling, installed };
|
|
578
|
+
if (!declared && floor === undefined) {
|
|
579
|
+
return { ...base, version: undefined, kind: "unknown" };
|
|
580
|
+
}
|
|
581
|
+
const wanted = Math.max(declared, floor ?? 0);
|
|
582
|
+
const usable = installed.filter((v) => v >= wanted && v <= (ceiling ?? Infinity));
|
|
583
|
+
// The newest that fits. Nothing reaches the oldest installed JDK unless a
|
|
584
|
+
// ceiling leaves nothing else, which is the only reason 8 and 11 are on the
|
|
585
|
+
// images at all.
|
|
586
|
+
if (usable.length > 0) {
|
|
587
|
+
return { ...base, version: usable[usable.length - 1], kind: "satisfies" };
|
|
588
|
+
}
|
|
589
|
+
if (declared > installed[installed.length - 1]) {
|
|
590
|
+
return { ...base, version: undefined, kind: "above-runners" };
|
|
591
|
+
}
|
|
592
|
+
const underCeiling = installed.filter((v) => v <= (ceiling ?? Infinity));
|
|
593
|
+
if (underCeiling.length > 0) {
|
|
594
|
+
return {
|
|
595
|
+
...base,
|
|
596
|
+
version: underCeiling[underCeiling.length - 1],
|
|
597
|
+
kind: "capped-by-wrapper",
|
|
598
|
+
};
|
|
599
|
+
}
|
|
600
|
+
return { ...base, version: undefined, kind: "wrapper-below-runners" };
|
|
601
|
+
}
|
|
527
602
|
/**
|
|
528
603
|
* The Java version to write into a generated pipeline: the **newest**
|
|
529
604
|
* available JDK that satisfies both what the sources declare and what the
|
|
@@ -542,34 +617,44 @@ export const NEWEST_AVAILABLE_JAVA_VERSION = Math.max(...AVAILABLE_JAVA_VERSIONS
|
|
|
542
617
|
* above had to learn minor versions before this could ship.
|
|
543
618
|
*/
|
|
544
619
|
export function runnableJavaVersion(detectedJavaVersion, gradleVersion) {
|
|
545
|
-
|
|
546
|
-
const floor = Math.max(detectedJavaVersion ?? 0, gradleJavaFloor(gradleVersion) ?? 0);
|
|
547
|
-
const usable = AVAILABLE_JAVA_VERSIONS.filter((v) => v >= floor && v <= ceiling).sort((a, b) => a - b);
|
|
548
|
-
if (usable.length === 0)
|
|
549
|
-
return NEWEST_AVAILABLE_JAVA_VERSION;
|
|
550
|
-
return usable[usable.length - 1];
|
|
620
|
+
return chooseJavaVersion(detectedJavaVersion, gradleVersion).version;
|
|
551
621
|
}
|
|
552
622
|
/**
|
|
553
|
-
* What
|
|
554
|
-
*
|
|
623
|
+
* What the choice could not honour, as a sentence, or undefined when it
|
|
624
|
+
* honoured everything.
|
|
625
|
+
*
|
|
626
|
+
* Silence is the failure this exists to prevent: a pipeline that quietly
|
|
627
|
+
* overruled what a project asked for reads as the project's own problem, and
|
|
628
|
+
* the commonest shape of all — an old wrapper under a modern declaration — was
|
|
629
|
+
* the one that used to fall through every branch.
|
|
630
|
+
*
|
|
631
|
+
* `source` names the file that asked, when the caller knows it. The scan now
|
|
632
|
+
* returns it, so "asks for Java 12" can become "asks for Java 12
|
|
633
|
+
* (.github/workflows/Build.yml)" — a version with no provenance sends a reader
|
|
634
|
+
* looking through every Gradle file for a number that is not in any of them.
|
|
555
635
|
*/
|
|
556
|
-
export function javaVersionProblem(detectedJavaVersion, gradleVersion) {
|
|
636
|
+
export function javaVersionProblem(detectedJavaVersion, gradleVersion, source) {
|
|
637
|
+
const choice = chooseJavaVersion(detectedJavaVersion, gradleVersion);
|
|
638
|
+
if (choice.kind === "satisfies" || choice.kind === "unknown")
|
|
639
|
+
return undefined;
|
|
640
|
+
const { declared, ceiling, installed } = choice;
|
|
557
641
|
// "11, 17 and 21", not "11 and 17 and 21" — a human reads this next to a
|
|
558
642
|
// build that will not start.
|
|
559
|
-
const
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
if (ceiling !== undefined && ceiling < lowest) {
|
|
566
|
-
return `Gradle ${gradleVersion} runs on Java ${ceiling} at most, and build machines carry only ${installed}. This pipeline will very likely fail before it compiles anything — upgrade the Gradle wrapper.`;
|
|
643
|
+
const list = installed.length > 1
|
|
644
|
+
? `${installed.slice(0, -1).join(", ")} and ${installed[installed.length - 1]}`
|
|
645
|
+
: String(installed[0]);
|
|
646
|
+
const asked = source ? `Java ${declared} (${source})` : `Java ${declared}`;
|
|
647
|
+
if (choice.kind === "wrapper-below-runners") {
|
|
648
|
+
return `Gradle ${gradleVersion} runs on Java ${ceiling} at most, and build machines carry only ${list}. This pipeline will very likely fail before it compiles anything — upgrade the Gradle wrapper.`;
|
|
567
649
|
}
|
|
568
|
-
|
|
569
|
-
|
|
570
|
-
return `This project declares Java ${detectedJavaVersion}, and build machines carry only ${installed}. Writing Java ${runnableJavaVersion(detectedJavaVersion, gradleVersion)} instead — asking for ${detectedJavaVersion} would fail at "Set the Java version".`;
|
|
650
|
+
if (choice.kind === "above-runners") {
|
|
651
|
+
return `This project declares Java ${declared}, and build machines carry only ${list}. Leaving JAVA_VERSION at the pipeline default — asking for ${declared} would fail at "Set the Java version", and quietly choosing a lower one would be a guess.`;
|
|
571
652
|
}
|
|
572
|
-
|
|
653
|
+
// capped-by-wrapper
|
|
654
|
+
const preamble = declared
|
|
655
|
+
? `This project asks for ${asked}, and Gradle ${gradleVersion} runs on Java ${ceiling} at most.`
|
|
656
|
+
: `Gradle ${gradleVersion} runs on Java ${ceiling} at most.`;
|
|
657
|
+
return `${preamble} Building on ${choice.version} — the newest the wrapper allows.`;
|
|
573
658
|
}
|
|
574
659
|
// ---------------------------------------------------------------------------
|
|
575
660
|
// Gitignore helper
|
|
@@ -817,6 +902,12 @@ export async function scanAndroidProject(projectRoot) {
|
|
|
817
902
|
const detectedJavaVersion = declaredJavaVersion === undefined && pinnedJava === undefined
|
|
818
903
|
? undefined
|
|
819
904
|
: Math.max(declaredJavaVersion ?? 0, pinnedJava?.version ?? 0);
|
|
905
|
+
// Only when the pin is what set the level. A Gradle file asking for as much
|
|
906
|
+
// or more is the thing a reader would find by looking, so naming the
|
|
907
|
+
// workflow there would point away from the answer.
|
|
908
|
+
const detectedJavaVersionSource = pinnedJava !== undefined && pinnedJava.version > (declaredJavaVersion ?? 0)
|
|
909
|
+
? pinnedJava.source
|
|
910
|
+
: undefined;
|
|
820
911
|
const detectedGradleVersion = detectGradleWrapperVersion(projectRoot);
|
|
821
912
|
const buildVariants = detectBuildVariants(gradleFiles);
|
|
822
913
|
// ------------------------------------------------------------------
|
|
@@ -1024,7 +1115,13 @@ export async function scanAndroidProject(projectRoot) {
|
|
|
1024
1115
|
});
|
|
1025
1116
|
}
|
|
1026
1117
|
}
|
|
1027
|
-
return {
|
|
1118
|
+
return {
|
|
1119
|
+
warnings,
|
|
1120
|
+
detectedJavaVersion,
|
|
1121
|
+
detectedJavaVersionSource,
|
|
1122
|
+
detectedGradleVersion,
|
|
1123
|
+
buildVariants,
|
|
1124
|
+
};
|
|
1028
1125
|
}
|
|
1029
1126
|
// ---------------------------------------------------------------------------
|
|
1030
1127
|
// Formatter
|
|
@@ -1045,9 +1142,18 @@ export function formatScanResult(result) {
|
|
|
1045
1142
|
// actually name — they differ whenever the declaration is below the oldest
|
|
1046
1143
|
// installed JDK or above the newest, and saying only the first made the
|
|
1047
1144
|
// second look like it had been honoured.
|
|
1145
|
+
//
|
|
1146
|
+
// And when they differ, say why in the same breath. An answer that is not
|
|
1147
|
+
// what was asked for, printed with no reason, reads as a fact about the
|
|
1148
|
+
// project rather than as a decision made on its behalf.
|
|
1048
1149
|
if (result.detectedJavaVersion !== undefined) {
|
|
1049
1150
|
const willUse = runnableJavaVersion(result.detectedJavaVersion, result.detectedGradleVersion);
|
|
1050
|
-
lines.push(
|
|
1151
|
+
lines.push(willUse === undefined
|
|
1152
|
+
? `ℹ Detected Java ${result.detectedJavaVersion} requirement — no installed JDK can satisfy it`
|
|
1153
|
+
: `ℹ Detected Java ${result.detectedJavaVersion} requirement — pipeline will use Java ${willUse}`);
|
|
1154
|
+
const problem = javaVersionProblem(result.detectedJavaVersion, result.detectedGradleVersion, result.detectedJavaVersionSource);
|
|
1155
|
+
if (problem)
|
|
1156
|
+
lines.push(` ${problem}`);
|
|
1051
1157
|
lines.push("");
|
|
1052
1158
|
}
|
|
1053
1159
|
if (result.warnings.length === 0) {
|
|
@@ -197,6 +197,14 @@ export declare function detectSetupNeeds(warnings: BuildWarning[]): Omit<SetupOp
|
|
|
197
197
|
* and a webhook must never reach it.
|
|
198
198
|
*/
|
|
199
199
|
export declare function triggerMapBlock(defaultBranch?: string): string;
|
|
200
|
+
/**
|
|
201
|
+
* The JDK a generated pipeline names when the project's own constraints have
|
|
202
|
+
* no answer — nothing declared and no readable wrapper, or a declaration no
|
|
203
|
+
* installed JDK can meet. A generated pipeline has to write something; what it
|
|
204
|
+
* must not do is write a number the wrapper cannot start on and call that a
|
|
205
|
+
* choice.
|
|
206
|
+
*/
|
|
207
|
+
export declare const DEFAULT_PIPELINE_JAVA_VERSION = 17;
|
|
200
208
|
export declare function generateAndroidPipeline(javaVersion?: number, setup?: SetupOptions, variants?: WorkflowVariants, cacheTechnology?: "gradle" | "kmm", metaNamespace?: 'invarn' | 'cibuild.io', defaultBranch?: string): string;
|
|
201
209
|
export declare function generateIosPipeline(projectPath: string, setup: IosSetupOptions, variants: IosWorkflowVariants, metaNamespace?: 'invarn' | 'cibuild.io', defaultBranch?: string): string;
|
|
202
210
|
export declare function handleBuildCommand(detectMobileProjectRoot: (dir: string) => "android" | "ios" | "kmm" | null, options?: {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"build.d.ts","sourceRoot":"","sources":["../../../src/commands/build.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"build.d.ts","sourceRoot":"","sources":["../../../src/commands/build.ts"],"names":[],"mappings":"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"}
|
|
@@ -326,7 +326,15 @@ trigger_map:
|
|
|
326
326
|
workflow: pull-request
|
|
327
327
|
`;
|
|
328
328
|
}
|
|
329
|
-
|
|
329
|
+
/**
|
|
330
|
+
* The JDK a generated pipeline names when the project's own constraints have
|
|
331
|
+
* no answer — nothing declared and no readable wrapper, or a declaration no
|
|
332
|
+
* installed JDK can meet. A generated pipeline has to write something; what it
|
|
333
|
+
* must not do is write a number the wrapper cannot start on and call that a
|
|
334
|
+
* choice.
|
|
335
|
+
*/
|
|
336
|
+
export const DEFAULT_PIPELINE_JAVA_VERSION = 17;
|
|
337
|
+
export function generateAndroidPipeline(javaVersion = DEFAULT_PIPELINE_JAVA_VERSION, setup = { keystore: false, keystoreProperties: false, googleServices: false, googlePlayDeploy: false, googlePlayPackageName: '', artifactType: 'apk', keystorePaths: {}, googleServicesPaths: {}, workflowFlavors: {}, secretsProperties: false, secretsPropertiesPath: 'local.properties' }, variants = DEFAULT_VARIANTS, cacheTechnology = "gradle", metaNamespace = 'cibuild.io', defaultBranch = FALLBACK_DEFAULT_BRANCH) {
|
|
330
338
|
const keystoreStepFor = (wf) => {
|
|
331
339
|
if (!setup.keystore)
|
|
332
340
|
return "";
|
|
@@ -1370,11 +1378,17 @@ async function handleAndroidBuildCommand(cwd, options, cacheTechnology) {
|
|
|
1370
1378
|
}
|
|
1371
1379
|
}
|
|
1372
1380
|
// 7. Generate and write the pipeline
|
|
1381
|
+
//
|
|
1382
|
+
// The chooser abstains rather than falling back, so `undefined` here means
|
|
1383
|
+
// "no installed JDK meets this project's constraints" — not "17 is fine".
|
|
1384
|
+
// The default is what gets written in that case, and the warning below is
|
|
1385
|
+
// what says so; it is never silent when the answer is not what was asked
|
|
1386
|
+
// for, which is the whole reason the two are resolved together.
|
|
1373
1387
|
const javaVersion = runnableJavaVersion(scanResult.detectedJavaVersion, scanResult.detectedGradleVersion);
|
|
1374
|
-
const javaProblem = javaVersionProblem(scanResult.detectedJavaVersion, scanResult.detectedGradleVersion);
|
|
1388
|
+
const javaProblem = javaVersionProblem(scanResult.detectedJavaVersion, scanResult.detectedGradleVersion, scanResult.detectedJavaVersionSource);
|
|
1375
1389
|
if (javaProblem)
|
|
1376
1390
|
console.log(`\n⚠️ ${javaProblem}`);
|
|
1377
|
-
const yaml = generateAndroidPipeline(javaVersion, setupOptions, variants, cacheTechnology, options.metaNamespace, detectDefaultBranch());
|
|
1391
|
+
const yaml = generateAndroidPipeline(javaVersion ?? DEFAULT_PIPELINE_JAVA_VERSION, setupOptions, variants, cacheTechnology, options.metaNamespace, detectDefaultBranch());
|
|
1378
1392
|
writeFileSync(outputPath, yaml, "utf-8");
|
|
1379
1393
|
console.log("\n✅ Generated .ci/pipelines/cibuild.yml");
|
|
1380
1394
|
console.log(` Platform: ${platformLabel}`);
|
|
@@ -0,0 +1,90 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Which built `.app` belongs to the scheme that was built.
|
|
3
|
+
*
|
|
4
|
+
* A simulator build leaves every application bundle its graph produced under
|
|
5
|
+
* `DerivedData/Build/Products/<configuration>-<platform>/`, and a scheme that
|
|
6
|
+
* builds a watchOS or tvOS companion alongside the app produces two. Taking
|
|
7
|
+
* whichever one a directory scan reaches first is a coin toss, and it lands the
|
|
8
|
+
* wrong way often enough to matter: a project whose scheme builds both an iOS
|
|
9
|
+
* app and a watch companion exported the 588 KB watch bundle as the app under
|
|
10
|
+
* test. The build was green, the artifact manifest was non-empty, and the
|
|
11
|
+
* thing a user downloaded could not be installed on the device they built for.
|
|
12
|
+
* That is worse than delivering nothing, because nothing is visibly wrong and
|
|
13
|
+
* a plausible wrong answer is not.
|
|
14
|
+
*
|
|
15
|
+
* The scheme already knows. A shared `.xcscheme` lists its build entries with a
|
|
16
|
+
* `BuildableName` whose extension IS the product type, and `buildForRunning`
|
|
17
|
+
* separates what the scheme builds from what it merely references — a scheme
|
|
18
|
+
* may list several `.app` entries it does not build, so "mentions an app" is
|
|
19
|
+
* not the question and a check that asked it would pick just as badly.
|
|
20
|
+
*
|
|
21
|
+
* Where the scheme gives no answer this falls back rather than failing. A
|
|
22
|
+
* project with no shared scheme at all is ordinary — plenty of them never
|
|
23
|
+
* commit one — and those builds work. Absence of evidence is not evidence, so
|
|
24
|
+
* the destination's own platform directory decides, and failing to resolve an
|
|
25
|
+
* app is left to the caller's existing guard.
|
|
26
|
+
*
|
|
27
|
+
* The whole resolver runs on the machine that did the build, against the
|
|
28
|
+
* products that build actually produced, so it needs nothing from the step
|
|
29
|
+
* generator but the scheme name and the destination.
|
|
30
|
+
*/
|
|
31
|
+
/** A built application bundle, as found under `Build/Products`. */
|
|
32
|
+
export interface BuiltApp {
|
|
33
|
+
/** The `<configuration>-<platform>` directory, or `''` directly under Products. */
|
|
34
|
+
platform: string;
|
|
35
|
+
/** The bundle's own name, e.g. `MyApp.app`. */
|
|
36
|
+
name: string;
|
|
37
|
+
/** Absolute path to the bundle. */
|
|
38
|
+
path: string;
|
|
39
|
+
}
|
|
40
|
+
/**
|
|
41
|
+
* The SDK suffix the Products directory carries for a given destination.
|
|
42
|
+
*
|
|
43
|
+
* `-destination 'generic/platform=iOS Simulator'` builds into
|
|
44
|
+
* `Debug-iphonesimulator`; the watchOS and tvOS spellings are the ones that
|
|
45
|
+
* matter here, because a companion target is exactly what produces the second
|
|
46
|
+
* bundle this resolver exists to skip past.
|
|
47
|
+
*/
|
|
48
|
+
export declare function platformSuffixForDestination(destination: string): string;
|
|
49
|
+
/**
|
|
50
|
+
* The application bundles a scheme's build action actually builds.
|
|
51
|
+
*
|
|
52
|
+
* `buildForRunning="NO"` entries are listed and not built. A scheme can carry
|
|
53
|
+
* three `.app` entries that are API-compatibility testers in other containers
|
|
54
|
+
* beside the one framework it really produces, so the attribute is the whole
|
|
55
|
+
* filter rather than a refinement of one.
|
|
56
|
+
*
|
|
57
|
+
* Returns an empty list for a file that cannot be read or carries no build
|
|
58
|
+
* action — no evidence, which the caller must not read as "builds no app".
|
|
59
|
+
*/
|
|
60
|
+
export declare function runnableAppProducts(schemeXml: string | null): string[];
|
|
61
|
+
/**
|
|
62
|
+
* The bundle to export, given everything that was built and what the scheme
|
|
63
|
+
* says it builds.
|
|
64
|
+
*
|
|
65
|
+
* In order: the scheme's own product on the destination's platform, the
|
|
66
|
+
* scheme's own product anywhere, anything on the destination's platform,
|
|
67
|
+
* anything at all. The last two are the no-shared-scheme path, and they are
|
|
68
|
+
* what keeps a project that never committed a scheme building exactly as it
|
|
69
|
+
* did before.
|
|
70
|
+
*/
|
|
71
|
+
export declare function chooseAppProduct(apps: BuiltApp[], schemeProducts: string[], destination: string): BuiltApp | null;
|
|
72
|
+
/**
|
|
73
|
+
* The resolver as it runs on the build machine: dependency-free CommonJS,
|
|
74
|
+
* written to a temp file and invoked with
|
|
75
|
+
* `node <file> <productsDir> <projectPath> <scheme> <destination>`.
|
|
76
|
+
*
|
|
77
|
+
* It prints the chosen bundle's path and nothing else, and exits non-zero with
|
|
78
|
+
* no output when it cannot choose — which is the signal for the caller's
|
|
79
|
+
* existing scan to take over, so a machine without a usable node is no worse
|
|
80
|
+
* off than before this existed.
|
|
81
|
+
*
|
|
82
|
+
* Kept as source text rather than bundled because the step ships a shell
|
|
83
|
+
* script, not a module graph. The three functions above are the same rules in
|
|
84
|
+
* testable form, and `xcode-app-product.test.ts` holds them to each other.
|
|
85
|
+
*
|
|
86
|
+
* Must contain no backtick and no dollar-brace: it is emitted into a bash
|
|
87
|
+
* heredoc, and it is a TypeScript template literal on the way there.
|
|
88
|
+
*/
|
|
89
|
+
export declare const APP_PRODUCT_RESOLVER_SOURCE: string;
|
|
90
|
+
//# sourceMappingURL=xcode-app-product.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"xcode-app-product.d.ts","sourceRoot":"","sources":["../../../../src/yaml/steps/xcode-app-product.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6BG;AAEH,mEAAmE;AACnE,MAAM,WAAW,QAAQ;IACvB,mFAAmF;IACnF,QAAQ,EAAE,MAAM,CAAC;IACjB,+CAA+C;IAC/C,IAAI,EAAE,MAAM,CAAC;IACb,mCAAmC;IACnC,IAAI,EAAE,MAAM,CAAC;CACd;AAED;;;;;;;GAOG;AACH,wBAAgB,4BAA4B,CAAC,WAAW,EAAE,MAAM,GAAG,MAAM,CAMxE;AAED;;;;;;;;;;GAUG;AACH,wBAAgB,mBAAmB,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI,GAAG,MAAM,EAAE,CAatE;AAED;;;;;;;;;GASG;AACH,wBAAgB,gBAAgB,CAC9B,IAAI,EAAE,QAAQ,EAAE,EAChB,cAAc,EAAE,MAAM,EAAE,EACxB,WAAW,EAAE,MAAM,GAClB,QAAQ,GAAG,IAAI,CAOjB;AAED;;;;;;;;;;;;;;;;GAgBG;AACH,eAAO,MAAM,2BAA2B,EAAE,MAqIzC,CAAC"}
|