package main import ( "bytes" "encoding/json" "flag" "fmt" "os" "os/exec" "path/filepath" "sort" "strings" "amadan.net/oficina/estilo.git/credits" "amadan.net/oficina/estilo.git/credits/catalog" ) func main() { entry := flag.String("package", "", "production Go package") excludes := flag.String("exclude", "", "comma-separated first-party module paths") lucide := flag.Bool("lucide", false, "include vendored Lucide and Feather notices") onest := flag.Bool("onest", false, "include the Onest font notice (apps that mount theme.FontHandler)") flag.Parse() if *entry == "" || flag.NArg() != 0 { fmt.Fprintln(os.Stderr, "oficina-notices: -package is required") os.Exit(2) } command := exec.Command("go", "list", "-deps", "-json", *entry) command.Stderr = os.Stderr raw, err := command.Output() if err != nil { fmt.Fprintln(os.Stderr, "oficina-notices: go list failed") os.Exit(1) } excluded := map[string]bool{} for _, name := range strings.Split(*excludes, ",") { if name = strings.TrimSpace(name); name != "" { excluded[name] = true } } inventory, err := catalog.Collect(bytes.NewReader(raw), excluded) if err != nil { fmt.Fprintln(os.Stderr, err) os.Exit(1) } env, err := exec.Command("go", "env", "-json", "GOROOT", "GOVERSION").Output() if err != nil { fmt.Fprintln(os.Stderr, "oficina-notices: Go provenance unavailable") os.Exit(1) } var toolchain struct{ GOROOT, GOVERSION string } if json.Unmarshal(env, &toolchain) != nil || toolchain.GOROOT == "" || toolchain.GOVERSION == "" { fmt.Fprintln(os.Stderr, "oficina-notices: invalid Go provenance") os.Exit(1) } license, err := os.ReadFile(filepath.Join(toolchain.GOROOT, "LICENSE")) if err != nil { fmt.Fprintln(os.Stderr, "oficina-notices: Go license unavailable") os.Exit(1) } inventory.Components = append(inventory.Components, credits.Component{Name: "Go", Version: toolchain.GOVERSION, SourceURL: "https://go.dev/LICENSE", Notices: []credits.Notice{{Name: "LICENSE", Text: string(license)}}}) if *lucide { inventory.Components = append(inventory.Components, credits.Lucide()) } if *onest { inventory.Components = append(inventory.Components, credits.Onest()) } sort.Slice(inventory.Components, func(i, j int) bool { return inventory.Components[i].Name < inventory.Components[j].Name }) encoder := json.NewEncoder(os.Stdout) encoder.SetIndent("", " ") if err := encoder.Encode(inventory); err != nil { os.Exit(1) } }