如何在Go中调用未导出类的方法

huangapple go评论88阅读模式
英文:

How to invoke unexported class' method in go

问题

你想在net/http/server.go中调用http.Server的newConn方法。

func (srv *Server) newConn(rwc net.Conn) *conn {
    c := &conn{
        server: srv,
        rwc:    rwc,
    }
    if debugServerConnections {
        c.rwc = newLoggingConn("server", c.rwc)
    }
    return c
}

尝试使用反射访问,但出现了错误。

conn := ...
server := &http.Server{}

inputs := make([]reflect.Value, 1)
inputs[0] = reflect.ValueOf(conn)
c := reflect.ValueOf(server).MethodByName("newConn").Call(inputs)

错误信息如下:

panic: reflect: call of reflect.Value.Call on zero Value

goroutine 17 [running, locked to thread]:
reflect.flag.mustBe(0x0, 0x13)
    /usr/local/go/src/reflect/value.go:201 +0xae
reflect.Value.Call(0x0, 0x0, 0x0, 0xc420047d10, 0x1, 0x1, 0x0, 0x0, 0xc4200e82c0)
    /usr/local/go/src/reflect/value.go:300 +0x38

是否有解决方案?

英文:

I want to invoke http.Server's newConn method in net/http/server.go

func (srv *Server) newConn(rwc net.Conn) *conn {
	c := &conn{
		server: srv,
		rwc:    rwc,
	}
	if debugServerConnections {
		c.rwc = newLoggingConn("server", c.rwc)
	}
	return c
}

Tried to access using reflect but errors occured

conn := ...
server := &http.Server{}

inputs := make([]reflect.Value, 1)
inputs[0] = reflect.ValueOf(conn)
c := reflect.ValueOf(server).MethodByName("newConn").Call(inputs)

<!-- language: text -->

panic: reflect: call of reflect.Value.Call on zero Value

goroutine 17 [running, locked to thread]:
reflect.flag.mustBe(0x0, 0x13)
    /usr/local/go/src/reflect/value.go:201 +0xae
reflect.Value.Call(0x0, 0x0, 0x0, 0xc420047d10, 0x1, 0x1, 0x0, 0x0, 0xc4200e82c0)
    /usr/local/go/src/reflect/value.go:300 +0x38

<!-- end snippet -->

Is there any solution?

答案1

得分: 1

TLDR 你不需要这样做。这正是不导出东西的整个目的,以防止直接访问它们。

话虽如此,这个问题听起来很像一个XY问题。也许如果你能解释一下你想要实现什么,我们可以提供一种替代的方法。

更详细的回答

这可以通过反射来实现(正如你所尝试的那样)。这只应该在极为罕见的情况下才这样做,甚至可能都不需要。

为了帮助解决问题,请提供一个完整且可复现的示例。你提供的代码无法编译,所以无法进行调试。

英文:

TLDR You don't. That's the whole point of not exporting things; to prevent direct access to them.

Having said that, this question sounds a lot like an XY Problem. Perhaps if you can explain what you're trying to accomplish, we can suggest an alternative approach.

Longer answer

This can be possible with reflection (as you're attempting). This should only be done in the absolute rarest of situations, if even then.

To help with that, please include a complete, reproducible example. The code you've included doesn't compile, so it's impossible to debug.

huangapple
  • 本文由 发表于 2017年8月7日 18:01:37
  • 转载请务必保留本文链接:https://go.coder-hub.com/45544252.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定