github.com/gopherjs/gopherjs@v1.19.0-beta1.0.20240506212314-27071a8796e4/compiler/compiler_test.go (about) 1 package compiler 2 3 import ( 4 "bytes" 5 "go/ast" 6 "go/build" 7 "go/parser" 8 "go/token" 9 "go/types" 10 "testing" 11 12 "github.com/google/go-cmp/cmp" 13 "golang.org/x/tools/go/loader" 14 ) 15 16 func TestOrder(t *testing.T) { 17 fileA := ` 18 package foo 19 20 var Avar = "a" 21 22 type Atype struct{} 23 24 func Afunc() int { 25 var varA = 1 26 var varB = 2 27 return varA+varB 28 } 29 ` 30 31 fileB := ` 32 package foo 33 34 var Bvar = "b" 35 36 type Btype struct{} 37 38 func Bfunc() int { 39 var varA = 1 40 var varB = 2 41 return varA+varB 42 } 43 ` 44 files := []source{{"fileA.go", []byte(fileA)}, {"fileB.go", []byte(fileB)}} 45 46 compare(t, "foo", files, false) 47 compare(t, "foo", files, true) 48 } 49 50 func compare(t *testing.T, path string, sourceFiles []source, minify bool) { 51 outputNormal, err := compile(path, sourceFiles, minify) 52 if err != nil { 53 t.Fatal(err) 54 } 55 56 // reverse the array 57 for i, j := 0, len(sourceFiles)-1; i < j; i, j = i+1, j-1 { 58 sourceFiles[i], sourceFiles[j] = sourceFiles[j], sourceFiles[i] 59 } 60 61 outputReversed, err := compile(path, sourceFiles, minify) 62 if err != nil { 63 t.Fatal(err) 64 } 65 66 if diff := cmp.Diff(string(outputNormal), string(outputReversed)); diff != "" { 67 t.Errorf("files in different order produce different JS:\n%s", diff) 68 } 69 } 70 71 type source struct { 72 name string 73 contents []byte 74 } 75 76 func compile(path string, sourceFiles []source, minify bool) ([]byte, error) { 77 conf := loader.Config{} 78 conf.Fset = token.NewFileSet() 79 conf.ParserMode = parser.ParseComments 80 81 context := build.Default // make a copy of build.Default 82 conf.Build = &context 83 conf.Build.BuildTags = []string{"js"} 84 85 var astFiles []*ast.File 86 for _, sourceFile := range sourceFiles { 87 astFile, err := parser.ParseFile(conf.Fset, sourceFile.name, sourceFile.contents, parser.ParseComments) 88 if err != nil { 89 return nil, err 90 } 91 astFiles = append(astFiles, astFile) 92 } 93 conf.CreateFromFiles(path, astFiles...) 94 prog, err := conf.Load() 95 if err != nil { 96 return nil, err 97 } 98 99 archiveCache := map[string]*Archive{} 100 var importContext *ImportContext 101 importContext = &ImportContext{ 102 Packages: make(map[string]*types.Package), 103 Import: func(path string) (*Archive, error) { 104 // find in local cache 105 if a, ok := archiveCache[path]; ok { 106 return a, nil 107 } 108 109 pi := prog.Package(path) 110 importContext.Packages[path] = pi.Pkg 111 112 // compile package 113 a, err := Compile(path, pi.Files, prog.Fset, importContext, minify) 114 if err != nil { 115 return nil, err 116 } 117 archiveCache[path] = a 118 return a, nil 119 }, 120 } 121 122 a, err := importContext.Import(path) 123 if err != nil { 124 return nil, err 125 } 126 b, err := renderPackage(a) 127 if err != nil { 128 return nil, err 129 } 130 return b, nil 131 } 132 133 func renderPackage(archive *Archive) ([]byte, error) { 134 selection := make(map[*Decl]struct{}) 135 for _, d := range archive.Declarations { 136 selection[d] = struct{}{} 137 } 138 139 buf := &bytes.Buffer{} 140 141 if err := WritePkgCode(archive, selection, goLinknameSet{}, false, &SourceMapFilter{Writer: buf}); err != nil { 142 return nil, err 143 } 144 145 return buf.Bytes(), nil 146 }