【问题标题】:how do I extract the right type from my pseduo-union type如何从我的伪联合类型中提取正确的类型
【发布时间】:2017-04-25 07:02:03
【问题描述】:

我有一个从 js 返回的伪联合类型。

这是我的 scalajs:

@js.native 特征 ErrorResponse 扩展 js.Object { val 错误:字符串 = js.native val errorDescription: String = js.native } @js.native 特征 TokenResponse 扩展 js.Object{ val accessToken: String = js.native val expriseOn: js.Date = js.native val tokenType: String = js.native val userId: String = js.native val identityProvider: String = js.native }

还有我的 scalajs

@js.native @JSImport("mymodule", "JSClassInModule") 类 JSClassInModule 扩展 js.Object { // ... def scalajsfunc(): 错误响应 | TokenResponse = js.native // .. }

如果我调用 scalajsfunc,我如何习惯性地将返回值归结为伪联合类中指定的两个类之一?

【问题讨论】:

    标签: scala.js


    【解决方案1】:

    使用模式匹配:

    val jsClassInModule: JSClassInModule = ???
    (jsClassInModule.scalajsfunc(): Any) match {
      case response: ErrorResponse => ...
      case response: TokenResponse => ...
    }
    

    : Any 的归属对于解决 Scala 类型检查器不知道 | 的具体语义这一事实是必要的,并且如果您尝试直接匹配 |,则会给出虚假的错误消息。

    编辑:如果个别类型是 JS 特征,即扩展 js.Any 的特征,上述方法将不起作用,因为一般情况下不可能使用 JS 特征执行 isInstanceOf 测试(这是模式匹配所做的,并且大部分与 | 无关)。相反,您需要编写任何有意义的实例测试,然后进行转换。例如,假设我们可以通过测试 errorCode 属性的存在来区分 ErrorResponseTokenResponse,我们可以这样做:

    val jsClassInModule: JSClassInModule = ???
    (jsClassInModule.scalajsfunc(): Any) match {
      case response if js.Object.hasOwnProperty(response, "errorCode") =>
        val errorResponse = response.asInstanceOf[ErrorResponse]
        ...
      case response =>
        val tokenResponse = response.asInstanceOf[TokenResponse]
        ...
    }
    

    这就是 JavaScript 的丑陋本质。

    【讨论】:

    • 这似乎不起作用。每个 case 子句都说:“不支持,因为它是原始的 JS 特征”。考虑到对象的唯一区别是某些属性可能会或可能不会被定义......我不确定它会如何确定这一点......是 js.Objects。
    • 哦,那是与| 几乎无关的另一件事。 Scala.js 编译器确实无法测试对象是否是 JS 特征的实例。在这种情况下,您必须自己编写测试代码,然后进行转换。请参阅我的更新答案。
    • 这似乎做到了。我不得不将 if 测试调整为 response.merge[js.Object].hasProperty("error")
    猜你喜欢
    • 2022-07-19
    • 1970-01-01
    • 2019-03-27
    • 1970-01-01
    • 2017-05-15
    • 2019-03-05
    • 1970-01-01
    • 2020-09-22
    相关资源
    最近更新 更多