From e2b4c3882762406fd3da16f5865cfc3e36e048b5 Mon Sep 17 00:00:00 2001 From: Niall Sheridan Date: Wed, 1 Aug 2018 00:37:11 +0100 Subject: Migrate from esc to packr for static files --- .../github.com/gobuffalo/packr/builder/visitor.go | 248 +++++++++++++++++++++ 1 file changed, 248 insertions(+) create mode 100644 vendor/github.com/gobuffalo/packr/builder/visitor.go (limited to 'vendor/github.com/gobuffalo/packr/builder/visitor.go') diff --git a/vendor/github.com/gobuffalo/packr/builder/visitor.go b/vendor/github.com/gobuffalo/packr/builder/visitor.go new file mode 100644 index 0000000..ea24bde --- /dev/null +++ b/vendor/github.com/gobuffalo/packr/builder/visitor.go @@ -0,0 +1,248 @@ +package builder + +import ( + "go/ast" + "go/parser" + "go/token" + "io/ioutil" + "sort" + "strings" + + "github.com/pkg/errors" +) + +type visitor struct { + Path string + Package string + Boxes []string + Errors []error +} + +func newVisitor(path string) *visitor { + return &visitor{ + Path: path, + Boxes: []string{}, + Errors: []error{}, + } +} + +func (v *visitor) Run() error { + b, err := ioutil.ReadFile(v.Path) + if err != nil { + return errors.WithStack(err) + } + + fset := token.NewFileSet() + file, err := parser.ParseFile(fset, v.Path, string(b), parser.ParseComments) + if err != nil { + return errors.WithStack(err) + } + + v.Package = file.Name.Name + ast.Walk(v, file) + + m := map[string]string{} + for _, s := range v.Boxes { + m[s] = s + } + v.Boxes = []string{} + for k := range m { + v.Boxes = append(v.Boxes, k) + } + + sort.Strings(v.Boxes) + + if len(v.Errors) > 0 { + s := make([]string, len(v.Errors)) + for i, e := range v.Errors { + s[i] = e.Error() + } + return errors.New(strings.Join(s, "\n")) + } + return nil +} + +func (v *visitor) Visit(node ast.Node) ast.Visitor { + if node == nil { + return v + } + if err := v.eval(node); err != nil { + v.Errors = append(v.Errors, err) + } + return v +} + +func (v *visitor) eval(node ast.Node) error { + switch t := node.(type) { + case *ast.CallExpr: + return v.evalExpr(t) + case *ast.Ident: + return v.evalIdent(t) + case *ast.GenDecl: + for _, n := range t.Specs { + if err := v.eval(n); err != nil { + return errors.WithStack(err) + } + } + case *ast.FuncDecl: + if t.Body == nil { + return nil + } + for _, b := range t.Body.List { + if err := v.evalStmt(b); err != nil { + return errors.WithStack(err) + } + } + return nil + case *ast.ValueSpec: + for _, e := range t.Values { + if err := v.evalExpr(e); err != nil { + return errors.WithStack(err) + } + } + } + return nil +} + +func (v *visitor) evalStmt(stmt ast.Stmt) error { + switch t := stmt.(type) { + case *ast.ExprStmt: + return v.evalExpr(t.X) + case *ast.AssignStmt: + for _, e := range t.Rhs { + if err := v.evalArgs(e); err != nil { + return errors.WithStack(err) + } + } + } + return nil +} + +func (v *visitor) evalExpr(expr ast.Expr) error { + switch t := expr.(type) { + case *ast.CallExpr: + if t.Fun == nil { + return nil + } + for _, a := range t.Args { + switch at := a.(type) { + case *ast.CallExpr: + if sel, ok := t.Fun.(*ast.SelectorExpr); ok { + return v.evalSelector(at, sel) + } + + if err := v.evalArgs(at); err != nil { + return errors.WithStack(err) + } + case *ast.CompositeLit: + for _, e := range at.Elts { + if err := v.evalExpr(e); err != nil { + return errors.WithStack(err) + } + } + } + } + if ft, ok := t.Fun.(*ast.SelectorExpr); ok { + return v.evalSelector(t, ft) + } + case *ast.KeyValueExpr: + return v.evalExpr(t.Value) + } + return nil +} + +func (v *visitor) evalArgs(expr ast.Expr) error { + switch at := expr.(type) { + case *ast.CompositeLit: + for _, e := range at.Elts { + if err := v.evalExpr(e); err != nil { + return errors.WithStack(err) + } + } + // case *ast.BasicLit: + // fmt.Println("evalArgs", at.Value) + // v.addBox(at.Value) + case *ast.CallExpr: + if at.Fun == nil { + return nil + } + switch st := at.Fun.(type) { + case *ast.SelectorExpr: + if err := v.evalSelector(at, st); err != nil { + return errors.WithStack(err) + } + case *ast.Ident: + return v.evalIdent(st) + } + for _, a := range at.Args { + if err := v.evalArgs(a); err != nil { + return errors.WithStack(err) + } + } + } + return nil +} + +func (v *visitor) evalSelector(expr *ast.CallExpr, sel *ast.SelectorExpr) error { + x, ok := sel.X.(*ast.Ident) + if !ok { + return nil + } + if x.Name == "packr" && sel.Sel.Name == "NewBox" { + for _, e := range expr.Args { + switch at := e.(type) { + case *ast.Ident: + switch at.Obj.Kind { + case ast.Var: + if as, ok := at.Obj.Decl.(*ast.AssignStmt); ok { + v.addVariable(as) + } + case ast.Con: + if vs, ok := at.Obj.Decl.(*ast.ValueSpec); ok { + v.addConstant(vs) + } + } + return v.evalIdent(at) + case *ast.BasicLit: + v.addBox(at.Value) + case *ast.CallExpr: + return v.evalExpr(at) + } + } + } + + return nil +} + +func (v *visitor) evalIdent(i *ast.Ident) error { + if i.Obj == nil { + return nil + } + if s, ok := i.Obj.Decl.(*ast.AssignStmt); ok { + return v.evalStmt(s) + } + return nil +} + +func (v *visitor) addBox(b string) { + b = strings.Replace(b, "\"", "", -1) + v.Boxes = append(v.Boxes, b) +} + +func (v *visitor) addVariable(as *ast.AssignStmt) error { + if len(as.Rhs) == 1 { + if bs, ok := as.Rhs[0].(*ast.BasicLit); ok { + v.addBox(bs.Value) + } + } + return nil +} + +func (v *visitor) addConstant(vs *ast.ValueSpec) error { + if len(vs.Values) == 1 { + if bs, ok := vs.Values[0].(*ast.BasicLit); ok { + v.addBox(bs.Value) + } + } + return nil +} -- cgit v1.2.3