每次在 Javascript 中使用 fetch() 时如何执行函数?
How can I execute a function every time fetch() is used in Javascript?
每次在我的脚本中发出 HTTP 请求时,我都在尝试 post 向我的 sharedWorker
发送一条消息,以免我在每次 HTTP 请求后都必须手动执行此操作。
我设法让它像这样工作:
var App = {
__webWorker: null,
__XMLHttpRequest: XMLHttpRequest.prototype.open,
__onScriptComplete: e => {
if( e.data.type && e.data.type === 'worker' ) {
sessionStorage.setItem( 'token', e.data.session.token );
return;
}
}
};
window.addEventListener( 'load', () => {
XMLHttpRequest.prototype.open = (method, url, async, user, password) => {
App.__XMLHttpRequest(method, url, async, user, password);
App.__webWorker.postMessage( '{{md5(session_id())}}' );
};
const worker = new SharedWorker( '{{$router->generate( 'web_notify_worker' )}}' );
worker.port.onmessage = e => App.__onScriptComplete( e );
App.__webWorker = worker.port;
// The below gives me a Uncaught TypeError: Illegal invocation and the App.__webWorker.postMessage is executed
let req = new XMLHttpRequest();
req.open( 'GET', '/', true );
req.send();
// The below works fine but the App.__webWorker.postMessage is not executed
fetch( '/', { method: 'GET' } );
} );
当我创建一个 new XMLHttpRequest()
时,它工作正常并且 sessionStorage
项目是用数据设置的。但是,我不使用 XMLHttpRequest
,而是使用 fetch()
。这似乎没有创建我认为会的 XMLHttpRequest
。
如何在每次调用新的 fetch()
时在我的 App.__webWorker
上执行 postMessage
函数?最好是完成后。
更新:这是我自己的框架,我使用了Smarty模板引擎,所以忽略了{{}}
前缀区域。这就是我将数据从 PHP.
导入脚本的方式
更新:我试过这样做,但我得到 Uncaught (in promise) TypeError: Failed to execute 'fetch' on 'Window': Illegal invocation
:
var App = {
...,
__fetch: fetch
}
fetch = ( uri, args ) => {
App.__fetch( uri, args );
App.__webWorker.postMessage( '{{md5( session_id() )}}' );
};
经过大量 Google 搜索后,我发现问题出在 fetch
存储在 App
范围内。要解决此问题,您必须将其存储在 window
范围内。
_fetch = fetch;
fetch = ( uri, args ) => {
let f = _fetch( uri, args );
App.__webWorker.postMessage( '{{md5( session_id() )}}' );
return f;
};
这样就可以正常工作了,每次发送 fetch()
时,我的 sharedWorker
都会发布一条消息。
您可以覆盖覆盖全局并调用它。如果你把它变成你自己的方法并且你调用它而不是这个 'hijacking
会更干净
const _fetch = window.fetch
// window.fetch = function() {
window.fetch = function(...args) {
console.log('before fetch')
// return Promise.resolve(_fetch.apply(window, arguments))
return Promise.resolve(_fetch.apply(window, args))
.then(resp => {
console.log('inside then');
return resp;
})
}
fetch('https://jsonplaceholder.typicode.com/todos/1')
.then(response => response.json())
.then(json => console.log(json))
每次在我的脚本中发出 HTTP 请求时,我都在尝试 post 向我的 sharedWorker
发送一条消息,以免我在每次 HTTP 请求后都必须手动执行此操作。
我设法让它像这样工作:
var App = {
__webWorker: null,
__XMLHttpRequest: XMLHttpRequest.prototype.open,
__onScriptComplete: e => {
if( e.data.type && e.data.type === 'worker' ) {
sessionStorage.setItem( 'token', e.data.session.token );
return;
}
}
};
window.addEventListener( 'load', () => {
XMLHttpRequest.prototype.open = (method, url, async, user, password) => {
App.__XMLHttpRequest(method, url, async, user, password);
App.__webWorker.postMessage( '{{md5(session_id())}}' );
};
const worker = new SharedWorker( '{{$router->generate( 'web_notify_worker' )}}' );
worker.port.onmessage = e => App.__onScriptComplete( e );
App.__webWorker = worker.port;
// The below gives me a Uncaught TypeError: Illegal invocation and the App.__webWorker.postMessage is executed
let req = new XMLHttpRequest();
req.open( 'GET', '/', true );
req.send();
// The below works fine but the App.__webWorker.postMessage is not executed
fetch( '/', { method: 'GET' } );
} );
当我创建一个 new XMLHttpRequest()
时,它工作正常并且 sessionStorage
项目是用数据设置的。但是,我不使用 XMLHttpRequest
,而是使用 fetch()
。这似乎没有创建我认为会的 XMLHttpRequest
。
如何在每次调用新的 fetch()
时在我的 App.__webWorker
上执行 postMessage
函数?最好是完成后。
更新:这是我自己的框架,我使用了Smarty模板引擎,所以忽略了{{}}
前缀区域。这就是我将数据从 PHP.
更新:我试过这样做,但我得到 Uncaught (in promise) TypeError: Failed to execute 'fetch' on 'Window': Illegal invocation
:
var App = {
...,
__fetch: fetch
}
fetch = ( uri, args ) => {
App.__fetch( uri, args );
App.__webWorker.postMessage( '{{md5( session_id() )}}' );
};
经过大量 Google 搜索后,我发现问题出在 fetch
存储在 App
范围内。要解决此问题,您必须将其存储在 window
范围内。
_fetch = fetch;
fetch = ( uri, args ) => {
let f = _fetch( uri, args );
App.__webWorker.postMessage( '{{md5( session_id() )}}' );
return f;
};
这样就可以正常工作了,每次发送 fetch()
时,我的 sharedWorker
都会发布一条消息。
您可以覆盖覆盖全局并调用它。如果你把它变成你自己的方法并且你调用它而不是这个 'hijacking
会更干净const _fetch = window.fetch
// window.fetch = function() {
window.fetch = function(...args) {
console.log('before fetch')
// return Promise.resolve(_fetch.apply(window, arguments))
return Promise.resolve(_fetch.apply(window, args))
.then(resp => {
console.log('inside then');
return resp;
})
}
fetch('https://jsonplaceholder.typicode.com/todos/1')
.then(response => response.json())
.then(json => console.log(json))