@@ -324,19 +324,19 @@ export async function findHaskellLanguageServer(
324
324
if ( promptBeforeDownloads ) {
325
325
const hlsInstalled = latestHLS
326
326
? await toolInstalled ( context , logger , 'hls' , latestHLS )
327
- : ( [ true , 'hls' , '' ] as [ boolean , Tool , string ] ) ;
327
+ : new InstalledTool ( 'hls' ) ;
328
328
const cabalInstalled = latestCabal
329
329
? await toolInstalled ( context , logger , 'cabal' , latestCabal )
330
- : ( [ true , 'cabal' , '' ] as [ boolean , Tool , string ] ) ;
330
+ : new InstalledTool ( 'cabal' ) ;
331
331
const stackInstalled = latestStack
332
332
? await toolInstalled ( context , logger , 'stack' , latestStack )
333
- : ( [ true , 'stack' , '' ] as [ boolean , Tool , string ] ) ;
333
+ : new InstalledTool ( 'stack' ) ;
334
334
const ghcInstalled = ( await executableExists ( 'ghc' ) )
335
- ? ( [ true , 'ghc' , '' ] as [ boolean , Tool , string ] )
335
+ ? new InstalledTool ( 'ghc' )
336
336
: await toolInstalled ( context , logger , 'ghc' , recGHC ! ) ;
337
337
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 ) ;
340
340
if ( toInstall . length > 0 ) {
341
341
const decision = await window . showInformationMessage (
342
342
`Need to download ${ toInstall . join ( ', ' ) } , continue?` ,
@@ -348,15 +348,15 @@ export async function findHaskellLanguageServer(
348
348
} else if ( decision === "Yes, don't ask again" ) {
349
349
workspace . getConfiguration ( 'haskell' ) . update ( 'promptBeforeDownloads' , false ) ;
350
350
} 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' ) {
354
354
throw new MissingToolError ( 'hls' ) ;
355
- } else if ( t === 'cabal' ) {
355
+ } else if ( tool . name === 'cabal' ) {
356
356
latestCabal = null ;
357
- } else if ( t === 'stack' ) {
357
+ } else if ( tool . name === 'stack' ) {
358
358
latestStack = null ;
359
- } else if ( t === 'ghc' ) {
359
+ } else if ( tool . name === 'ghc' ) {
360
360
recGHC = null ;
361
361
}
362
362
}
@@ -400,11 +400,13 @@ export async function findHaskellLanguageServer(
400
400
if ( promptBeforeDownloads ) {
401
401
const hlsInstalled = projectHls
402
402
? await toolInstalled ( context , logger , 'hls' , projectHls )
403
- : ( [ true , 'hls' , '' ] as [ boolean , Tool , string ] ) ;
403
+ : new InstalledTool ( 'hls' ) ;
404
404
const ghcInstalled = projectGhc
405
405
? 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 ) ;
408
410
if ( toInstall . length > 0 ) {
409
411
const decision = await window . showInformationMessage (
410
412
`Need to download ${ toInstall . join ( ', ' ) } , continue?` ,
@@ -417,11 +419,11 @@ export async function findHaskellLanguageServer(
417
419
} else if ( decision === "Yes, don't ask again" ) {
418
420
workspace . getConfiguration ( 'haskell' ) . update ( 'promptBeforeDownloads' , false ) ;
419
421
} 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' ) {
423
425
throw new MissingToolError ( 'hls' ) ;
424
- } else if ( t === 'ghc' ) {
426
+ } else if ( tool . name === 'ghc' ) {
425
427
projectGhc = null ;
426
428
}
427
429
}
@@ -774,11 +776,11 @@ async function toolInstalled(
774
776
logger : Logger ,
775
777
tool : Tool ,
776
778
version : string
777
- ) : Promise < [ boolean , Tool , string ] > {
779
+ ) : Promise < InstalledTool > {
778
780
const b = await callGHCup ( context , logger , [ 'whereis' , tool , version ] , undefined , false )
779
781
. then ( ( x ) => true )
780
782
. catch ( ( x ) => false ) ;
781
- return [ b , tool , version ] ;
783
+ return new InstalledTool ( tool , version , b ) ;
782
784
}
783
785
784
786
/**
@@ -896,3 +898,26 @@ async function getReleaseMetadata(
896
898
}
897
899
}
898
900
}
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