diff options
| -rw-r--r-- | actions.go | 108 | ||||
| -rw-r--r-- | main.go | 144 |
2 files changed, 130 insertions, 122 deletions
diff --git a/actions.go b/actions.go new file mode 100644 index 0000000..81d0e63 --- /dev/null +++ b/actions.go @@ -0,0 +1,108 @@ +package main + +import ( + "fmt" + "slices" + "sort" + "sync" + + "github.com/fatih/color" +) + +func fetchAndDisplay(pkgName string) *statistics { + fmt.Print("\033[s") + showLoadingPrompt(fmt.Sprintf("What the heck is \"%s\"", pkgName)) + + stat := initStat(pkgName) + + fmlChan := make(chan *FormulaInfo) + caskChan := make(chan *CaskInfo) + rvsChan := make(chan []string) + fetchData(pkgName, fmlChan, caskChan, rvsChan) + + var wg sync.WaitGroup + wg.Add(1) + go func() { + defer wg.Done() + var fml *FormulaInfo + var cask *CaskInfo + var rvs []string + remaining := 3 + for remaining > 0 { + select { + case v := <-fmlChan: + fml = v + remaining-- + case v := <-caskChan: + cask = v + remaining-- + case v := <-rvsChan: + rvs = v + remaining-- + } + fmt.Print("\033[u\033[J") + stat = NewStatistics(fml, cask, pkgName, rvs) + stat.Print() + } + }() + wg.Wait() + + return stat +} + +func initStat(pkgName string) *statistics { + if NoCache { + return &statistics{PkgName: pkgName} + } + stat := NewStatisticsFromCache(pkgName) + if stat == nil { + return &statistics{PkgName: pkgName} + } + return stat +} + +func runList() error { + depmap := GetBrewDeps() + list := GetBrewList() + + keys := []string{} + for k := range depmap { + if !slices.Contains(list, k) { + delete(depmap, k) + } else { + keys = append(keys, k) + } + } + + if ListAscend { + sort.Slice(keys, func(i, j int) bool { + return len(depmap[keys[i]]) > len(depmap[keys[j]]) + }) + } else if ListDescend { + sort.Slice(keys, func(i, j int) bool { + return len(depmap[keys[i]]) < len(depmap[keys[j]]) + }) + } else { + sort.Strings(keys) + } + + for _, pkg := range keys { + deps := depmap[pkg] + count := len(deps) + + color.New(color.FgBlue).Printf("%s", pkg) + if count > 1 { + fmt.Printf(" (%d dependencies)\n", count) + } else { + fmt.Printf(" (%d dependency)\n", count) + } + + if ListNoDep { + continue + } + for _, dep := range deps { + fmt.Printf(" ► %s\n", dep) + } + } + return nil +} @@ -5,22 +5,17 @@ import ( "fmt" "log" "os" - "slices" - "sort" - "sync" "github.com/fatih/color" "github.com/urfave/cli/v3" ) -// flags var NoCache, DoClearCache bool var ListAscend, ListDescend, ListNoDep bool func main() { EnsureBrewAvailable() - // declare CLI app cmd := &cli.Command{ Name: "wthis", Usage: "Fetch information of a Homebrew formulae or cask, like how it got installed, reverse dependencies, etc.", @@ -39,69 +34,23 @@ func main() { fmt.Println("Cache cleared.") os.Exit(0) } - - // handle arguments if cmd.Args().Len() == 0 { printErrorAndExit("Please provide a formulae/cask name.") } - pkgName := cmd.Args().First() - - fmt.Print("\033[s") - showLoadingPrompt(fmt.Sprintf("What the heck is \"%s\"", pkgName)) - // try reading from cache - var stat *statistics - if NoCache { - stat = &statistics{PkgName: pkgName} - } else { - stat = NewStatisticsFromCache(pkgName) - if stat == nil { - stat = &statistics{PkgName: pkgName} - } - } - fmlChan := make(chan *FormulaInfo) - caskChan := make(chan *CaskInfo) - rvsChan := make(chan []string) - fetchData(pkgName, fmlChan, caskChan, rvsChan) - var wg sync.WaitGroup - wg.Add(1) - go func(){ - defer wg.Done() - var fml *FormulaInfo - var cask *CaskInfo - var rvs []string - remaining := 3 - for remaining > 0 { - select { - case v := <-fmlChan: - fml = v - remaining-- - case v := <-caskChan: - cask = v - remaining-- - case v := <-rvsChan: - rvs = v - remaining-- - } - fmt.Print("\033[u\033[J") - stat = NewStatistics(fml, cask, pkgName, rvs) - stat.Print() - } - }() - wg.Wait() + pkgName := cmd.Args().First() + stat := fetchAndDisplay(pkgName) - // cache if !NoCache { stat.Cache() } - return nil }, Commands: []*cli.Command{ { - Name: "list", + Name: "list", Aliases: []string{"l", "ls"}, - Usage: "Better brew list.", + Usage: "Better brew list.", Flags: []cli.Flag{ &cli.BoolFlag{ Name: "ascending", @@ -125,80 +74,32 @@ func main() { Destination: &ListNoDep, }, }, - Action: func(ctx context.Context, cmd *cli.Command) error { - depmap := GetBrewDeps() - list := GetBrewList() - - // filter and get essential items - var keys = []string{} - for k := range depmap { - if !slices.Contains(list, k) { - delete(depmap, k) - } else { - keys = append(keys, k) - } - } - - // sort based on dependency count - if ListAscend { - sort.Slice(keys, func(i, j int) bool { - return len(depmap[keys[i]]) > len(depmap[keys[j]]) - }) - } else if ListDescend { - sort.Slice(keys, func(i, j int) bool { - return len(depmap[keys[i]]) < len(depmap[keys[j]]) - }) - } else { - sort.Strings(keys) - } - - // - for _, pkg := range keys { - deps := depmap[pkg] - count := len(deps) - - color.New(color.FgBlue).Printf("%s", pkg) - if count > 1 { - fmt.Printf(" (%d dependencies)\n", count) - } else { - fmt.Printf(" (%d dependency)\n", count) - } - - if ListNoDep { continue } - for _, dep := range deps { - fmt.Printf(" ► %s\n", dep) - } - } - return nil - }, - }, - { - Name: "clean", - Aliases: []string{"c", "cache"}, - Usage: "Delete all cache files.", - Action: func(ctx context.Context, cmd *cli.Command) error { - // TODO error handling here - ClearCache() + Action: func(ctx context.Context, cmd *cli.Command) error { + return runList() + }, + }, + { + Name: "clean", + Aliases: []string{"c", "cache"}, + Usage: "Delete all cache files.", + Action: func(ctx context.Context, cmd *cli.Command) error { + ClearCache() fmt.Println("Cache cleared.") return nil - }, - }, + }, + }, }, } - // run command and handle error if err := cmd.Run(context.Background(), os.Args); err != nil { log.Fatal(err) } } -func fetchData(pkgName string, - fmlChan chan *FormulaInfo, - caskChan chan *CaskInfo, - rvsChan chan []string) { - // fetching formula/cask info and uses - // async from brew CLI and HTTP API - // use whoever comes first +func fetchData(pkgName string, + fmlChan chan *FormulaInfo, + caskChan chan *CaskInfo, + rvsChan chan []string) { go func() { formula, cask := GetBrewInfo(pkgName) fmlChan <- formula @@ -207,11 +108,10 @@ func fetchData(pkgName string, go func() { fmlChan <- GetFormulaFromAPI(pkgName) }() - go func() { + go func() { caskChan <- GetCaskFromAPI(pkgName) }() - - // fetching brew uses + go func() { rvsChan <- GetBrewUses(pkgName) }() |
