Skip to content

Commit

Permalink
Merge pull request #321 from aquaproj/feat/append-pkg-file
Browse files Browse the repository at this point in the history
feat(scaffold): append `- import: pkgs/<pkg>/pkg.yaml` to aqua-local.yaml
  • Loading branch information
suzuki-shunsuke authored Mar 8, 2023
2 parents e36fae4 + d668cf2 commit 15b76d7
Show file tree
Hide file tree
Showing 3 changed files with 115 additions and 14 deletions.
19 changes: 5 additions & 14 deletions pkg/scaffold/api.go
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ e.g. $ aqua-registry scaffold cli/cli`)
if err := initcmd.Init(ctx); err != nil {
return err //nolint:wrapcheck
}
if err := aquaG(ctx, pkgName); err != nil {
if err := aquaG(pkgFile); err != nil {
return err
}
if !deep {
Expand Down Expand Up @@ -77,19 +77,10 @@ func aquaGR(ctx context.Context, pkgName, pkgFilePath, rgFilePath string, deep b
return nil
}

func aquaG(ctx context.Context, pkgName string) error {
outFile, err := os.OpenFile("aqua-local.yaml", os.O_APPEND|os.O_CREATE|os.O_WRONLY, filePermission)
if err != nil {
return fmt.Errorf("open aqua-local.yaml: %w", err)
}
defer outFile.Close()
fmt.Fprintf(os.Stderr, "+ aqua g %s >> aqua-local.yaml\n", pkgName)
cmd := exec.CommandContext(ctx, "aqua", "g", pkgName)
cmd.Stdin = os.Stdin
cmd.Stdout = outFile
cmd.Stderr = os.Stderr
if err := cmd.Run(); err != nil {
return fmt.Errorf("execute a command: %w", err)
func aquaG(pkgFilePath string) error {
fmt.Fprintf(os.Stderr, "appending '- import: %s' to aqua-local.yaml\n", pkgFilePath)
if err := generateInsert("aqua-local.yaml", pkgFilePath); err != nil {
return err
}
return nil
}
Expand Down
9 changes: 9 additions & 0 deletions pkg/scaffold/error.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package scaffold

import "errors"

var (
errDocumentMustBeOne = errors.New("the number of document in aqua.yaml must be one")
errBodyFormat = errors.New("fails to parse a configuration file. Format is wrong. body must be *ast.MappingNode or *ast.MappingValueNode")
errPkgsNotFound = errors.New("the field 'packages' isn't found")
)
101 changes: 101 additions & 0 deletions pkg/scaffold/insert.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,101 @@
package scaffold

import (
"errors"
"fmt"
"os"

"github.com/goccy/go-yaml"
"github.com/goccy/go-yaml/ast"
"github.com/goccy/go-yaml/parser"
"github.com/sirupsen/logrus"
"github.com/suzuki-shunsuke/logrus-error/logerr"
)

func generateInsert(cfgFilePath, pkgFilePath string) error {
b, err := os.ReadFile(cfgFilePath)
if err != nil {
return fmt.Errorf("read a configuration file: %w", err)
}
file, err := parser.ParseBytes(b, parser.ParseComments)
if err != nil {
return fmt.Errorf("parse configuration file as YAML: %w", err)
}

if len(file.Docs) != 1 {
return logerr.WithFields(errDocumentMustBeOne, logrus.Fields{ //nolint:wrapcheck
"num_of_docs": len(file.Docs),
})
}

if err := updateASTFile(file.Docs[0].Body, []map[string]string{
{
"import": pkgFilePath,
},
}); err != nil {
return err
}

stat, err := os.Stat(cfgFilePath)
if err != nil {
return fmt.Errorf("get configuration file stat: %w", err)
}
if err := os.WriteFile(cfgFilePath, []byte(file.String()), stat.Mode()); err != nil {
return fmt.Errorf("write the configuration file: %w", err)
}
return nil
}

func getPkgsAST(values []*ast.MappingValueNode) *ast.MappingValueNode {
for _, mapValue := range values {
if mapValue.Key.String() != "packages" {
continue
}
return mapValue
}
return nil
}

func getMappingValueNodeFromBody(body ast.Node) []*ast.MappingValueNode {
switch b := body.(type) {
case *ast.MappingNode:
return b.Values
case *ast.MappingValueNode:
return []*ast.MappingValueNode{b}
}
return nil
}

func appendPkgsNode(mapValue *ast.MappingValueNode, node ast.Node) error {
switch mapValue.Value.Type() {
case ast.NullType:
mapValue.Value = node
return nil
case ast.SequenceType:
if err := ast.Merge(mapValue.Value, node); err != nil {
return fmt.Errorf("merge packages: %w", err)
}
return nil
default:
return errors.New("packages must be null or array")
}
}

func updateASTFile(body ast.Node, pkgs []map[string]string) error {
node, err := yaml.ValueToNode(pkgs)
if err != nil {
return fmt.Errorf("convert packages to node: %w", err)
}

values := getMappingValueNodeFromBody(body)
if values == nil {
return errBodyFormat
}

mapValue := getPkgsAST(values)
if mapValue == nil {
return errPkgsNotFound
}

return appendPkgsNode(mapValue, node)
}

0 comments on commit 15b76d7

Please sign in to comment.