如何解决event.passThroughOnException将请求发送到源,但没有POST数据
我认为event.passThroughOnException();
应该为我的工作人员设置fail open
策略,这样,如果从我的代码中引发异常,原始请求将发送到我的原始服务器,但似乎丢失了发布数据。我认为这是因为请求正文是可读的流,一旦读取就无法再次读取,但是如何管理这种情况?
addEventListener('fetch',(event) => {
event.passThroughOnException();
event.respondWith(handleRequest(event));
});
async function handleRequest(event: FetchEvent): Promise<Response> {
const response = await fetch(event.request);
// do something here that potentially raises an Exception
// @ts-ignore
ohnoez(); // deliberate failure
return response;
}
如下图所示,原始服务器未收到任何正文(foobar
):
解决方法
不幸的是,这是passThroughOnException()
的已知限制。工人运行时使用流作为请求和响应主体;它不会缓冲身体。结果,一旦身体被消耗掉,它就消失了。因此,如果转发请求,然后再引发异常,则请求正文将无法再次发送。
通过克隆event.request
来解决问题,然后在handleRequest
中添加try / catch。在catch(err)
上,在传递克隆的请求的同时,使用fetch
将请求发送到源。
// Pass request to whatever it requested
async function passThrough(request: Request): Promise<Response> {
try {
let response = await fetch(request)
// Make the headers mutable by re-constructing the Response.
response = new Response(response.body,response)
return response
} catch (err) {
return ErrorResponse.NewError(err).respond()
}
}
// request handler
async function handleRequest(event: FetchEvent): Promise<Response> {
const request = event.request
const requestClone = event.request.clone()
let resp
try {
// handle request
resp = await handler.api(request)
} catch (err) {
// Pass through manually on exception (because event.passThroughOnException
// does not pass request body,so use that as a last resort)
resp = await passThrough(requestClone)
}
return resp
}
addEventListener('fetch',(event) => {
// Still added passThroughOnException here
// in case the `passThrough` function throws exception
event.passThroughOnException()
event.respondWith(handleRequest(event))
})
到目前为止,看来工作正常。很想知道是否还有其他解决方案。
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。