-
Notifications
You must be signed in to change notification settings - Fork 2.8k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Q] timeout handling #175
Comments
There is an open discussion on timeout handling in the Fetch specification repository: whatwg/fetch#20. We will add the behavior to the polyfill when the feature is added to the standard specification. |
You can implement your own timeout wrapper for Promises: // Rough implementation. Untested.
function timeout(ms, promise) {
return new Promise(function(resolve, reject) {
setTimeout(function() {
reject(new Error("timeout"))
}, ms)
promise.then(resolve, reject)
})
}
timeout(1000, fetch('/hello')).then(function(response) {
// process response
}).catch(function(error) {
// might be a timeout error
}) The Note that this is not a connection timeout. This is a response timeout. Due to technical restrictions we can't implement a connection timeout. Also note that with the above implementation, even if the timeout happens, the original request won't be aborted because we don't have an API to abort |
@mislav Awesome! |
@mislav Good one. |
Five cents to @mislav solution - remove timeout if promise was resolved or rejected internally. function timeoutPromise(ms, promise) {
return new Promise((resolve, reject) => {
const timeoutId = setTimeout(() => {
reject(new Error("promise timeout"))
}, ms);
promise.then(
(res) => {
clearTimeout(timeoutId);
resolve(res);
},
(err) => {
clearTimeout(timeoutId);
reject(err);
}
);
})
} |
i wish this was actually possible to stop the underlying fetch() work... |
@gre That would be nice, but in reality it's not so trivial to add. See whatwg/fetch#27 |
Another 2c to @nodkz enhancement. Don't re-resolve/re-reject the promise if the request does eventually complete after the timeout fires:
|
@dieseldjango @nodkz I appreciate you trying to improve upon my solution, but you assure you, both approaches are not necessary. Promises can't be re-resolved or re-rejected: the first resolution or rejection "wins" and the others are ignored. Thus, my original code works just as well without any extra code thrown at it: function timeout(ms, promise) {
return new Promise(function(resolve, reject) {
setTimeout(function() {
reject(new Error("timeout"))
}, ms)
promise.then(resolve, reject)
})
} If you add extra code that clears the timeout if it won't be necessary, it's a premature optimization. You're basically saving yourself from no more than just an overhead of executing a function that constructs a |
based on suggestion on JakeChampion/fetch#175
What about this? function timeout (promise, ms = TIME_OUT) {
let timerPromise = new Promise((resolve, reject) => {
setTimeout(() => {
reject(new Error('Request Timeout'))
}, ms)
})
return Promise.race([timerPromise, promise])
} |
#547 may help this. |
I tried a TypeScript Version of @mislav code. async function timeout<T>(ms, promise): Promise<T> {
return new Promise<T>(async (resolve, reject) => {
setTimeout(() => {
reject(new Error("timeout"))
}, ms)
resolve(await promise)
})
} |
@mislav it would be great to have a connection timeout. This seems to be a fairly common and needed option going as far back to AngularJS with $http timeout in ms, but as you suggested there are alternatives. Here's an ES6/ES7 compatible approach with a demo (note you will need to Babel this for IE):
Tested this out with NodeJS v9.4.0 Works really well and in an asynchronous manner as expected. |
@jasonwr Sure, but we are just a polyfill, and the fetch spec itself doesn't define any timeout functionality. If you want to discuss said features, you can ask in the official repo: whatwg/fetch#20 whatwg/fetch#180 |
Hi!
Haven't found the way to set connection timeout. How to?
The text was updated successfully, but these errors were encountered: