diff options
| author | Fuwn <[email protected]> | 2024-10-10 21:05:15 -0700 |
|---|---|---|
| committer | Fuwn <[email protected]> | 2024-10-10 21:08:35 -0700 |
| commit | 89a073b2e7590c2816c313567cf0ad4781e0ae0d (patch) | |
| tree | 5dcf79c7e50d1c52cb5d185e00b64679076529f5 /yae.go | |
| parent | d2deec027a60b42cc8451e250e8939f8f472c270 (diff) | |
| download | yae-89a073b2e7590c2816c313567cf0ad4781e0ae0d.tar.xz yae-89a073b2e7590c2816c313567cf0ad4781e0ae0d.zip | |
refactor!: wiene -> yae
It's far too easy to type wine.
Diffstat (limited to 'yae.go')
| -rw-r--r-- | yae.go | 190 |
1 files changed, 190 insertions, 0 deletions
@@ -0,0 +1,190 @@ +package main + +import ( + "fmt" + "os" + "os/exec" + "strings" + "time" + + "github.com/urfave/cli/v2" +) + +func main() { + sources := Sources{} + + (&cli.App{ + Name: "yae", + Usage: "Nix Dependency Manager", + Description: "Nix Dependency Manager", + EnableBashCompletion: true, + Authors: []*cli.Author{ + { + Name: "Fuwn", + Email: "[email protected]", + }, + }, + Before: func(c *cli.Context) error { + return sources.Load(c.String("sources")) + }, + Flags: []cli.Flag{ + &cli.StringFlag{ + Name: "sources", + Value: "./yae.json", + Usage: "Sources path", + }, + }, + Copyright: fmt.Sprintf("Copyright (c) 2024-%s Fuwn", fmt.Sprint(time.Now().Year())), + ExitErrHandler: func(c *cli.Context, err error) { + if err != nil { + fmt.Println(err) + } + }, + Suggest: true, + Commands: []*cli.Command{ + { + Name: "add", + Args: true, + ArgsUsage: "<name> <uri>", + Usage: "Add a source", + Flags: []cli.Flag{ + &cli.BoolFlag{ + Name: "unpack", + Usage: "Unpack the source into the Nix Store", + }, + }, + Action: func(c *cli.Context) error { + if c.Args().Len() != 2 { + return fmt.Errorf("invalid number of arguments") + } + + if sources.Exists(c.Args().Get(0)) { + return fmt.Errorf("source already exists") + } + + sha256, err := fetchSHA256(c.Args().Get(1), c.Bool("unpack")) + + if err != nil { + return err + } + + if err = sources.Add(c.Args().Get(0), Source{ + URI: c.Args().Get(1), + SHA256: sha256, + Unpack: c.Bool("unpack"), + }); err != nil { + return err + } + + return sources.Save(c.String("sources")) + }, + }, + { + Name: "drop", + Args: true, + Usage: "Drop a source", + Action: func(c *cli.Context) error { + if c.Args().Len() == 0 { + return fmt.Errorf("invalid number of arguments") + } + + if !sources.Exists(c.Args().Get(0)) { + return fmt.Errorf("source does not exist") + } + + sources.Drop(c.Args().Get(0)) + + return sources.Save(c.String("sources")) + }, + }, + { + Name: "update", + Args: true, + Usage: "Update one or all sources", + ArgsUsage: "[name]", + Flags: []cli.Flag{ + &cli.BoolFlag{ + Name: "unpack", + Usage: "Unpack the source into the Nix Store", + }, + }, + Action: func(c *cli.Context) error { + if c.Args().Len() == 0 { + for key, value := range sources { + sha256, err := fetchSHA256(value.URI, value.Unpack) + + if err != nil { + return err + } + + if sha256 != value.SHA256 { + sources[key] = Source{ + URI: value.URI, + SHA256: sha256, + Unpack: value.Unpack, + } + + fmt.Println("updated hash for", key) + } + + if err = sources.Save(c.String("sources")); err != nil { + return err + } + } + } else { + if !sources.Exists(c.Args().Get(0)) { + return fmt.Errorf("source does not exist") + } + + sha256, err := fetchSHA256(sources[c.Args().Get(0)].URI, c.Bool("unpack")) + + if err != nil { + return err + } + + sources[c.Args().Get(0)] = Source{ + URI: sources[c.Args().Get(0)].URI, + SHA256: sha256, + Unpack: c.Bool("unpack"), + } + + if err = sources.Save(c.String("sources")); err != nil { + return err + } + } + + return nil + }, + }, + }, + }).Run(os.Args) +} + +func fetchSHA256(uri string, unpack bool) (string, error) { + arguments := []string{"--type", "sha256", uri} + + if unpack { + arguments = append([]string{"--unpack"}, arguments...) + } + + output, err := commandOutput("nix-prefetch-url", arguments...) + + if err != nil { + return "", err + } + + lines := strings.Split(output, "\n") + + return strings.Trim(lines[len(lines)-2], "\n"), nil +} + +func commandOutput(name string, args ...string) (string, error) { + executable, err := exec.LookPath(name) + + cmd := exec.Command(executable, args...) + cmd.Stdin = os.Stdin + cmd.Stderr = os.Stderr + out, err := cmd.Output() + + return string(out), err +} |