goscript 0.0.58 → 0.0.59
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +40 -33
- package/compiler/analysis.go +115 -19
- package/compiler/assignment.go +163 -217
- package/compiler/compiler.go +35 -31
- package/compiler/composite-lit.go +233 -196
- package/compiler/constraint.go +88 -0
- package/compiler/decl.go +82 -24
- package/compiler/expr-call-async.go +20 -34
- package/compiler/expr-call-builtins.go +19 -0
- package/compiler/expr-call-helpers.go +0 -28
- package/compiler/expr-call-make.go +93 -343
- package/compiler/expr-call-type-conversion.go +221 -249
- package/compiler/expr-call.go +70 -69
- package/compiler/expr-selector.go +21 -24
- package/compiler/expr.go +3 -60
- package/compiler/protobuf.go +180 -36
- package/compiler/spec-value.go +132 -24
- package/compiler/spec.go +14 -55
- package/compiler/stmt-assign.go +338 -356
- package/compiler/stmt-range.go +4 -24
- package/compiler/stmt.go +92 -203
- package/compiler/type-utils.go +185 -0
- package/compiler/type.go +26 -80
- package/dist/gs/builtin/slice.d.ts +1 -1
- package/dist/gs/builtin/slice.js +3 -0
- package/dist/gs/builtin/slice.js.map +1 -1
- package/dist/gs/builtin/type.js +8 -2
- package/dist/gs/builtin/type.js.map +1 -1
- package/dist/gs/fmt/fmt.js +113 -16
- package/dist/gs/fmt/fmt.js.map +1 -1
- package/dist/gs/runtime/runtime.d.ts +1 -1
- package/dist/gs/runtime/runtime.js +1 -1
- package/dist/gs/slices/slices.d.ts +23 -0
- package/dist/gs/slices/slices.js +61 -0
- package/dist/gs/slices/slices.js.map +1 -1
- package/go.mod +8 -8
- package/go.sum +14 -14
- package/gs/builtin/slice.ts +5 -2
- package/gs/builtin/type.ts +13 -6
- package/gs/fmt/fmt.test.ts +176 -0
- package/gs/fmt/fmt.ts +109 -18
- package/gs/runtime/runtime.ts +1 -1
- package/gs/slices/slices.ts +68 -0
- package/package.json +3 -3
|
@@ -6,17 +6,13 @@ import (
|
|
|
6
6
|
"strings"
|
|
7
7
|
)
|
|
8
8
|
|
|
9
|
-
//
|
|
10
|
-
|
|
11
|
-
func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
9
|
+
// isCallExprAsync determines if a CallExpr represents an async function/method call
|
|
10
|
+
func (c *GoToTSCompiler) isCallExprAsync(exp *ast.CallExpr) bool {
|
|
12
11
|
switch fun := exp.Fun.(type) {
|
|
13
12
|
case *ast.Ident:
|
|
14
13
|
// Function call (e.g., func())
|
|
15
|
-
if obj := c.
|
|
16
|
-
|
|
17
|
-
c.tsw.WriteLiterally("await ")
|
|
18
|
-
return true
|
|
19
|
-
}
|
|
14
|
+
if obj := c.objectOfIdent(fun); obj != nil {
|
|
15
|
+
return c.analysis.IsAsyncFunc(obj)
|
|
20
16
|
}
|
|
21
17
|
return false
|
|
22
18
|
|
|
@@ -29,13 +25,13 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
29
25
|
switch x := fun.X.(type) {
|
|
30
26
|
case *ast.Ident:
|
|
31
27
|
// Direct identifier: obj.method()
|
|
32
|
-
obj = c.
|
|
28
|
+
obj = c.objectOfIdent(x)
|
|
33
29
|
objOk = obj != nil
|
|
34
30
|
|
|
35
31
|
case *ast.StarExpr:
|
|
36
32
|
// Pointer dereference: (*p).method() or p.method() where p is a pointer
|
|
37
33
|
if id, isIdent := x.X.(*ast.Ident); isIdent {
|
|
38
|
-
obj = c.
|
|
34
|
+
obj = c.objectOfIdent(id)
|
|
39
35
|
objOk = obj != nil
|
|
40
36
|
}
|
|
41
37
|
|
|
@@ -43,8 +39,6 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
43
39
|
// Field access: obj.field.method()
|
|
44
40
|
// Get the type of the field access expression
|
|
45
41
|
if fieldType := c.pkg.TypesInfo.TypeOf(x); fieldType != nil {
|
|
46
|
-
// For field access, we create a synthetic object representing the field type
|
|
47
|
-
// We'll handle this case below when we determine the method's type
|
|
48
42
|
objOk = true
|
|
49
43
|
}
|
|
50
44
|
|
|
@@ -61,13 +55,7 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
61
55
|
if pkgName, isPkg := obj.(*types.PkgName); isPkg {
|
|
62
56
|
methodName := fun.Sel.Name
|
|
63
57
|
pkgPath := pkgName.Imported().Path()
|
|
64
|
-
|
|
65
|
-
// Check if this package-level function is async (empty TypeName)
|
|
66
|
-
if c.analysis.IsMethodAsync(pkgPath, "", methodName) {
|
|
67
|
-
c.tsw.WriteLiterally("await ")
|
|
68
|
-
return true
|
|
69
|
-
}
|
|
70
|
-
return false
|
|
58
|
+
return c.analysis.IsMethodAsync(pkgPath, "", methodName)
|
|
71
59
|
}
|
|
72
60
|
}
|
|
73
61
|
|
|
@@ -83,7 +71,6 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
83
71
|
}
|
|
84
72
|
} else {
|
|
85
73
|
// Field access case: obj.field.method()
|
|
86
|
-
// Get the type of the field access expression
|
|
87
74
|
targetType = c.pkg.TypesInfo.TypeOf(fun.X)
|
|
88
75
|
if targetType == nil {
|
|
89
76
|
return false
|
|
@@ -94,12 +81,7 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
94
81
|
|
|
95
82
|
// Check if target type is an interface
|
|
96
83
|
if interfaceType, isInterface := targetType.Underlying().(*types.Interface); isInterface {
|
|
97
|
-
|
|
98
|
-
if c.analysis.IsInterfaceMethodAsync(interfaceType, methodName) {
|
|
99
|
-
c.tsw.WriteLiterally("await ")
|
|
100
|
-
return true
|
|
101
|
-
}
|
|
102
|
-
return false
|
|
84
|
+
return c.analysis.IsInterfaceMethodAsync(interfaceType, methodName)
|
|
103
85
|
}
|
|
104
86
|
|
|
105
87
|
// Get the named type from the target type
|
|
@@ -128,22 +110,26 @@ func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
|
128
110
|
if typePkg != nil {
|
|
129
111
|
pkgPath = typePkg.Path()
|
|
130
112
|
} else {
|
|
131
|
-
// Fallback to current package
|
|
132
113
|
pkgPath = c.pkg.Types.Path()
|
|
133
114
|
}
|
|
134
115
|
|
|
135
|
-
|
|
136
|
-
if c.analysis.IsMethodAsync(pkgPath, typeName, methodName) {
|
|
137
|
-
c.tsw.WriteLiterally("await ")
|
|
138
|
-
return true
|
|
139
|
-
}
|
|
140
|
-
return false
|
|
116
|
+
return c.analysis.IsMethodAsync(pkgPath, typeName, methodName)
|
|
141
117
|
|
|
142
118
|
default:
|
|
143
119
|
return false
|
|
144
120
|
}
|
|
145
121
|
}
|
|
146
122
|
|
|
123
|
+
// writeAsyncCallIfNeeded writes the await prefix for async function or method calls
|
|
124
|
+
// Returns true if await was written, false otherwise
|
|
125
|
+
func (c *GoToTSCompiler) writeAsyncCallIfNeeded(exp *ast.CallExpr) bool {
|
|
126
|
+
if c.isCallExprAsync(exp) {
|
|
127
|
+
c.tsw.WriteLiterally("await ")
|
|
128
|
+
return true
|
|
129
|
+
}
|
|
130
|
+
return false
|
|
131
|
+
}
|
|
132
|
+
|
|
147
133
|
// addNonNullAssertion adds ! for function calls that might return null
|
|
148
134
|
func (c *GoToTSCompiler) addNonNullAssertion(expFun ast.Expr) {
|
|
149
135
|
if funType := c.pkg.TypesInfo.TypeOf(expFun); funType != nil {
|
|
@@ -151,7 +137,7 @@ func (c *GoToTSCompiler) addNonNullAssertion(expFun ast.Expr) {
|
|
|
151
137
|
// Check if this is a function parameter identifier that needs not-null assertion
|
|
152
138
|
if ident, isIdent := expFun.(*ast.Ident); isIdent {
|
|
153
139
|
// Check if this identifier is a function parameter
|
|
154
|
-
if obj := c.
|
|
140
|
+
if obj := c.objectOfIdent(ident); obj != nil {
|
|
155
141
|
if _, isVar := obj.(*types.Var); isVar {
|
|
156
142
|
// This is a variable (including function parameters)
|
|
157
143
|
// Function parameters that are function types need ! assertion
|
|
@@ -8,6 +8,25 @@ import (
|
|
|
8
8
|
"github.com/pkg/errors"
|
|
9
9
|
)
|
|
10
10
|
|
|
11
|
+
// builtinFunctions is the definitive list of Go builtin functions handled by the compiler
|
|
12
|
+
var builtinFunctions = map[string]bool{
|
|
13
|
+
"len": true,
|
|
14
|
+
"cap": true,
|
|
15
|
+
"make": true,
|
|
16
|
+
"new": true,
|
|
17
|
+
"append": true,
|
|
18
|
+
"copy": true,
|
|
19
|
+
"delete": true,
|
|
20
|
+
"complex": true,
|
|
21
|
+
"real": true,
|
|
22
|
+
"imag": true,
|
|
23
|
+
"close": true,
|
|
24
|
+
"panic": true,
|
|
25
|
+
"recover": true,
|
|
26
|
+
"print": true,
|
|
27
|
+
"println": true,
|
|
28
|
+
}
|
|
29
|
+
|
|
11
30
|
// writeBuiltinFunction handles built-in Go functions
|
|
12
31
|
func (c *GoToTSCompiler) writeBuiltinFunction(exp *ast.CallExpr, funName string) (handled bool, err error) {
|
|
13
32
|
switch funName {
|
|
@@ -7,34 +7,6 @@ import (
|
|
|
7
7
|
"github.com/pkg/errors"
|
|
8
8
|
)
|
|
9
9
|
|
|
10
|
-
// isByteSliceType checks if a type is []byte (slice of uint8)
|
|
11
|
-
func (c *GoToTSCompiler) isByteSliceType(t types.Type) bool {
|
|
12
|
-
if sliceType, isSlice := t.Underlying().(*types.Slice); isSlice {
|
|
13
|
-
if basicElem, isBasic := sliceType.Elem().(*types.Basic); isBasic && basicElem.Kind() == types.Uint8 {
|
|
14
|
-
return true
|
|
15
|
-
}
|
|
16
|
-
}
|
|
17
|
-
return false
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
// isRuneSliceType checks if a type is []rune (slice of int32)
|
|
21
|
-
func (c *GoToTSCompiler) isRuneSliceType(t types.Type) bool {
|
|
22
|
-
if sliceType, isSlice := t.Underlying().(*types.Slice); isSlice {
|
|
23
|
-
if basicElem, isBasic := sliceType.Elem().(*types.Basic); isBasic && basicElem.Kind() == types.Int32 {
|
|
24
|
-
return true
|
|
25
|
-
}
|
|
26
|
-
}
|
|
27
|
-
return false
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
// isStringType checks if a type is string
|
|
31
|
-
func (c *GoToTSCompiler) isStringType(t types.Type) bool {
|
|
32
|
-
if basic, isBasic := t.Underlying().(*types.Basic); isBasic {
|
|
33
|
-
return basic.Kind() == types.String || basic.Kind() == types.UntypedString
|
|
34
|
-
}
|
|
35
|
-
return false
|
|
36
|
-
}
|
|
37
|
-
|
|
38
10
|
// writeByteSliceCreation handles the creation of []byte slices with proper Uint8Array handling
|
|
39
11
|
func (c *GoToTSCompiler) writeByteSliceCreation(lengthArg, capacityArg interface{}) error {
|
|
40
12
|
return c.writeSliceCreationForType(lengthArg, capacityArg, true)
|