使用递归重试 vue 资源 ajax 调用
Retry vue resource ajax calls using recursion
如果我的 ajax 呼叫最初失败,我正在尝试重试。如果初始 ajax 调用失败并超时 5 秒,它每次执行 3 次。该函数作为方法导入到我的 vue 组件中,并在 ready()
上调用
export function getOrderStatus (order) {
let url = `/orders/status/${order.id}`
let promise = this.$http.get(url)
function retry(order, path, promise, retryAttempt) {
promise.then((response) => {
if (response.body.status === 'success') {
showOrderStatus()
}
}, (response) => {
if (retries < 2) {
retryAttempt++
setTimeout(retry(order, path, promise, retryAttempt), 5000);
} else {
handleError()
}
})
}
retry(order, path, promise, 0)
}
组件
import { getOrderStatus } from '../shared'
export default {
name: 'order-page',
props: { order },
methods: { getOrderStatus },
ready() {
this.getOrderStatus(order)
}
}
我不确定这是否是重试 ajax 调用的最佳方式,因此我们将不胜感激任何建议。
您需要重构它,因为您正在缓存 promise
。这里的问题是 Promise 本质上只会完成一次,解决或拒绝。因此,如果您的 $http 请求确实失败,您以后对 retry()
的调用也将全部失败,而不会调用端点。
尝试如下操作:
如果您想跨组件共享 component 可以重构为 mixin(而不是 import { getOrderStatus } from '../shared'
)
data () {
return {
attempt: 0,
}
}
methods: {
showOrder () { // or whatever needs this
this.getOrderStatus('order-123')
.then((reponse) => this.showOrderStatus())
.catch((reponse) => this.handleError(response))
},
getOrderStatus (order) {
this.attempt = 0
return
new Promise((resolve, reject) => this.callOrderEndpoint({
order,
resolve,
reject,
}))
},
callOrderEndpoint ({ order, resolve, reject }) {
const url = `/orders/status/${order.id}`
this.$http
.get(url)
.then((response) => {
if (response.body.status === 'success') {
resolve()
} else {
reject()
}
})
.catch(response) => {
if (this.attempt++ < 2) {
setTimeout(() =>
this.callOrderEndpoint({ order, resolve, reject }),
5000))
} else {
reject(response)
}
})
},
showOrderStatus () {
// whatever this does
},
handleError (response) {
console.error('fail')
},
},
我认为更好的方法是 return 来自 getOrderStatus
的 Promise。这将允许您将成功/失败方法移动到 then/catch 方法以获得更好的结构。
如果我的 ajax 呼叫最初失败,我正在尝试重试。如果初始 ajax 调用失败并超时 5 秒,它每次执行 3 次。该函数作为方法导入到我的 vue 组件中,并在 ready()
export function getOrderStatus (order) {
let url = `/orders/status/${order.id}`
let promise = this.$http.get(url)
function retry(order, path, promise, retryAttempt) {
promise.then((response) => {
if (response.body.status === 'success') {
showOrderStatus()
}
}, (response) => {
if (retries < 2) {
retryAttempt++
setTimeout(retry(order, path, promise, retryAttempt), 5000);
} else {
handleError()
}
})
}
retry(order, path, promise, 0)
}
组件
import { getOrderStatus } from '../shared'
export default {
name: 'order-page',
props: { order },
methods: { getOrderStatus },
ready() {
this.getOrderStatus(order)
}
}
我不确定这是否是重试 ajax 调用的最佳方式,因此我们将不胜感激任何建议。
您需要重构它,因为您正在缓存 promise
。这里的问题是 Promise 本质上只会完成一次,解决或拒绝。因此,如果您的 $http 请求确实失败,您以后对 retry()
的调用也将全部失败,而不会调用端点。
尝试如下操作:
如果您想跨组件共享component 可以重构为 mixin(而不是 import { getOrderStatus } from '../shared'
)
data () {
return {
attempt: 0,
}
}
methods: {
showOrder () { // or whatever needs this
this.getOrderStatus('order-123')
.then((reponse) => this.showOrderStatus())
.catch((reponse) => this.handleError(response))
},
getOrderStatus (order) {
this.attempt = 0
return
new Promise((resolve, reject) => this.callOrderEndpoint({
order,
resolve,
reject,
}))
},
callOrderEndpoint ({ order, resolve, reject }) {
const url = `/orders/status/${order.id}`
this.$http
.get(url)
.then((response) => {
if (response.body.status === 'success') {
resolve()
} else {
reject()
}
})
.catch(response) => {
if (this.attempt++ < 2) {
setTimeout(() =>
this.callOrderEndpoint({ order, resolve, reject }),
5000))
} else {
reject(response)
}
})
},
showOrderStatus () {
// whatever this does
},
handleError (response) {
console.error('fail')
},
},
我认为更好的方法是 return 来自 getOrderStatus
的 Promise。这将允许您将成功/失败方法移动到 then/catch 方法以获得更好的结构。