Skip to content

Commit b40cd48

Browse files
myitcvdmitshur
authored andcommitted
compiler: Fix generated code for type switch with *js.Object case. (#683)
This brings generated JS code for a type switch with a *js.Object case in line with the runtime $assertType function. For *js.Object type, we have to dereference via .$val.object. See https://github.com/gopherjs/gopherjs/blob/4b94c02883c52ae7f268e602db1dacf7bd0fbd78/compiler/prelude/types.go#L735-L740. Fixes #682.
1 parent 4b94c02 commit b40cd48

File tree

2 files changed

+29
-1
lines changed

2 files changed

+29
-1
lines changed

compiler/statements.go

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,9 @@ func (c *funcContext) translateStmt(stmt ast.Stmt, label *types.Label) {
123123
var bodyPrefix []ast.Stmt
124124
if implicit := c.p.Implicits[clause]; implicit != nil {
125125
value := refVar
126-
if _, isInterface := implicit.Type().Underlying().(*types.Interface); !isInterface {
126+
if typesutil.IsJsObject(implicit.Type().Underlying()) {
127+
value += ".$val.object"
128+
} else if _, ok := implicit.Type().Underlying().(*types.Interface); !ok {
127129
value += ".$val"
128130
}
129131
bodyPrefix = []ast.Stmt{&ast.AssignStmt{

js/js_test.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -571,3 +571,29 @@ func TestUint8Array(t *testing.T) {
571571
t.Errorf("Non-empty byte array is not externalized as a Uint8Array")
572572
}
573573
}
574+
575+
func TestTypeSwitchJSObject(t *testing.T) {
576+
obj := js.Global.Get("Object").New()
577+
obj.Set("foo", "bar")
578+
579+
want := "bar"
580+
581+
if got := obj.Get("foo").String(); got != want {
582+
t.Errorf("Direct access to *js.Object field gave %q, want %q", got, want)
583+
}
584+
585+
var x interface{} = obj
586+
587+
switch x := x.(type) {
588+
case *js.Object:
589+
if got := x.Get("foo").String(); got != want {
590+
t.Errorf("Value passed through interface and type switch gave %q, want %q", got, want)
591+
}
592+
}
593+
594+
if y, ok := x.(*js.Object); ok {
595+
if got := y.Get("foo").String(); got != want {
596+
t.Errorf("Value passed through interface and type assert gave %q, want %q", got, want)
597+
}
598+
}
599+
}

0 commit comments

Comments
 (0)