You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

JavaScript转TypeScript接口映射:解决onvif-nvt库add方法调用报错问题

问题原因

你遇到的报错核心来自两个问题:

  • 初始值的不安全类型断言:你用{} as OnvifDevice把空对象强制断言为自定义接口类型,骗过了TypeScript的编译检查,但空对象本身没有add方法,只要你在connect异步请求完成之前调用coreService,就会触发运行时报错。
  • connect方法语法错误:你当前的connect方法没有包裹Promise构造函数,直接在then里调用resolve会触发引用错误,很容易出现coreService调用时connect还没完成赋值,this.device还是初始空对象的情况。

修复方案

第一步:修正类的类型定义和逻辑

import OnvifManager from 'onvif-nvt'

// 自定义匹配Camera返回值的接口,可根据实际返回属性补全
interface OnvifDevice {
  address: string
  add(name: string): void
  // 补充其他你用到的Camera对象属性/方法
}

class OnvifApi {
  // 初始值设为null,明确标注可能为空的状态
  device: OnvifDevice | null = null
  private connectParams: any[]

  constructor (...params: any[]) {
    this.connectParams = params
  }

  // 修正connect方法,正确返回Promise
  connect (): Promise<OnvifDevice> {
    return new Promise((resolve, reject) => {
      OnvifManager.connect(...this.connectParams)
        .then((response: OnvifDevice) => {
          this.device = response
          resolve(response)
        })
        .catch(err => reject(err))
    })
  }

  coreService(): Promise<Type[]> {
    // 调用方法前先判断device是否完成初始化,TS会自动做类型收窄
    if (!this.device) {
      throw new Error('请先调用connect完成设备连接')
    }
    this.device.add('core')
    // 后续业务逻辑
  }
}

第二步:调整调用逻辑,必须等待connect完成后再调用其他方法

const api = new OnvifApi('设备地址', '端口', '用户名', '密码')
async function exec() {
  // 等待连接完成
  await api.connect()
  // 再调用业务方法
  const res = await api.coreService()
}
exec()

全局类型映射(可选优化)

如果需要在项目全局复用onvif-nvt的类型,你可以在项目根目录新增types/onvif-nvt.d.ts类型声明文件:

declare module 'onvif-nvt' {
  export interface OnvifDevice {
    address: string
    add(name: string): void
    // 补全所有用到的属性方法
  }
  export default class OnvifManager {
    static connect(...params: any[]): Promise<OnvifDevice>
  }
}

配置完成后整个项目中引入onvif-nvt时都会自动带上类型提示,不需要反复定义接口。

内容的提问来源于stack exchange,提问作者nirvair

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 18:21:03