Commit | Line | Data |
---|---|---|
96dbc930 ELB |
1 | #compdef guix |
2 | # | |
3 | # GNU Guix --- Functional package management for GNU | |
4 | # Copyright © 2016 Eric Le Bihan <eric.le.bihan.dev@free.fr> | |
5 | # | |
6 | # This file is part of GNU Guix. | |
7 | # | |
8 | # GNU Guix is free software; you can redistribute it and/or modify it | |
9 | # under the terms of the GNU General Public License as published by | |
10 | # the Free Software Foundation; either version 3 of the License, or (at | |
11 | # your option) any later version. | |
12 | # | |
13 | # GNU Guix is distributed in the hope that it will be useful, but | |
14 | # WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
16 | # GNU General Public License for more details. | |
17 | # | |
18 | # You should have received a copy of the GNU General Public License | |
19 | # along with GNU Guix. If not, see <http://www.gnu.org/licenses/>. | |
20 | ||
21 | ||
22 | _guix_caching_policy() | |
23 | { | |
24 | local -a old_policy | |
25 | old_policy=( "$1"(Nmh+24) ) | |
26 | (( $#old_policy )) | |
27 | } | |
28 | ||
29 | _guix_list_actions() | |
30 | { | |
31 | _guix_actions=( $(guix system --help | sed -n 's/^ \([a-z-]\+\)\s\+.\+/\1/p') ) | |
32 | } | |
33 | ||
34 | _guix_list_checkers() | |
35 | { | |
36 | _guix_checkers=( $(guix lint -l | sed -n 's/^- \(.\+\): .\+/\1/p') ) | |
37 | } | |
38 | ||
39 | _guix_list_graph_types() | |
40 | { | |
41 | _guix_graph_types=( $(guix graph --list-types | sed -n 's/^ - \(.\+\): .\+/\1/p') ) | |
42 | } | |
43 | ||
44 | _guix_list_importers() | |
45 | { | |
46 | _guix_importers=( $(guix import --help | sed -n 's/^\s\+\([a-z]\+\)$/\1/p') ) | |
47 | } | |
48 | ||
49 | _guix_list_updaters() | |
50 | { | |
51 | _guix_updaters=( $(guix lint -l | sed -n 's/^- \(.\+\): .\+/\1/p') ) | |
52 | } | |
53 | ||
54 | _guix_list_available_packages() | |
55 | { | |
56 | if ( [[ ${+_guix_available_packages} -eq 0 ]] || _cache_invalid GUIX_AVAILABLE_PACKAGES ) \ | |
57 | && ! _retrieve_cache GUIX_AVAILABLE_PACKAGES; then | |
58 | _guix_available_packages=(${${(f)"$(guix package -A | cut -f1)"}}) | |
59 | _store_cache GUIX_AVAILABLE_PACKAGES _guix_available_packages | |
60 | fi | |
61 | } | |
62 | ||
63 | _guix_list_installed_packages() | |
64 | { | |
65 | _guix_installed_packages=( $(guix package -I "^${prefix}" | cut -f1) ) | |
66 | } | |
67 | ||
68 | (( $+functions[_guix_build] )) || _guix_build() | |
69 | { | |
70 | _arguments \ | |
71 | '--expression=[build the package matching EXPR]:EXPR' \ | |
72 | '--file=[build the package matching code evaluated from FILE]:FILE:_files' \ | |
73 | '--source[build the packages source derivations]' \ | |
74 | '--sources=[build source derivations]:TYPE:(all package transitive)' \ | |
75 | '--system=[attempt to build for SYSTEM (e.g. "i686-linux")]:SYSTEM' \ | |
76 | '--target=[cross-build for TRIPLET (e.g. "armel-linux-gnu")]:TRIPLET' \ | |
77 | '--derivations[return the derivation paths of the given packages]' \ | |
78 | '--check[rebuild items to check for non-determinism issues]' \ | |
79 | '--root=[symlink result to FILE and register it as GC root]:FILE:_files' \ | |
80 | '--quiet[do not show the build log]' \ | |
81 | '--log-file[return the log file names for the given derivations]' \ | |
82 | '--load-path=[prepend DIR to the package module search path]:DIR:_dirs' \ | |
83 | '--keep-failed[keep build tree of failed builds]' \ | |
84 | '--keep-going[keep going when some of the derivations fail]' \ | |
85 | '--dry-run[do not build the derivations]' \ | |
86 | '--fallback[fall back to building when the substituter fails]' \ | |
87 | '--no-substitutes[build instead of resorting to pre-built substitutes]' \ | |
88 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URLS:_urls' \ | |
89 | '--no-grafts[do not graft packages]' \ | |
dc209d5a | 90 | '--no-offload[do not attempt to offload builds]' \ |
96dbc930 ELB |
91 | '--max-silent-time=[mark the build as failed after SECONDS of silence]:SECONDS' \ |
92 | '--timeout=[mark the build as failed after SECONDS of activity]:SECONDS' \ | |
93 | '--verbosity=[use the given verbosity LEVEL]:LEVEL' \ | |
94 | '--rounds=[build N times in a row to detect non-determinism]:N' \ | |
95 | '--cores=[allow the use of up to N CPU cores for the build]:N' \ | |
96 | '--max-jobs=[allow at most N build jobs]:N' \ | |
97 | '--with-source=[use SOURCE when building the corresponding package]:SOURCE' \ | |
98 | '--with-input=[replace dependency PACKAGE by REPLACEMENT]:PACKAGE=REPLACEMENT' \ | |
99 | '*:package:->packages' | |
100 | ||
101 | if [[ "$state" = packages ]]; then | |
102 | _guix_list_available_packages | |
103 | compadd -a -- _guix_available_packages | |
104 | fi | |
105 | } | |
106 | ||
107 | (( $+functions[_guix_challenge] )) || _guix_challenge() | |
108 | { | |
109 | _arguments \ | |
110 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URL:_urls' \ | |
111 | '*:package:->packages' | |
112 | ||
113 | if [[ "$state" = packages ]]; then | |
114 | _guix_list_available_packages | |
115 | compadd -a -- _guix_available_packages | |
116 | fi | |
117 | } | |
118 | ||
119 | (( $+functions[_guix_container] )) || _guix_container() | |
120 | { | |
121 | _arguments \ | |
122 | ':action:(exec)' \ | |
123 | '*:args' | |
124 | } | |
125 | ||
126 | (( $+functions[_guix_download] )) || _guix_download() | |
127 | { | |
128 | _arguments \ | |
129 | '--format=[write the hash in the given format]:FMT:(nix-base32 base16 base32 hex)' \ | |
130 | '1:URL:_urls' | |
131 | } | |
132 | ||
133 | (( $+functions[_guix_edit] )) || _guix_edit() | |
134 | { | |
135 | _guix_list_available_packages | |
136 | compadd -a -- _guix_available_packages | |
137 | } | |
138 | ||
139 | (( $+functions[_guix_environment] )) || _guix_environment() | |
140 | { | |
141 | _arguments \ | |
142 | '--expression=[create environment for the package evaluated from EXPR]:EXPR' \ | |
143 | '--load=[create environment for the package evaluated from FILE]:FILE:_files' \ | |
144 | '--ad-hoc[include all specified packages, not only their inputs]' \ | |
145 | '--pure[unset existing environment variables]' \ | |
146 | '--search-paths[display needed environment variable definitions]' \ | |
147 | '--system=[attempt to build for SYSTEM (e.g. "i686-linux")]:SYSTEM' \ | |
148 | '--container[run command within an isolated container]' \ | |
149 | '--network[allow containers to access the network]' \ | |
150 | '--share=[share writable host file system according to SPEC]:SPEC' \ | |
151 | '--expose=[expose read-only host file system according to SPEC]:SPEC' \ | |
152 | '--bootstrap[use bootstrap binaries to build the environment]' \ | |
153 | '--load-path=[prepend DIR to the package module search path]:DIR:_dirs' \ | |
154 | '--keep-failed[keep build tree of failed builds]' \ | |
155 | '--keep-going[keep going when some of the derivations fail]' \ | |
156 | '--dry-run[do not build the derivations]' \ | |
157 | '--fallback[fall back to building when the substituter fails]' \ | |
158 | '--no-substitutes[build instead of resorting to pre-built substitutes]' \ | |
159 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URLS:_urls' \ | |
160 | '--no-grafts[do not graft packages]' \ | |
dc209d5a | 161 | '--no-offload[do not attempt to offload builds]' \ |
96dbc930 ELB |
162 | '--max-silent-time=[mark the build as failed after SECONDS of silence]:SECONDS' \ |
163 | '--timeout=[mark the build as failed after SECONDS of activity]:SECONDS' \ | |
164 | '--verbosity=[use the given verbosity LEVEL]:LEVEL' \ | |
165 | '--rounds=[build N times in a row to detect non-determinism]:N' \ | |
166 | '--cores=[allow the use of up to N CPU cores for the build]:N' \ | |
167 | '--max-jobs=[allow at most N build jobs]:N' \ | |
168 | '*:package:->packages' | |
169 | ||
170 | if [[ "$state" = packages ]]; then | |
171 | _guix_list_available_packages | |
172 | compadd -a -- _guix_available_packages | |
173 | fi | |
174 | ||
175 | } | |
176 | ||
177 | (( $+functions[_guix_gc] )) || _guix_gc() | |
178 | { | |
179 | _arguments \ | |
180 | '--collect-garbage=[collect at least MIN bytes of garbage]:MIN' \ | |
181 | '--free-space=[attempt to reach FREE available space in the store]:FREE' \ | |
182 | '--delete[attempt to delete PATHS]' \ | |
183 | '--optimize[optimize the store by deduplicating identical files]' \ | |
184 | '--list-dead[list dead paths]' \ | |
185 | '--list-live[list live paths]' \ | |
186 | '--references[list the references of PATHS]' \ | |
187 | '--requisites[list the requisites of PATHS]' \ | |
188 | '--referrers[list the referrers of PATHS]' \ | |
189 | '--verify=[verify the integrity of the store]:OPTS:(contents repair)' \ | |
190 | '--list-failures[list cached build failures]' \ | |
191 | '--clear-failures[remove PATHS from the set of cached failures]' \ | |
192 | '1:PATH:_dirs' | |
193 | } | |
194 | ||
195 | (( $+functions[_guix_graph] )) || _guix_graph() | |
196 | { | |
197 | _arguments \ | |
198 | '--type=[represent nodes of the given TYPE]:TYPE:->types' \ | |
199 | '--list-types[list the available graph types]' \ | |
200 | '--expression=[consider the package EXPR evaluates to]:EXPR' \ | |
201 | '1:PACKAGE:->packages' | |
202 | ||
203 | case "$state" in | |
204 | types) | |
205 | _guix_list_graph_types | |
206 | compadd -a -- _guix_graph_types | |
207 | ;; | |
208 | packages) | |
209 | _guix_list_available_packages | |
210 | compadd -a -- _guix_available_packages | |
211 | ;; | |
212 | esac | |
213 | ||
214 | } | |
215 | ||
216 | (( $+functions[_guix_hash] )) || _guix_hash() | |
217 | { | |
218 | _arguments \ | |
219 | '--format=[write the hash in the given format]:FMT:(nix-base32 base16 base32 hex)' \ | |
220 | '--recursive[compute the hash on FILE recursively]'\ | |
221 | '1:FILE:_files' | |
222 | } | |
223 | ||
224 | (( $+functions[_guix_import] )) || _guix_import() | |
225 | { | |
226 | _arguments \ | |
227 | '1:IMPORTER:->importer' \ | |
228 | '*:args:' | |
229 | ||
230 | if [[ "$state" = importer ]]; then | |
231 | _guix_list_importers | |
232 | compadd -a -- _guix_importers | |
233 | fi | |
234 | } | |
235 | ||
236 | (( $+functions[_guix_lint] )) || _guix_lint() | |
237 | { | |
238 | _arguments \ | |
239 | '--checkers=[only run the specified checkers]:CHECKERS:->checkers' \ | |
240 | '--list-checkers[display the list of available lint checkers]' \ | |
241 | '1:PACKAGE:->packages' | |
242 | ||
243 | case "$state" in | |
244 | checkers) | |
245 | _guix_list_checkers | |
246 | compadd -a -- _guix_checkers | |
247 | ;; | |
248 | packages) | |
249 | _guix_list_available_packages | |
250 | compadd -a -- _guix_available_packages | |
251 | ;; | |
252 | esac | |
253 | } | |
254 | ||
255 | (( $+functions[_guix_package] )) || _guix_package() | |
256 | { | |
257 | _arguments \ | |
258 | '--install[install one or more packages]: :->install' \ | |
259 | '--install-from-expression=[install the package EXP evaluates to]:EXP' \ | |
260 | '--install-from-file=[install the package evaluated from FILE]:FILE:_files' \ | |
261 | '--remove[remove one or more packages]: :->remove' \ | |
262 | '--upgrade=[upgrade all the installed packages matching REGEXP]:REGEXP' \ | |
263 | '--manifest=[create a new profile generation from FILE]:FILE:_files' \ | |
264 | '--do-not-upgrade=[do not upgrade any packages matching REGEXP]:REGEXP' \ | |
265 | '--roll-back[roll back to the previous generation]' \ | |
266 | '--search-paths=[display needed environment variable definitions]:KINDS' \ | |
267 | '--list-generations=[list generations matching PATTERN]:PATTERN' \ | |
268 | '--delete-generations=[delete generations matching PATTERN]:PATTERN' \ | |
269 | '--switch-generation=[switch to a generation matching PATTERN]:PATTERN' \ | |
270 | '--profile=[use PROFILE instead of the default profile]:PROFILE' \ | |
271 | '--bootstrap[use the bootstrap Guile to build the profile]' \ | |
272 | '--verbose[produce verbose output]' \ | |
273 | '--search=[search in synopsis and description using REGEXP]:REGEXP' \ | |
274 | '--list-installed=[list installed packages matching REGEXP]:REGEXP' \ | |
275 | '--list-available=[list available packages matching REGEXP]:REGEXP' \ | |
276 | '--show=[show details about a package]: :->show' \ | |
277 | '--load-path=[prepend DIR to the package module search path]:DIR:_dirs' \ | |
278 | '--keep-failed[keep build tree of failed builds]' \ | |
279 | '--keep-going[keep going when some of the derivations fail]' \ | |
280 | '--dry-run[do not build the derivations]' \ | |
281 | '--fallback[fall back to building when the substituter fails]' \ | |
282 | '--no-substitutes[build instead of resorting to pre-built substitutes]' \ | |
283 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URLS:_urls' \ | |
284 | '--no-grafts[do not graft packages]' \ | |
dc209d5a | 285 | '--no-offload[do not attempt to offload builds]' \ |
96dbc930 ELB |
286 | '--max-silent-time=[mark the build as failed after SECONDS of silence]:SECONDS' \ |
287 | '--timeout=[mark the build as failed after SECONDS of activity]:SECONDS' \ | |
288 | '--verbosity=[use the given verbosity LEVEL]:LEVEL' \ | |
289 | '--rounds=[build N times in a row to detect non-determinism]:N' \ | |
290 | '--cores=[allow the use of up to N CPU cores for the build]:N' \ | |
291 | '--max-jobs=[allow at most N build jobs]:N' \ | |
292 | '--with-source=[use SOURCE when building the corresponding package]:SOURCE' \ | |
293 | '--with-input=[replace dependency PACKAGE by REPLACEMENT]:PACKAGE=REPLACEMENT' | |
294 | ||
295 | case "$state" in | |
296 | install|show) | |
297 | _guix_list_available_packages | |
298 | compadd -a -- _guix_available_packages | |
299 | ;; | |
300 | remove) | |
301 | _guix_list_installed_packages | |
302 | compadd -a -- _guix_installed_packages | |
303 | ;; | |
304 | esac | |
305 | } | |
306 | ||
307 | (( $+functions[_guix_publish] )) || _guix_publish() | |
308 | { | |
309 | _arguments \ | |
310 | '--port=[listen on PORT]:PORT:' \ | |
311 | '--listen=[listen on the network interface for HOST]:HOST:_hosts' \ | |
312 | '--user=[change privileges to USER as soon as possible]:USER:_users' \ | |
313 | '--compression=[compress archives at LEVEL]:LEVEL' \ | |
314 | '--ttl=[announce narinfos can be cached for TTL seconds]:TTL' \ | |
315 | '--repl=[spawn REPL server on PORT]:PORT' | |
316 | } | |
317 | ||
318 | (( $+functions[_guix_pull] )) || _guix_pull() | |
319 | { | |
320 | _arguments \ | |
321 | '--verbose[produce verbose output]' \ | |
322 | '--url=[download the Guix tarball from URL]:URL:_urls' \ | |
323 | '--bootstrap[use the bootstrap Guile to build the new Guix]' | |
324 | } | |
325 | ||
326 | (( $+functions[_guix_refresh] )) || _guix_refresh() | |
327 | { | |
328 | _arguments \ | |
329 | '--expression=[consider the package EXPR evaluates to]:EXPR' \ | |
330 | '--update[update source files in place]' \ | |
331 | '--select=[select all the packages in SUBSET]:SUBSET:(core non-core)' \ | |
332 | '--type=[restrict to updates from the specified updaters]:UPDATER:->updaters' \ | |
333 | '--list-updaters[list available updaters and exit]' \ | |
334 | '--list-dependent[list top-level dependent packages]' \ | |
335 | '--key-server=[use HOST as the OpenPGP key server]:HOST:_hosts' \ | |
336 | '--gpg=[use COMMAND as the GnuPG 2.x command]:COMMAND' \ | |
337 | '--key-download=[policy to handle missing OpenPGP keys]:POLICY:(always interactive never)' \ | |
338 | '*:package:->packages' | |
339 | ||
340 | case "$state" in | |
341 | updaters) | |
342 | _guix_list_updaters | |
343 | compadd -a -- _guix_updaters | |
344 | ;; | |
345 | packages) | |
346 | _guix_list_available_packages | |
347 | compadd -a -- _guix_available_packages | |
348 | ;; | |
349 | esac | |
350 | } | |
351 | ||
352 | (( $+functions[_guix_size] )) || _guix_size() | |
353 | { | |
354 | _arguments \ | |
355 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URL:_urls' \ | |
356 | '-system=[consider packages for SYSTEM--e.g., "i686-linux"]:SYSTEM' \ | |
357 | '--map-file=[write to FILE a graphical map of disk usage]:FILE:_files' \ | |
358 | '*:package:->packages' | |
359 | ||
360 | if [[ "$state" = packages ]]; then | |
361 | _guix_list_available_packages | |
362 | compadd -a -- _guix_available_packages | |
363 | fi | |
364 | } | |
365 | ||
366 | (( $+functions[_guix_system] )) || _guix_system() | |
367 | { | |
368 | _arguments \ | |
369 | '--load-path=[prepend DIR to the package module search path]:DIR:_dirs' \ | |
370 | '--keep-failed[keep build tree of failed builds]' \ | |
371 | '--keep-going[keep going when some of the derivations fail]' \ | |
372 | '--dry-run[do not build the derivations]' \ | |
373 | '--fallback[fall back to building when the substituter fails]' \ | |
374 | '--no-substitutes[build instead of resorting to pre-built substitutes]' \ | |
375 | '--substitute-urls=[fetch substitute from URLS if they are authorized]:URL:_urls' \ | |
376 | '--no-grafts[do not graft packages]' \ | |
dc209d5a | 377 | '--no-offload[do not attempt to offload builds]' \ |
96dbc930 ELB |
378 | '--max-silent-time=[mark the build as failed after SECONDS of silence]:SECONDS' \ |
379 | '--timeout=[mark the build as failed after SECONDS of activity]:SECONDS' \ | |
380 | '--verbosity=[use the given verbosity LEVEL]:LEVEL' \ | |
381 | '--rounds=[build N times in a row to detect non-determinism]:N' \ | |
382 | '--cores=[allow the use of up to N CPU cores for the build]:N' \ | |
383 | '--max-jobs=[allow at most N build jobs]:N' \ | |
384 | '--derivation[return the derivation of the given system]' \ | |
385 | '--on-error=[apply STRATEGY when an error occurs while reading FILE]:STRATEGY' \ | |
ee2a5da8 | 386 | '--image-size=[for "image", produce an image of SIZE]:SIZE' \ |
96dbc930 ELB |
387 | '--no-grub[for "init", do not install GRUB]' \ |
388 | '--share=[for "vm", share host file system according to SPEC]:SPEC' \ | |
389 | '--expose=[for "vm", expose host file system according to SPEC]:SPEC' \ | |
390 | '--full-boot[for "vm", make a full boot sequence]' \ | |
391 | '1:action:->actions' \ | |
392 | '*:file:_files' | |
393 | ||
394 | if [[ "$state" = actions ]]; then | |
395 | _guix_list_actions | |
396 | compadd -a -- _guix_actions | |
397 | fi | |
398 | } | |
399 | ||
400 | (( $+functions[_guix_command] )) || _guix_command() | |
401 | { | |
402 | local -a _guix_cmds | |
403 | _guix_cmds=( | |
404 | "archive:Export/import one or more packages from/to the store" | |
405 | "build:Build a given package" | |
406 | "challenge:Challenge the substitutes for a package" | |
407 | "container:Build and manipulate Linux containers" | |
408 | "download:Download the file at given URL and add it to the store" | |
409 | "edit:Edit the definitions of a package" | |
410 | "environment:Build an environment with a package and its dependencies" | |
411 | "gc:Invoke the garbage collector" | |
412 | "graph:Emit a DOT representation of the dependencies of a package" | |
413 | "hash:Return the cryptographic hash of a file" | |
414 | "import:Run an importer" | |
415 | "lint:Run a set of checkers on a package" | |
416 | "package:Install, remove, or upgrade packages" | |
417 | "publish:Publish /gnu/store over HTTP." | |
418 | "pull:Download and deploy the latest version of Guix" | |
419 | "refresh:Update package definitions to match the latest version" | |
420 | "size:Report the size of a package and its dependencies" | |
421 | "system:Build the operating system" | |
422 | ) | |
423 | ||
424 | if (( CURRENT == 1 )); then | |
425 | _describe -t commands 'guix command' _guix_cmds || compadd "$@" | |
426 | else | |
427 | local curcontext="$curcontext" | |
428 | ||
429 | cmd="${${_guix_cmds[(r)$words[1]:*]%%:*}}" | |
430 | ||
431 | if (( $#cmd )); then | |
432 | local cache_policy | |
433 | ||
434 | zstyle -s ":completion:${curcontext}:" cache-policy cache_policy | |
435 | if [[ -z "$cache_policy" ]]; then | |
436 | zstyle ":completion:${curcontext}:" cache-policy _guix_caching_policy | |
437 | fi | |
438 | ||
439 | curcontext="${curcontext%:*:*}:guix-${cmd}:" | |
440 | ||
441 | _call_function ret _guix_${cmd} || _message 'no more arguments' | |
442 | else | |
443 | _message "unknown guix command: $words[1]" | |
444 | fi | |
445 | return ret | |
446 | fi | |
447 | } | |
448 | ||
449 | _arguments \ | |
450 | '(--version)--version[Display version information and exit]' \ | |
451 | '*::guix command:_guix_command' | |
452 | ||
453 | # vim: ts=4 sts=4 sw=4 et ai | |
454 | # Local variables: | |
455 | # mode: sh | |
456 | # End: |