-
Notifications
You must be signed in to change notification settings - Fork 7
Expand file tree
/
Copy pathTool.purs
More file actions
181 lines (152 loc) · 5.09 KB
/
Tool.purs
File metadata and controls
181 lines (152 loc) · 5.09 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
module Setup.Data.Tool where
import Prelude
import Affjax (URL)
import Data.Bounded.Generic (genericBottom, genericTop)
import Data.Either (fromRight')
import Data.Enum (class Enum, upFromIncluding)
import Data.Enum.Generic (genericPred, genericSucc)
import Data.Foldable (elem, fold)
import Data.Generic.Rep (class Generic)
import Data.Version (parseVersion)
import Node.Path (FilePath)
import Node.Path as Path
import Partial.Unsafe (unsafeCrashWith)
import Setup.Data.Platform (Platform(..), platform)
import Setup.Data.VersionField (VersionField(..))
import Setup.Data.VersionField as VersionField
data Tool
= PureScript
| Spago
| Psa
| PursTidy
| Zephyr
derive instance eqTool :: Eq Tool
derive instance ordTool :: Ord Tool
derive instance genericTool :: Generic Tool _
instance boundedTool :: Bounded Tool where
bottom = genericBottom
top = genericTop
instance enumTool :: Enum Tool where
succ = genericSucc
pred = genericPred
-- | A list of all available tools in the toolchain
allTools :: Array Tool
allTools = upFromIncluding bottom
-- | Tools that are required in the toolchain
requiredTools :: Array Tool
requiredTools = [ PureScript, Spago ]
-- | Tools that are required in the toolchain
required :: Tool -> Boolean
required tool = elem tool requiredTools
name :: Tool -> String
name = case _ of
PureScript -> "purs"
Spago -> "spago"
Psa -> "psa"
PursTidy -> "purs-tidy"
Zephyr -> "zephyr"
-- | The source repository for a tool (whether on GitHub or Gitlab)
type ToolRepository = { owner :: String, name :: String }
repository :: Tool -> ToolRepository
repository = case _ of
PureScript ->
{ owner: "purescript", name: "purescript" }
Spago ->
{ owner: "purescript", name: "spago" }
Psa ->
{ owner: "natefaubion", name: "purescript-psa" }
PursTidy ->
{ owner: "natefaubion", name: "purescript-tidy" }
Zephyr ->
{ owner: "coot", name: "zephyr" }
-- | How a tool will be installed: either a tarball from a URL, or an NPM package
-- | at a particular version.
data InstallMethod = Tarball TarballOpts | NPM NPMPackage
-- | The source used to download a tarball and its path inside the extracted
-- | directory.
type TarballOpts =
{ source :: URL
, getExecutablePath :: FilePath -> FilePath
}
-- | An NPM package. Example: "purescript-psa@0.7.2"
type NPMPackage = String
-- | The installation method for a tool, which includes the source path necessary
-- | to download or install the tool.
installMethod :: Tool -> VersionField -> InstallMethod
installMethod tool versionField = do
let
toolName = name tool
toolRepo = repository tool
formatArgs = { repo: toolRepo, tag: formatTag, tarball: _ }
formatGitHub' = formatGitHub <<< formatArgs
unsafeVersion str = fromRight' (\_ -> unsafeCrashWith "Unexpected Left") $ parseVersion str
executableName = case platform of
Windows -> toolName <> ".exe"
_ -> toolName
case tool of
PureScript -> Tarball
{ source: formatGitHub' case platform of
Windows -> "win64"
Mac -> "macos"
Linux -> "linux64"
, getExecutablePath: \p -> Path.concat [ p, "purescript", executableName ]
}
Spago -> Tarball
{ source: formatGitHub'
-- Spago has changed naming conventions from version to version
case versionField of
Exact version
| version >= unsafeVersion "0.18.1" ->
case platform of
Windows -> "Windows"
Mac -> "macOS"
Linux -> "Linux"
| version == unsafeVersion "0.18.1" ->
case platform of
Windows -> "windows-latest"
Mac -> "macOS-latest"
Linux -> "linux-latest"
_ ->
case platform of
Windows -> "windows"
Mac -> "osx"
Linux -> "linux"
, getExecutablePath: \p -> Path.concat [ p, executableName ]
}
Psa ->
NPM ("purescript-psa@" <> VersionField.showVersionField versionField)
PursTidy ->
NPM ("purs-tidy@" <> VersionField.showVersionField versionField)
Zephyr -> Tarball
{ source: formatGitHub' $ case platform of
Windows -> "Windows"
Mac -> "macOS"
Linux -> "Linux"
, getExecutablePath: \p -> Path.concat [ p, "zephyr", executableName ]
}
where
-- Format the release tag for a tool at a specific version. Not all tools use
-- the same format.
--
-- Example: "v0.13.2", "0.15.2"
formatTag :: String
formatTag = do
let versionStr = VersionField.showVersionField versionField
if tool `elem` [ PureScript, Zephyr ] then
fold [ "v", versionStr ]
else
versionStr
formatGitHub :: { repo :: ToolRepository, tag :: String, tarball :: String } -> String
formatGitHub { repo, tag, tarball } =
-- Example: https://github.com/purescript/purescript/releases/download/v0.13.8/win64.tar.gz
fold
[ "https://github.com/"
, repo.owner
, "/"
, repo.name
, "/releases/download/"
, tag
, "/"
, tarball
, ".tar.gz"
]