Skip to content

Commit e3d6a80

Browse files
committed
feat(ios): swift package clarity while installing and time formatting
1 parent 1344dc2 commit e3d6a80

2 files changed

Lines changed: 51 additions & 16 deletions

File tree

lib/services/ios/spm-service.ts

Lines changed: 27 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -168,7 +168,7 @@ export class SPMService implements ISPMService {
168168

169169
const render = () => {
170170
const elapsed = Math.round((Date.now() - startedAt) / 1000);
171-
spinner.text = `${activity}${color.dim(`(${elapsed}s)`)}`;
171+
spinner.text = `${activity}${color.dim(`(${this.formatElapsed(elapsed)})`)}`;
172172
};
173173
// keep the elapsed timer ticking even when xcodebuild is silent (e.g.
174174
// while a binary artifact downloads) so the user can see it's alive.
@@ -256,10 +256,10 @@ export class SPMService implements ISPMService {
256256
return "Downloading Swift Package binaries (first build only)";
257257
}
258258
if (/^Fetching\b/i.test(trimmed)) {
259-
return `Fetching ${this.shortenPackageRef(trimmed)}`;
259+
return this.describePackageActivity("Fetching", trimmed);
260260
}
261261
if (/^Cloning\b/i.test(trimmed)) {
262-
return `Cloning ${this.shortenPackageRef(trimmed)}`;
262+
return this.describePackageActivity("Cloning", trimmed);
263263
}
264264
if (/Computing version for/i.test(trimmed)) {
265265
return "Computing package versions";
@@ -273,18 +273,39 @@ export class SPMService implements ISPMService {
273273
return null;
274274
}
275275

276-
/** Extracts a short, readable name from a SwiftPM repo URL/log line. */
277-
private shortenPackageRef(line: string): string {
276+
/**
277+
* Builds a stable, self-explanatory activity label with the package being
278+
* worked on in parentheses, e.g. "Fetching Swift Packages (Auth0.swift)".
279+
*/
280+
private describePackageActivity(verb: string, line: string): string {
281+
const packageRef = this.shortenPackageRef(line);
282+
return packageRef
283+
? `${verb} Swift Packages (${packageRef})`
284+
: `${verb} Swift Packages`;
285+
}
286+
287+
/**
288+
* Extracts a short, readable name from a SwiftPM repo URL/log line, or null
289+
* when the line contains no URL to name the package by.
290+
*/
291+
private shortenPackageRef(line: string): string | null {
278292
const match = line.match(/https?:\/\/\S+/);
279293
if (!match) {
280-
return "Swift Packages";
294+
return null;
281295
}
282296
return path
283297
.basename(match[0])
284298
.replace(/\.git$/, "")
285299
.replace(/[)\s].*$/, "");
286300
}
287301

302+
/** Formats an elapsed duration in whole seconds as "5m 15s". */
303+
private formatElapsed(totalSeconds: number): string {
304+
const minutes = Math.floor(totalSeconds / 60);
305+
const seconds = totalSeconds % 60;
306+
return `${minutes}m ${seconds}s`;
307+
}
308+
288309
/** True when the Xcode project references any Swift packages. */
289310
private hasSPMReferences(
290311
platformData: IPlatformData,

test/spm-service.ts

Lines changed: 24 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -205,21 +205,28 @@ describe("SPM Service - resolution log parsing", () => {
205205
);
206206
});
207207

208-
it("summarizes fetching with the package name", () => {
208+
it("summarizes fetching with the package name in parentheses", () => {
209209
assert.equal(
210210
service.describeSPMActivity(
211211
"Fetching from https://github.com/NativeScript/ios-spm.git",
212212
),
213-
"Fetching ios-spm",
213+
"Fetching Swift Packages (ios-spm)",
214214
);
215215
});
216216

217-
it("summarizes cloning with the package name", () => {
217+
it("summarizes cloning with the package name in parentheses", () => {
218218
assert.equal(
219219
service.describeSPMActivity(
220220
"Cloning https://github.com/Alamofire/Alamofire.git",
221221
),
222-
"Cloning Alamofire",
222+
"Cloning Swift Packages (Alamofire)",
223+
);
224+
});
225+
226+
it("omits the parenthesized name when the line has no URL", () => {
227+
assert.equal(
228+
service.describeSPMActivity("Fetching cached package"),
229+
"Fetching Swift Packages",
223230
);
224231
});
225232

@@ -251,7 +258,7 @@ describe("SPM Service - resolution log parsing", () => {
251258
service.describeSPMActivity(
252259
" Fetching https://github.com/NativeScript/ios-spm.git ",
253260
),
254-
"Fetching ios-spm",
261+
"Fetching Swift Packages (ios-spm)",
255262
);
256263
});
257264

@@ -286,11 +293,18 @@ describe("SPM Service - resolution log parsing", () => {
286293
);
287294
});
288295

289-
it("falls back to a generic label when there is no URL", () => {
290-
assert.equal(
291-
service.shortenPackageRef("Fetching cached package"),
292-
"Swift Packages",
293-
);
296+
it("returns null when there is no URL", () => {
297+
assert.isNull(service.shortenPackageRef("Fetching cached package"));
298+
});
299+
});
300+
301+
describe("formatElapsed", () => {
302+
it("always renders minutes and seconds", () => {
303+
assert.equal(service.formatElapsed(0), "0m 0s");
304+
assert.equal(service.formatElapsed(42), "0m 42s");
305+
assert.equal(service.formatElapsed(60), "1m 0s");
306+
assert.equal(service.formatElapsed(315), "5m 15s");
307+
assert.equal(service.formatElapsed(3725), "62m 5s");
294308
});
295309
});
296310
});

0 commit comments

Comments
 (0)