1 {-# LANGUAGE DeriveDataTypeable #-}
2 {-# LANGUAGE DeriveGeneric #-}
4 module Distribution
.Types
.HookedBuildInfo
9 -- import Distribution.Compat.Prelude
10 import Distribution
.Types
.BuildInfo
11 import Distribution
.Types
.UnqualComponentName
13 -- | 'HookedBuildInfo' is mechanism that hooks can use to
14 -- override the 'BuildInfo's inside packages. One example
15 -- use-case (which is used in core libraries today) is as
16 -- a way of passing flags which are computed by a configure
17 -- script into Cabal. In this case, the autoconf build type adds
18 -- hooks to read in a textual 'HookedBuildInfo' format prior
19 -- to doing any operations.
21 -- Quite honestly, this mechanism is a massive hack since we shouldn't
22 -- be editing the 'PackageDescription' data structure (it's easy
23 -- to assume that this data structure shouldn't change and
24 -- run into bugs, see for example 1c20a6328579af9e37677d507e2e9836ef70ab9d).
25 -- But it's a bit convenient, because there isn't another data
26 -- structure that allows adding extra 'BuildInfo' style things.
28 -- In any case, a lot of care has to be taken to make sure the
29 -- 'HookedBuildInfo' is applied to the 'PackageDescription'. In
30 -- general this process occurs in "Distribution.Simple", which is
31 -- responsible for orchestrating the hooks mechanism. The
34 -- 1. We run the pre-hook, which produces a 'HookedBuildInfo'
35 -- (e.g., in the Autoconf case, it reads it out from a file).
36 -- 2. We sanity-check the hooked build info with
37 -- 'sanityCheckHookedBuildInfo'.
38 -- 3. We update our 'PackageDescription' (either freshly read
39 -- or cached from 'LocalBuildInfo') with 'updatePackageDescription'.
41 -- In principle, we are also supposed to update the copy of
42 -- the 'PackageDescription' stored in 'LocalBuildInfo'
43 -- at 'localPkgDescr'. Unfortunately, in practice, there
44 -- are lots of Custom setup scripts which fail to update
45 -- 'localPkgDescr' so you really shouldn't rely on it.
46 -- It's not DEPRECATED because there are legitimate uses
47 -- for it, but... yeah. Sharp knife. See
48 -- <https://github.com/haskell/cabal/issues/3606>
49 -- for more information on the issue.
51 -- It is not well-specified whether or not a 'HookedBuildInfo' applied
52 -- at configure time is persistent to the 'LocalBuildInfo'. The
53 -- fact that 'HookedBuildInfo' is passed to 'confHook' MIGHT SUGGEST
54 -- that the 'HookedBuildInfo' is applied at this time, but actually
55 -- since 9317b67e6122ab14e53f81b573bd0ecb388eca5a it has been ONLY used
56 -- to create a modified package description that we check for problems:
57 -- it is never actually saved to the LBI. Since 'HookedBuildInfo' is
58 -- applied monoidally to the existing build infos (and it is not an
59 -- idempotent monoid), it could break things to save it, since we
60 -- are obligated to apply any new 'HookedBuildInfo' and then we'd
61 -- get the effect twice. But this does mean we have to re-apply
62 -- it every time. Hey, it's more flexibility.
63 type HookedBuildInfo
= (Maybe BuildInfo
, [(UnqualComponentName
, BuildInfo
)])
65 emptyHookedBuildInfo
:: HookedBuildInfo
66 emptyHookedBuildInfo
= (Nothing
, [])