Skip to content

Commit df18811

Browse files
committed
Add InstalledTool class instead of ad-hoc list
1 parent 81e7709 commit df18811

File tree

1 file changed

+46
-21
lines changed

1 file changed

+46
-21
lines changed

src/hlsBinaries.ts

Lines changed: 46 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -324,19 +324,19 @@ export async function findHaskellLanguageServer(
324324
if (promptBeforeDownloads) {
325325
const hlsInstalled = latestHLS
326326
? await toolInstalled(context, logger, 'hls', latestHLS)
327-
: ([true, 'hls', ''] as [boolean, Tool, string]);
327+
: new InstalledTool('hls');
328328
const cabalInstalled = latestCabal
329329
? await toolInstalled(context, logger, 'cabal', latestCabal)
330-
: ([true, 'cabal', ''] as [boolean, Tool, string]);
330+
: new InstalledTool('cabal');
331331
const stackInstalled = latestStack
332332
? await toolInstalled(context, logger, 'stack', latestStack)
333-
: ([true, 'stack', ''] as [boolean, Tool, string]);
333+
: new InstalledTool('stack');
334334
const ghcInstalled = (await executableExists('ghc'))
335-
? ([true, 'ghc', ''] as [boolean, Tool, string])
335+
? new InstalledTool('ghc')
336336
: await toolInstalled(context, logger, 'ghc', recGHC!);
337337
const toInstall = [hlsInstalled, cabalInstalled, stackInstalled, ghcInstalled]
338-
.filter(([b, t, v]) => !b)
339-
.map(([_, t, v]) => `${t}-${v}`);
338+
.filter((tool) => !tool.installed)
339+
.map((tool) => tool.nameWithVersion);
340340
if (toInstall.length > 0) {
341341
const decision = await window.showInformationMessage(
342342
`Need to download ${toInstall.join(', ')}, continue?`,
@@ -348,15 +348,15 @@ export async function findHaskellLanguageServer(
348348
} else if (decision === "Yes, don't ask again") {
349349
workspace.getConfiguration('haskell').update('promptBeforeDownloads', false);
350350
} else {
351-
[hlsInstalled, cabalInstalled, stackInstalled, ghcInstalled].forEach(([b, t]) => {
352-
if (!b) {
353-
if (t === 'hls') {
351+
[hlsInstalled, cabalInstalled, stackInstalled, ghcInstalled].forEach((tool) => {
352+
if (!tool.installed) {
353+
if (tool.name === 'hls') {
354354
throw new MissingToolError('hls');
355-
} else if (t === 'cabal') {
355+
} else if (tool.name === 'cabal') {
356356
latestCabal = null;
357-
} else if (t === 'stack') {
357+
} else if (tool.name === 'stack') {
358358
latestStack = null;
359-
} else if (t === 'ghc') {
359+
} else if (tool.name === 'ghc') {
360360
recGHC = null;
361361
}
362362
}
@@ -400,11 +400,13 @@ export async function findHaskellLanguageServer(
400400
if (promptBeforeDownloads) {
401401
const hlsInstalled = projectHls
402402
? await toolInstalled(context, logger, 'hls', projectHls)
403-
: ([true, 'hls', ''] as [boolean, Tool, string]);
403+
: new InstalledTool('hls');
404404
const ghcInstalled = projectGhc
405405
? await toolInstalled(context, logger, 'ghc', projectGhc)
406-
: ([true, 'ghc', ''] as [boolean, Tool, string]);
407-
const toInstall = [hlsInstalled, ghcInstalled].filter(([b, t, v]) => !b).map(([_, t, v]) => `${t}-${v}`);
406+
: new InstalledTool('ghc');
407+
const toInstall = [hlsInstalled, ghcInstalled]
408+
.filter((tool) => !tool.installed)
409+
.map((tool) => tool.nameWithVersion);
408410
if (toInstall.length > 0) {
409411
const decision = await window.showInformationMessage(
410412
`Need to download ${toInstall.join(', ')}, continue?`,
@@ -417,11 +419,11 @@ export async function findHaskellLanguageServer(
417419
} else if (decision === "Yes, don't ask again") {
418420
workspace.getConfiguration('haskell').update('promptBeforeDownloads', false);
419421
} else {
420-
[hlsInstalled, ghcInstalled].forEach(([b, t]) => {
421-
if (!b) {
422-
if (t === 'hls') {
422+
[hlsInstalled, ghcInstalled].forEach((tool) => {
423+
if (!tool.installed) {
424+
if (tool.name === 'hls') {
423425
throw new MissingToolError('hls');
424-
} else if (t === 'ghc') {
426+
} else if (tool.name === 'ghc') {
425427
projectGhc = null;
426428
}
427429
}
@@ -774,11 +776,11 @@ async function toolInstalled(
774776
logger: Logger,
775777
tool: Tool,
776778
version: string
777-
): Promise<[boolean, Tool, string]> {
779+
): Promise<InstalledTool> {
778780
const b = await callGHCup(context, logger, ['whereis', tool, version], undefined, false)
779781
.then((x) => true)
780782
.catch((x) => false);
781-
return [b, tool, version];
783+
return new InstalledTool(tool, version, b);
782784
}
783785

784786
/**
@@ -896,3 +898,26 @@ async function getReleaseMetadata(
896898
}
897899
}
898900
}
901+
902+
/**
903+
* Tracks the name, version and installation state of tools we need.
904+
*/
905+
class InstalledTool {
906+
/**
907+
* "<name>-<version>" of the installed Tool.
908+
*/
909+
readonly nameWithVersion: string = '';
910+
911+
/**
912+
* Initialize an installed tool entry.
913+
*
914+
* If optional parameters are omitted, we assume the tool is installed.
915+
*
916+
* @param name Name of the tool.
917+
* @param version Version of the tool, expected to be either SemVer or PVP versioned.
918+
* @param installed Is this tool currently installed?
919+
*/
920+
public constructor(readonly name: string, readonly version: string = '', readonly installed: boolean = true) {
921+
this.nameWithVersion = `${name}-${version}`;
922+
}
923+
}

0 commit comments

Comments
 (0)