Как перехватить все http-запросы, включая отправку формы
Я хотел бы перехватить все http-запросы, исходящие с моей веб-страницы, и добавить параметр в тело запроса. Моя страница включает в себя формы - я также хочу захватить отправленные формы. Я пытался использовать Jquery ajaxSend и Javascript setRequestHeader, но оба не работали для меня. Как мне этого добиться?
Спасибо
3 ответа
https://developer.mozilla.org/en/docs/Web/API/Service_Worker_API
Сервисные работники, по сути, действуют как прокси-серверы, которые размещаются между веб-приложениями, браузером и сетью (при наличии).
Он принимает форму файла JavaScript, который может управлять веб-страницей / сайтом, с которыми он связан, перехватывая и изменяя запросы навигации и ресурсов
Вы регистрируете работника сервиса в своем коде приложения из файла с именем, например, sw.js
делая это:
if ('serviceWorker' in navigator) {
window.addEventListener('load', function() {
navigator.serviceWorker.register('sw.js').then(function(registration) {
console.log('Service worker registered with scope: ', registration.scope);
}, function(err) {
console.log('ServiceWorker registration failed: ', err);
});
});
}
И в sw.js
файл (фактический код работника службы): чтобы перехватывать запросы, вы прикрепляете fetch
прослушиватель события для сервисного работника, который вызывает respondWith()
метод и делает что-то с .request
участник из объекта события:
self.addEventListener('fetch', function(event) {
event.respondWith(
// intercept requests by handling event.request here
);
});
Простой сервисный работник, который просто проходит через запросы без изменений, выглядит так:
self.addEventListener('fetch', function(event) {
event.respondWith(
fetch(event.request)
);
});
Чтобы добавить параметр в тело запроса, я думаю, вам нужно сериализовать запрос, изменить этот сериализованный запрос, затем десериализовать его, чтобы воссоздать новый запрос, затем вызвать fetch(…)
с этим новым запросом.
Поэтому я думаю, что работник службы, который делает все, что хотелось бы (непроверенный):
self.addEventListener('fetch', function(event) {
event.respondWith(
fetchWithParamAddedToRequestBody(event.request)
);
});
function fetchWithParamAddedToRequestBody(request) {
serialize(request).then(function(serialized) {
// modify serialized.body here to add your request parameter
deserialize(serialized).then(function(request) {
return fetch(request);
});
}
function serialize(request) {
var headers = {};
for (var entry of request.headers.entries()) {
headers[entry[0]] = entry[1];
}
var serialized = {
url: request.url,
headers: headers,
method: request.method,
mode: request.mode,
credentials: request.credentials,
cache: request.cache,
redirect: request.redirect,
referrer: request.referrer
};
if (request.method !== 'GET' && request.method !== 'HEAD') {
return request.clone().text().then(function(body) {
serialized.body = body;
return Promise.resolve(serialized);
});
}
return Promise.resolve(serialized);
}
function deserialize(data) {
return Promise.resolve(new Request(data.url, data));
}
Примечание. На https://serviceworke.rs/request-deferrer_service-worker_doc.html, странице из книги поваренных услуг, я поднял эту страницу. serialize(…)
код / подход от - путем ответа на Как изменить заголовки запроса?- и на это стоит взглянуть, потому что в коде есть подробные аннотации, объясняющие, что все это делает
Попробуйте этот код:
(function(send) {
XMLHttpRequest.prototype.send = function(data) {
var _valuToAdd = $("input[name='valuToAdd']").val();
this.setRequestHeader('valueName', _valuToAdd);
send.call(this, data);
};
})(XMLHttpRequest.prototype.send);
// Override the open method of XMLHttpRequest to intercept all requests
var originalOpen = XMLHttpRequest.prototype.open;
XMLHttpRequest.prototype.open = function(method, url) {
console.log("Intercepted HTTP request: " + method + " " + url);
originalOpen.apply(this, arguments);
};