1// Package main is complete tool for the go command line
2package main
3
4import "github.com/posener/complete"
5
6var (
7	ellipsis   = complete.PredictSet("./...")
8	anyPackage = complete.PredictFunc(predictPackages)
9	goFiles    = complete.PredictFiles("*.go")
10	anyFile    = complete.PredictFiles("*")
11	anyGo      = complete.PredictOr(goFiles, anyPackage, ellipsis)
12)
13
14func main() {
15	build := complete.Command{
16		Flags: complete.Flags{
17			"-o": anyFile,
18			"-i": complete.PredictNothing,
19
20			"-a":             complete.PredictNothing,
21			"-n":             complete.PredictNothing,
22			"-p":             complete.PredictAnything,
23			"-race":          complete.PredictNothing,
24			"-msan":          complete.PredictNothing,
25			"-v":             complete.PredictNothing,
26			"-work":          complete.PredictNothing,
27			"-x":             complete.PredictNothing,
28			"-asmflags":      complete.PredictAnything,
29			"-buildmode":     complete.PredictAnything,
30			"-compiler":      complete.PredictAnything,
31			"-gccgoflags":    complete.PredictSet("gccgo", "gc"),
32			"-gcflags":       complete.PredictAnything,
33			"-installsuffix": complete.PredictAnything,
34			"-ldflags":       complete.PredictAnything,
35			"-linkshared":    complete.PredictNothing,
36			"-pkgdir":        anyPackage,
37			"-tags":          complete.PredictAnything,
38			"-toolexec":      complete.PredictAnything,
39		},
40		Args: anyGo,
41	}
42
43	run := complete.Command{
44		Flags: complete.Flags{
45			"-exec": complete.PredictAnything,
46		},
47		Args: goFiles,
48	}
49
50	test := complete.Command{
51		Flags: complete.Flags{
52			"-args": complete.PredictAnything,
53			"-c":    complete.PredictNothing,
54			"-exec": complete.PredictAnything,
55
56			"-bench":     predictBenchmark,
57			"-benchtime": complete.PredictAnything,
58			"-count":     complete.PredictAnything,
59			"-cover":     complete.PredictNothing,
60			"-covermode": complete.PredictSet("set", "count", "atomic"),
61			"-coverpkg":  complete.PredictDirs("*"),
62			"-cpu":       complete.PredictAnything,
63			"-run":       predictTest,
64			"-short":     complete.PredictNothing,
65			"-timeout":   complete.PredictAnything,
66
67			"-benchmem":             complete.PredictNothing,
68			"-blockprofile":         complete.PredictFiles("*.out"),
69			"-blockprofilerate":     complete.PredictAnything,
70			"-coverprofile":         complete.PredictFiles("*.out"),
71			"-cpuprofile":           complete.PredictFiles("*.out"),
72			"-memprofile":           complete.PredictFiles("*.out"),
73			"-memprofilerate":       complete.PredictAnything,
74			"-mutexprofile":         complete.PredictFiles("*.out"),
75			"-mutexprofilefraction": complete.PredictAnything,
76			"-outputdir":            complete.PredictDirs("*"),
77			"-trace":                complete.PredictFiles("*.out"),
78		},
79		Args: anyGo,
80	}
81
82	fmt := complete.Command{
83		Flags: complete.Flags{
84			"-n": complete.PredictNothing,
85			"-x": complete.PredictNothing,
86		},
87		Args: anyGo,
88	}
89
90	get := complete.Command{
91		Flags: complete.Flags{
92			"-d":        complete.PredictNothing,
93			"-f":        complete.PredictNothing,
94			"-fix":      complete.PredictNothing,
95			"-insecure": complete.PredictNothing,
96			"-t":        complete.PredictNothing,
97			"-u":        complete.PredictNothing,
98		},
99		Args: anyGo,
100	}
101
102	generate := complete.Command{
103		Flags: complete.Flags{
104			"-n":   complete.PredictNothing,
105			"-x":   complete.PredictNothing,
106			"-v":   complete.PredictNothing,
107			"-run": complete.PredictAnything,
108		},
109		Args: anyGo,
110	}
111
112	vet := complete.Command{
113		Flags: complete.Flags{
114			"-n": complete.PredictNothing,
115			"-x": complete.PredictNothing,
116		},
117		Args: anyGo,
118	}
119
120	list := complete.Command{
121		Flags: complete.Flags{
122			"-e":    complete.PredictNothing,
123			"-f":    complete.PredictAnything,
124			"-json": complete.PredictNothing,
125		},
126		Args: complete.PredictOr(anyPackage, ellipsis),
127	}
128
129	doc := complete.Command{
130		Flags: complete.Flags{
131			"-c":   complete.PredictNothing,
132			"-cmd": complete.PredictNothing,
133			"-u":   complete.PredictNothing,
134		},
135		Args: anyPackage,
136	}
137
138	tool := complete.Command{
139		Flags: complete.Flags{
140			"-n": complete.PredictNothing,
141		},
142		Sub: complete.Commands{
143			"addr2line": {
144				Args: anyFile,
145			},
146			"asm": {
147				Flags: complete.Flags{
148					"-D":        complete.PredictAnything,
149					"-I":        complete.PredictDirs("*"),
150					"-S":        complete.PredictNothing,
151					"-V":        complete.PredictNothing,
152					"-debug":    complete.PredictNothing,
153					"-dynlink":  complete.PredictNothing,
154					"-e":        complete.PredictNothing,
155					"-o":        anyFile,
156					"-shared":   complete.PredictNothing,
157					"-trimpath": complete.PredictNothing,
158				},
159				Args: complete.PredictFiles("*.s"),
160			},
161			"cgo": {
162				Flags: complete.Flags{
163					"-debug-define":      complete.PredictNothing,
164					"debug-gcc":          complete.PredictNothing,
165					"dynimport":          anyFile,
166					"dynlinker":          complete.PredictNothing,
167					"dynout":             anyFile,
168					"dynpackage":         anyPackage,
169					"exportheader":       complete.PredictDirs("*"),
170					"gccgo":              complete.PredictNothing,
171					"gccgopkgpath":       complete.PredictDirs("*"),
172					"gccgoprefix":        complete.PredictAnything,
173					"godefs":             complete.PredictNothing,
174					"import_runtime_cgo": complete.PredictNothing,
175					"import_syscall":     complete.PredictNothing,
176					"importpath":         complete.PredictDirs("*"),
177					"objdir":             complete.PredictDirs("*"),
178					"srcdir":             complete.PredictDirs("*"),
179				},
180				Args: goFiles,
181			},
182			"compile": {
183				Flags: complete.Flags{
184					"-%":              complete.PredictNothing,
185					"-+":              complete.PredictNothing,
186					"-B":              complete.PredictNothing,
187					"-D":              complete.PredictDirs("*"),
188					"-E":              complete.PredictNothing,
189					"-I":              complete.PredictDirs("*"),
190					"-K":              complete.PredictNothing,
191					"-N":              complete.PredictNothing,
192					"-S":              complete.PredictNothing,
193					"-V":              complete.PredictNothing,
194					"-W":              complete.PredictNothing,
195					"-asmhdr":         anyFile,
196					"-bench":          anyFile,
197					"-buildid":        complete.PredictNothing,
198					"-complete":       complete.PredictNothing,
199					"-cpuprofile":     anyFile,
200					"-d":              complete.PredictNothing,
201					"-dynlink":        complete.PredictNothing,
202					"-e":              complete.PredictNothing,
203					"-f":              complete.PredictNothing,
204					"-h":              complete.PredictNothing,
205					"-i":              complete.PredictNothing,
206					"-importmap":      complete.PredictAnything,
207					"-installsuffix":  complete.PredictAnything,
208					"-j":              complete.PredictNothing,
209					"-l":              complete.PredictNothing,
210					"-largemodel":     complete.PredictNothing,
211					"-linkobj":        anyFile,
212					"-live":           complete.PredictNothing,
213					"-m":              complete.PredictNothing,
214					"-memprofile":     complete.PredictNothing,
215					"-memprofilerate": complete.PredictAnything,
216					"-msan":           complete.PredictNothing,
217					"-nolocalimports": complete.PredictNothing,
218					"-o":              anyFile,
219					"-p":              complete.PredictDirs("*"),
220					"-pack":           complete.PredictNothing,
221					"-r":              complete.PredictNothing,
222					"-race":           complete.PredictNothing,
223					"-s":              complete.PredictNothing,
224					"-shared":         complete.PredictNothing,
225					"-traceprofile":   anyFile,
226					"-trimpath":       complete.PredictAnything,
227					"-u":              complete.PredictNothing,
228					"-v":              complete.PredictNothing,
229					"-w":              complete.PredictNothing,
230					"-wb":             complete.PredictNothing,
231				},
232				Args: goFiles,
233			},
234			"cover": {
235				Flags: complete.Flags{
236					"-func": complete.PredictAnything,
237					"-html": complete.PredictAnything,
238					"-mode": complete.PredictSet("set", "count", "atomic"),
239					"-o":    anyFile,
240					"-var":  complete.PredictAnything,
241				},
242				Args: anyFile,
243			},
244			"dist": {
245				Sub: complete.Commands{
246					"banner":    {Flags: complete.Flags{"-v": complete.PredictNothing}},
247					"bootstrap": {Flags: complete.Flags{"-v": complete.PredictNothing}},
248					"clean":     {Flags: complete.Flags{"-v": complete.PredictNothing}},
249					"env":       {Flags: complete.Flags{"-v": complete.PredictNothing, "-p": complete.PredictNothing}},
250					"install":   {Flags: complete.Flags{"-v": complete.PredictNothing}, Args: complete.PredictDirs("*")},
251					"list":      {Flags: complete.Flags{"-v": complete.PredictNothing, "-json": complete.PredictNothing}},
252					"test":      {Flags: complete.Flags{"-v": complete.PredictNothing, "-h": complete.PredictNothing}},
253					"version":   {Flags: complete.Flags{"-v": complete.PredictNothing}},
254				},
255			},
256			"doc": doc,
257			"fix": {
258				Flags: complete.Flags{
259					"-diff":  complete.PredictNothing,
260					"-force": complete.PredictAnything,
261					"-r":     complete.PredictSet("context", "gotypes", "netipv6zone", "printerconfig"),
262				},
263				Args: anyGo,
264			},
265			"link": {
266				Flags: complete.Flags{
267					"-B":              complete.PredictAnything,  // note
268					"-D":              complete.PredictAnything,  // address (default -1)
269					"-E":              complete.PredictAnything,  // entry symbol name
270					"-H":              complete.PredictAnything,  // header type
271					"-I":              complete.PredictAnything,  // linker binary
272					"-L":              complete.PredictDirs("*"), // directory
273					"-R":              complete.PredictAnything,  // quantum (default -1)
274					"-T":              complete.PredictAnything,  // address (default -1)
275					"-V":              complete.PredictNothing,
276					"-X":              complete.PredictAnything,
277					"-a":              complete.PredictAnything,
278					"-buildid":        complete.PredictAnything, // build id
279					"-buildmode":      complete.PredictAnything,
280					"-c":              complete.PredictNothing,
281					"-cpuprofile":     anyFile,
282					"-d":              complete.PredictNothing,
283					"-debugtramp":     complete.PredictAnything, // int
284					"-dumpdep":        complete.PredictNothing,
285					"-extar":          complete.PredictAnything,
286					"-extld":          complete.PredictAnything,
287					"-extldflags":     complete.PredictAnything, // flags
288					"-f":              complete.PredictNothing,
289					"-g":              complete.PredictNothing,
290					"-importcfg":      anyFile,
291					"-installsuffix":  complete.PredictAnything, // dir suffix
292					"-k":              complete.PredictAnything, // symbol
293					"-libgcc":         complete.PredictAnything, // maybe "none"
294					"-linkmode":       complete.PredictAnything, // mode
295					"-linkshared":     complete.PredictNothing,
296					"-memprofile":     anyFile,
297					"-memprofilerate": complete.PredictAnything, // rate
298					"-msan":           complete.PredictNothing,
299					"-n":              complete.PredictNothing,
300					"-o":              complete.PredictAnything,
301					"-pluginpath":     complete.PredictAnything,
302					"-r":              complete.PredictAnything, // "dir1:dir2:..."
303					"-race":           complete.PredictNothing,
304					"-s":              complete.PredictNothing,
305					"-tmpdir":         complete.PredictDirs("*"),
306					"-u":              complete.PredictNothing,
307					"-v":              complete.PredictNothing,
308					"-w":              complete.PredictNothing,
309					// "-h":           complete.PredictAnything, // halt on error
310				},
311				Args: complete.PredictOr(
312					complete.PredictFiles("*.a"),
313					complete.PredictFiles("*.o"),
314				),
315			},
316			"nm": {
317				Flags: complete.Flags{
318					"-n":    complete.PredictNothing,
319					"-size": complete.PredictNothing,
320					"-sort": complete.PredictAnything,
321					"-type": complete.PredictNothing,
322				},
323				Args: anyGo,
324			},
325			"objdump": {
326				Flags: complete.Flags{
327					"-s": complete.PredictAnything,
328					"-S": complete.PredictNothing,
329				},
330				Args: anyFile,
331			},
332			"pack": {
333				/* this lacks the positional aspect of all these params */
334				Flags: complete.Flags{
335					"c":  complete.PredictNothing,
336					"p":  complete.PredictNothing,
337					"r":  complete.PredictNothing,
338					"t":  complete.PredictNothing,
339					"x":  complete.PredictNothing,
340					"cv": complete.PredictNothing,
341					"pv": complete.PredictNothing,
342					"rv": complete.PredictNothing,
343					"tv": complete.PredictNothing,
344					"xv": complete.PredictNothing,
345				},
346				Args: complete.PredictOr(
347					complete.PredictFiles("*.a"),
348					complete.PredictFiles("*.o"),
349				),
350			},
351			"pprof": {
352				Flags: complete.Flags{
353					"-callgrind":     complete.PredictNothing,
354					"-disasm":        complete.PredictAnything,
355					"-dot":           complete.PredictNothing,
356					"-eog":           complete.PredictNothing,
357					"-evince":        complete.PredictNothing,
358					"-gif":           complete.PredictNothing,
359					"-gv":            complete.PredictNothing,
360					"-list":          complete.PredictAnything,
361					"-pdf":           complete.PredictNothing,
362					"-peek":          complete.PredictAnything,
363					"-png":           complete.PredictNothing,
364					"-proto":         complete.PredictNothing,
365					"-ps":            complete.PredictNothing,
366					"-raw":           complete.PredictNothing,
367					"-svg":           complete.PredictNothing,
368					"-tags":          complete.PredictNothing,
369					"-text":          complete.PredictNothing,
370					"-top":           complete.PredictNothing,
371					"-tree":          complete.PredictNothing,
372					"-web":           complete.PredictNothing,
373					"-weblist":       complete.PredictAnything,
374					"-output":        anyFile,
375					"-functions":     complete.PredictNothing,
376					"-files":         complete.PredictNothing,
377					"-lines":         complete.PredictNothing,
378					"-addresses":     complete.PredictNothing,
379					"-base":          complete.PredictAnything,
380					"-drop_negative": complete.PredictNothing,
381					"-cum":           complete.PredictNothing,
382					"-seconds":       complete.PredictAnything,
383					"-nodecount":     complete.PredictAnything,
384					"-nodefraction":  complete.PredictAnything,
385					"-edgefraction":  complete.PredictAnything,
386					"-sample_index":  complete.PredictNothing,
387					"-mean":          complete.PredictNothing,
388					"-inuse_space":   complete.PredictNothing,
389					"-inuse_objects": complete.PredictNothing,
390					"-alloc_space":   complete.PredictNothing,
391					"-alloc_objects": complete.PredictNothing,
392					"-total_delay":   complete.PredictNothing,
393					"-contentions":   complete.PredictNothing,
394					"-mean_delay":    complete.PredictNothing,
395					"-runtime":       complete.PredictNothing,
396					"-focus":         complete.PredictAnything,
397					"-ignore":        complete.PredictAnything,
398					"-tagfocus":      complete.PredictAnything,
399					"-tagignore":     complete.PredictAnything,
400					"-call_tree":     complete.PredictNothing,
401					"-unit":          complete.PredictAnything,
402					"-divide_by":     complete.PredictAnything,
403					"-buildid":       complete.PredictAnything,
404					"-tools":         complete.PredictDirs("*"),
405					"-help":          complete.PredictNothing,
406				},
407				Args: anyFile,
408			},
409			"tour": {
410				Flags: complete.Flags{
411					"-http":        complete.PredictAnything,
412					"-openbrowser": complete.PredictNothing,
413				},
414			},
415			"trace": {
416				Flags: complete.Flags{
417					"-http":  complete.PredictAnything,
418					"-pprof": complete.PredictSet("net", "sync", "syscall", "sched"),
419				},
420				Args: anyFile,
421			},
422			"vet": {
423				Flags: complete.Flags{
424					"-all":                 complete.PredictNothing,
425					"-asmdecl":             complete.PredictNothing,
426					"-assign":              complete.PredictNothing,
427					"-atomic":              complete.PredictNothing,
428					"-bool":                complete.PredictNothing,
429					"-buildtags":           complete.PredictNothing,
430					"-cgocall":             complete.PredictNothing,
431					"-composites":          complete.PredictNothing,
432					"-compositewhitelist":  complete.PredictNothing,
433					"-copylocks":           complete.PredictNothing,
434					"-httpresponse":        complete.PredictNothing,
435					"-lostcancel":          complete.PredictNothing,
436					"-methods":             complete.PredictNothing,
437					"-nilfunc":             complete.PredictNothing,
438					"-printf":              complete.PredictNothing,
439					"-printfuncs":          complete.PredictAnything,
440					"-rangeloops":          complete.PredictNothing,
441					"-shadow":              complete.PredictNothing,
442					"-shadowstrict":        complete.PredictNothing,
443					"-shift":               complete.PredictNothing,
444					"-structtags":          complete.PredictNothing,
445					"-tags":                complete.PredictAnything,
446					"-tests":               complete.PredictNothing,
447					"-unreachable":         complete.PredictNothing,
448					"-unsafeptr":           complete.PredictNothing,
449					"-unusedfuncs":         complete.PredictAnything,
450					"-unusedresult":        complete.PredictNothing,
451					"-unusedstringmethods": complete.PredictAnything,
452					"-v":                   complete.PredictNothing,
453				},
454				Args: anyGo,
455			},
456		},
457	}
458
459	clean := complete.Command{
460		Flags: complete.Flags{
461			"-i":         complete.PredictNothing,
462			"-r":         complete.PredictNothing,
463			"-n":         complete.PredictNothing,
464			"-x":         complete.PredictNothing,
465			"-cache":     complete.PredictNothing,
466			"-testcache": complete.PredictNothing,
467			"-modcache":  complete.PredictNothing,
468		},
469		Args: complete.PredictOr(anyPackage, ellipsis),
470	}
471
472	env := complete.Command{
473		Args: complete.PredictAnything,
474	}
475
476	bug := complete.Command{}
477	version := complete.Command{}
478
479	fix := complete.Command{
480		Args: anyGo,
481	}
482
483	modDownload := complete.Command{
484		Flags: complete.Flags{
485			"-json": complete.PredictNothing,
486		},
487		Args: anyPackage,
488	}
489
490	modEdit := complete.Command{
491		Flags: complete.Flags{
492			"-fmt":    complete.PredictNothing,
493			"-module": complete.PredictNothing,
494			"-print":  complete.PredictNothing,
495
496			"-exclude":     anyPackage,
497			"-dropexclude": anyPackage,
498			"-replace":     anyPackage,
499			"-dropreplace": anyPackage,
500			"-require":     anyPackage,
501			"-droprequire": anyPackage,
502		},
503		Args: complete.PredictFiles("go.mod"),
504	}
505
506	modGraph := complete.Command{}
507
508	modInit := complete.Command{
509		Args: complete.PredictAnything,
510	}
511
512	modTidy := complete.Command{
513		Flags: complete.Flags{
514			"-v": complete.PredictNothing,
515		},
516	}
517
518	modVendor := complete.Command{
519		Flags: complete.Flags{
520			"-v": complete.PredictNothing,
521		},
522	}
523
524	modVerify := complete.Command{}
525
526	modWhy := complete.Command{
527		Flags: complete.Flags{
528			"-m":      complete.PredictNothing,
529			"-vendor": complete.PredictNothing,
530		},
531		Args: anyPackage,
532	}
533
534	modHelp := complete.Command{
535		Sub: complete.Commands{
536			"download": complete.Command{},
537			"edit":     complete.Command{},
538			"graph":    complete.Command{},
539			"init":     complete.Command{},
540			"tidy":     complete.Command{},
541			"vendor":   complete.Command{},
542			"verify":   complete.Command{},
543			"why":      complete.Command{},
544		},
545	}
546
547	mod := complete.Command{
548		Sub: complete.Commands{
549			"download": modDownload,
550			"edit":     modEdit,
551			"graph":    modGraph,
552			"init":     modInit,
553			"tidy":     modTidy,
554			"vendor":   modVendor,
555			"verify":   modVerify,
556			"why":      modWhy,
557			"help":     modHelp,
558		},
559	}
560
561	help := complete.Command{
562		Sub: complete.Commands{
563			"bug":         complete.Command{},
564			"build":       complete.Command{},
565			"clean":       complete.Command{},
566			"doc":         complete.Command{},
567			"env":         complete.Command{},
568			"fix":         complete.Command{},
569			"fmt":         complete.Command{},
570			"generate":    complete.Command{},
571			"get":         complete.Command{},
572			"install":     complete.Command{},
573			"list":        complete.Command{},
574			"mod":         modHelp,
575			"run":         complete.Command{},
576			"test":        complete.Command{},
577			"tool":        complete.Command{},
578			"version":     complete.Command{},
579			"vet":         complete.Command{},
580			"buildmode":   complete.Command{},
581			"c":           complete.Command{},
582			"cache":       complete.Command{},
583			"environment": complete.Command{},
584			"filetype":    complete.Command{},
585			"go.mod":      complete.Command{},
586			"gopath":      complete.Command{},
587			"gopath-get":  complete.Command{},
588			"goproxy":     complete.Command{},
589			"importpath":  complete.Command{},
590			"modules":     complete.Command{},
591			"module-get":  complete.Command{},
592			"packages":    complete.Command{},
593			"testflag":    complete.Command{},
594			"testfunc":    complete.Command{},
595		},
596	}
597
598	// commands that also accepts the build flags
599	for name, options := range build.Flags {
600		test.Flags[name] = options
601		run.Flags[name] = options
602		list.Flags[name] = options
603		vet.Flags[name] = options
604		get.Flags[name] = options
605	}
606
607	gogo := complete.Command{
608		Sub: complete.Commands{
609			"build":    build,
610			"install":  build, // install and build have the same flags
611			"run":      run,
612			"test":     test,
613			"fmt":      fmt,
614			"get":      get,
615			"generate": generate,
616			"vet":      vet,
617			"list":     list,
618			"doc":      doc,
619			"tool":     tool,
620			"clean":    clean,
621			"env":      env,
622			"bug":      bug,
623			"fix":      fix,
624			"version":  version,
625			"mod":      mod,
626			"help":     help,
627		},
628		GlobalFlags: complete.Flags{
629			"-h": complete.PredictNothing,
630		},
631	}
632
633	complete.New("go", gogo).Run()
634}
635