70 lines
2.5 KiB
Go
70 lines
2.5 KiB
Go
// Package packagename reads a package artifact's name in its own ecosystem (design 32, a package named by its name in its
|
|
// own language): a Go package by the module line of its go.mod, a TypeScript package by the name in its package.json, read
|
|
// at a commit of the repository that builds it. The indexer reads it so at each trunk merge (its packages state's series
|
|
// keys), and the checker so at a delivery group member's head for a package new in the group, so the judge is handed one
|
|
// name for each package whoever reads it (mesh-sdk composer.Request.Packages).
|
|
package packagename
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"fmt"
|
|
"path"
|
|
"strings"
|
|
|
|
"git.novox.be/novox/mesh-delivery/contracts/go/clients/meshcatalogclient"
|
|
"git.novox.be/novox/mesh-sdk/go/catalogue"
|
|
)
|
|
|
|
// ReadFile reads one file of a repository at a commit; a file the commit does not hold is nil with no error.
|
|
type ReadFile func(ctx context.Context, repository, commit, file string) ([]byte, error)
|
|
|
|
// Of is a package artifact's name in its ecosystem, read at commit from the first of its paths (or the module's directory
|
|
// dir, meshcatalogclient.RootPath or empty for the repository's root) that holds its go.mod (Go) or package.json (TypeScript). A
|
|
// file read that fails, a go.mod that names no module and a package.json that names no name are errors, said.
|
|
func Of(ctx context.Context, read ReadFile, repository, commit, dir string, a catalogue.Artifact) (string, error) {
|
|
file := "package.json"
|
|
if a.Language == "go" {
|
|
file = "go.mod"
|
|
}
|
|
base := dir
|
|
if base == meshcatalogclient.RootPath {
|
|
base = ""
|
|
}
|
|
roots := a.Paths
|
|
if len(roots) == 0 {
|
|
roots = []string{"."}
|
|
}
|
|
for _, r := range roots {
|
|
p := path.Join(base, r, file)
|
|
if strings.HasSuffix(r, file) {
|
|
p = path.Join(base, r)
|
|
}
|
|
raw, err := read(ctx, repository, commit, p)
|
|
if err != nil {
|
|
return "", fmt.Errorf("%s: %w", p, err)
|
|
}
|
|
if raw == nil {
|
|
continue
|
|
}
|
|
if a.Language == "go" {
|
|
for _, line := range strings.Split(string(raw), "\n") {
|
|
if rest, ok := strings.CutPrefix(strings.TrimSpace(line), "module "); ok {
|
|
if name := strings.Trim(strings.TrimSpace(rest), `"`); name != "" {
|
|
return name, nil
|
|
}
|
|
}
|
|
}
|
|
return "", fmt.Errorf("%s names no module", p)
|
|
}
|
|
var pj struct {
|
|
Name string `json:"name"`
|
|
}
|
|
if err := json.Unmarshal(raw, &pj); err != nil || pj.Name == "" {
|
|
return "", fmt.Errorf("%s names no name (%v)", p, err)
|
|
}
|
|
return pj.Name, nil
|
|
}
|
|
return "", fmt.Errorf("no %s under %v", file, roots)
|
|
}
|