@@ -442,8 +442,8 @@ installAction flags@NixStyleFlags{extraFlags, configFlags, installFlags, project
442
442
let
443
443
GhcImplInfo {supportsPkgEnvFiles} = getImplInfo compiler
444
444
445
- envFile <- getEnvFile clientInstallFlags platform compilerVersion
446
- existingEnvEntries <-
445
+ (usedPackageEnvFlag, envFile) <- getEnvFile clientInstallFlags platform compilerVersion
446
+ (usedExistingPkgEnvFile, existingEnvEntries) <-
447
447
getExistingEnvEntries verbosity compilerFlavor supportsPkgEnvFiles envFile
448
448
packageDbs <- getPackageDbStack compiler projectConfigStoreDir projectConfigLogsDir projectConfigPackageDBs
449
449
installedIndex <- getInstalledPackages verbosity compiler packageDbs progDb
@@ -534,6 +534,7 @@ installAction flags@NixStyleFlags{extraFlags, configFlags, installFlags, project
534
534
packageDbs
535
535
envFile
536
536
nonGlobalEnvEntries'
537
+ (not usedExistingPkgEnvFile && not usedPackageEnvFlag)
537
538
else -- Install any built exe by symlinking or copying it we don't use
538
539
-- BuildOutcomes because we also need the component names
539
540
traverseInstall (installCheckUnitExes InstallCheckInstall ) installCfg
@@ -960,6 +961,9 @@ installLibraries
960
961
-> FilePath
961
962
-- ^ Environment file
962
963
-> [GhcEnvironmentFileEntry ]
964
+ -> Bool
965
+ -- ^ Whether we need to show a warning (i.e. we created a new environment
966
+ -- file, and the user did not use --package-env)
963
967
-> IO ()
964
968
installLibraries
965
969
verbosity
@@ -968,7 +972,8 @@ installLibraries
968
972
compiler
969
973
packageDbs'
970
974
envFile
971
- envEntries = do
975
+ envEntries
976
+ showWarning = do
972
977
if supportsPkgEnvFiles $ getImplInfo compiler
973
978
then do
974
979
let validDb (SpecificPackageDB fp) = doesPathExist fp
@@ -994,6 +999,27 @@ installLibraries
994
999
contents' = renderGhcEnvironmentFile (baseEntries ++ pkgEntries)
995
1000
createDirectoryIfMissing True (takeDirectory envFile)
996
1001
writeFileAtomic envFile (BS. pack contents')
1002
+ when showWarning $
1003
+ warn verbosity $
1004
+ " The libraries were installed by creating a global GHC environment file at:\n "
1005
+ ++ envFile
1006
+ ++ " \n "
1007
+ ++ " \n "
1008
+ ++ " The presence of such an environment file is likely to confuse or break other "
1009
+ ++ " tools because it changes GHC's behaviour: it changes the default package set in "
1010
+ ++ " ghc and ghci from its normal value (which is \" all boot libraries\" ). GHC "
1011
+ ++ " environment files are little-used and often not tested for.\n "
1012
+ ++ " \n "
1013
+ ++ " Furthermore, management of these environment files is still more difficult than "
1014
+ ++ " it could be; see e.g. https://github.com/haskell/cabal/issues/6481 .\n "
1015
+ ++ " \n "
1016
+ ++ " Double-check that creating a global GHC environment file is really what you "
1017
+ ++ " wanted! You can limit the effects of the environment file by creating it in a "
1018
+ ++ " specific directory using the --package-env flag. For example, use:\n "
1019
+ ++ " \n "
1020
+ ++ " cabal install --lib <packages...> --package-env .\n "
1021
+ ++ " \n "
1022
+ ++ " to create the file in the current directory."
997
1023
else
998
1024
warn verbosity $
999
1025
" The current compiler doesn't support safely installing libraries, "
@@ -1224,46 +1250,50 @@ entriesForLibraryComponents = Map.foldrWithKey' (\k v -> mappend (go k v)) []
1224
1250
| any hasLib targets = [GhcEnvFilePackageId unitId]
1225
1251
| otherwise = []
1226
1252
1227
- -- | Gets the file path to the request environment file.
1228
- getEnvFile :: ClientInstallFlags -> Platform -> Version -> IO FilePath
1253
+ -- | Gets the file path to the request environment file. The @Bool@ is @True@
1254
+ -- if we got an explicit instruction using @--package-env@, @False@ if we used
1255
+ -- the default.
1256
+ getEnvFile :: ClientInstallFlags -> Platform -> Version -> IO (Bool , FilePath )
1229
1257
getEnvFile clientInstallFlags platform compilerVersion = do
1230
1258
appDir <- getGhcAppDir
1231
1259
case flagToMaybe (cinstEnvironmentPath clientInstallFlags) of
1232
1260
Just spec
1233
1261
-- Is spec a bare word without any "pathy" content, then it refers to
1234
1262
-- a named global environment.
1235
1263
| takeBaseName spec == spec ->
1236
- return (getGlobalEnv appDir platform compilerVersion spec)
1264
+ return (True , getGlobalEnv appDir platform compilerVersion spec)
1237
1265
| otherwise -> do
1238
1266
spec' <- makeAbsolute spec
1239
1267
isDir <- doesDirectoryExist spec'
1240
1268
if isDir
1241
1269
then -- If spec is a directory, then make an ambient environment inside
1242
1270
-- that directory.
1243
- return (getLocalEnv spec' platform compilerVersion)
1271
+ return (True , getLocalEnv spec' platform compilerVersion)
1244
1272
else -- Otherwise, treat it like a literal file path.
1245
- return spec'
1273
+ return ( True , spec')
1246
1274
Nothing ->
1247
- return (getGlobalEnv appDir platform compilerVersion " default" )
1275
+ return (False , getGlobalEnv appDir platform compilerVersion " default" )
1248
1276
1249
- -- | Returns the list of @GhcEnvFilePackageIj@ values already existing in the
1250
- -- environment being operated on.
1251
- getExistingEnvEntries :: Verbosity -> CompilerFlavor -> Bool -> FilePath -> IO [GhcEnvironmentFileEntry ]
1277
+ -- | Returns the list of @GhcEnvFilePackageId@ values already existing in the
1278
+ -- environment being operated on. The @Bool@ is @True@ if we took settings
1279
+ -- from an existing file, @False@ otherwise.
1280
+ getExistingEnvEntries :: Verbosity -> CompilerFlavor -> Bool -> FilePath -> IO (Bool , [GhcEnvironmentFileEntry ])
1252
1281
getExistingEnvEntries verbosity compilerFlavor supportsPkgEnvFiles envFile = do
1253
1282
envFileExists <- doesFileExist envFile
1254
- filterEnvEntries
1255
- <$> if (compilerFlavor == GHC || compilerFlavor == GHCJS )
1283
+ (usedExisting, allEntries) <-
1284
+ if (compilerFlavor == GHC || compilerFlavor == GHCJS )
1256
1285
&& supportsPkgEnvFiles
1257
1286
&& envFileExists
1258
- then catch (readGhcEnvironmentFile envFile) $ \ (_ :: ParseErrorExc ) ->
1287
+ then catch (( True ,) <$> readGhcEnvironmentFile envFile) $ \ (_ :: ParseErrorExc ) ->
1259
1288
warn
1260
1289
verbosity
1261
1290
( " The environment file "
1262
1291
++ envFile
1263
1292
++ " is unparsable. Libraries cannot be installed."
1264
1293
)
1265
- >> return []
1266
- else return []
1294
+ >> return (False , [] )
1295
+ else return (False , [] )
1296
+ return (usedExisting, filterEnvEntries allEntries)
1267
1297
where
1268
1298
-- Why? We know what the first part will be, we only care about the packages.
1269
1299
filterEnvEntries = filter $ \ case
0 commit comments