普通 JS 函数中的回调并不总是有效?

Callback in vanilla JS function doesn't always work?

我编写了一个小的 vanilla JS 函数来利用 XMLHttpRequest 对象。我有一个到 return 的回调,但出于某种原因,我只能让回调在 onreadystatechange 函数上工作,我需要它在我的 ontimeoutonerror 上工作...

我的函数:

function makeHttpRequest (type, url, timeout, callback) {
  const xhr = new XMLHttpRequest()

  xhr.open(type, url, true)
  xhr.timeout = timeout
  xhr.ontimeout = () => {
    callback.apply('timeout error')
  }

  xhr.onreadystatechange = () => {
    if (xhr.readyState === 4 && xhr.response != null) {
      callback.apply(xhr)
    }
  }

  xhr.onerror = () => {
    callback.apply('generic error')
  }

  xhr.send()
}

我如何使用函数:

makeHttpRequest('GET', url, timeout, function() {
  const res = this.response != '' ? this.response : JSON.stringify({})
  // ...
})

this.response 在超时和错误时不包含任何内容。

apply 方法将函数的 this 参数设置为其第一个参数。当发生超时或错误时,您可以这样调用应用程序:

callback.apply('timeout error');

因此,this 值是一个字符串。如果您在 documentation for javascript strings,您会看到 String 对象没有 .response 属性。这就是为什么 'timeout error'.response 不包含任何内容(它是 undefined)。

如果您希望 this.response 包含错误消息,则不要将字符串作为 this 传递。而是将其作为 .response:

传递
let error = {
    response: 'timeout error'
}

callback.apply(error)

或者更简单地说:

callback.apply({ response: 'timeout error' })