如何正确检查plugin.Open返回的错误类型

时间:2018-09-24 03:02:11

标签: go

我想知道如何检查plugin.Open返回的错误类型,例如:

package main

import "plugin"

func main() {
  _, err := plugin.Open("./module.so")
  // here
}

如果错误是我想做些不同的事情

plugin.Open("./module.so"): realpath failed

这基本上意味着该文件不存在。

预期结果示例:

package main

import "plugin"

func main() {
  _, err := plugin.Open("./module.so")
  if err.Error() == "plugin.Open(\"./module.so\"): realpath failed" {
    // do something different here
  } else {
    log.Fatal(err)
  }
}

我传递给plugin.Open的字符串可以具有其他值,因此它需要比这更聪明的东西。

谢谢。

1 个答案:

答案 0 :(得分:2)

plugin.Open()的{​​{3}}进行检查可以发现该软件包调用了一些C代码来确定该路径是否存在。如果不是,则返回纯错误值。特别是,该程序包未定义可与之进行比较的任何前哨错误,也未返回其自己的error接口的具体实现程序,该接口带有自定义元数据。这是产生该错误的代码:

return nil, errors.New(`plugin.Open("` + name + `"): realpath failed`)

errors.Newerror接口的基本实现,该接口不允许传递任何其他信息。与标准库中其他返回错误(例如,os包中的路径不存在错误)的位置不同,在这种情况下,您无法获得此类元数据。


检查模块文件是否首先存在

我的偏好是使用os软件包提供的本机功能在尝试加载模块之前,先验证该模块是否存在:

modulePath := "./module.so"
if _, err := os.Stat(modulePath); os.IsNotExist(err) {
    // Do whatever is required on module not existing
}

// Continue to load the module – can be another branch of the if block
// above if necessary, depending on your desired control flow.

比较错误值的子集

您还可以使用strings.Contains在返回的错误值中搜索值realpath failed这不是一个好主意,如果将来字符串发生变化,因此,如果采用这种模式,至少应该确保围绕它进行严格的测试(即便如此,它仍然不是很好)。

_, err := plugin.Open("./module.so")
if err != nil {
    if strings.Contains(err.Error(), "realpath failed") {
        // Do your fallback behavior for module not existing
        log.Fatalf("module doesn't exist")
    } else {
        // Some other type of error
        log.Fatalf("%+v", err)
    }
}