Service Worker 在 Firefox 上导致 CORS 问题
Service worker causing CORS issues on Firefox
我正在使用 service worker 推送通知,遵循 this 文章。 Chrome 一切正常,但在 Firefox (v.44.0.2) 上我遇到了一个奇怪的问题。
成功登录到我的应用程序后,我注册了 service worker,它除了等待推送事件外什么都不做;我看到它已正确注册(来自一些日志记录和 about:serviceworkers)。现在,如果我刷新页面 (CTRL+R),我的所有 POST 都有 CORS 问题(缺少 Access-Control-Allow-Origin header),因为这个 service worker并且用户被重定向到登录页面;从这里开始,所有 POST 都出于同样的原因不起作用。
相反,如果我登录,取消注册 service worker,然后 then 刷新,则完全没有问题。知道发生了什么事吗?同样,我的 service worker 只处理推送事件,没有缓存,没有完成其他处理,它在 Chrome.
上完美运行
这是我的 service worker 代码(SOME_API_URL 指向一个真实的 API,测试目的不需要它,因为问题发生在 service worker 注册之后,不需要推送事件)
self.addEventListener('push', function(event) {
// Since there is no payload data with the first version
// of push messages, we'll grab some data from
// an API and use it to populate a notification
event.waitUntil(
fetch(SOME_API_URL).then(function(response) {
if (response.status !== 200) {
// Either show a message to the user explaining the error
// or enter a generic message and handle the
// onnotificationclick event to direct the user to a web page
console.log('Looks like there was a problem. Status Code: ' + response.status);
throw new Error();
}
// Examine the text in the response
return response.json().then(function(data) {
if (data.error || !data.notification) {
console.error('The API returned an error.', data.error);
throw new Error();
}
var title = data.notification.title;
var message = data.notification.message;
var icon = data.notification.icon;
var notificationTag = data.notification.tag;
return self.registration.showNotification(title, {
body: message,
icon: icon,
tag: notificationTag
});
});
}).catch(function(err) {
console.error('Unable to retrieve data', err);
var title = 'An error occurred';
var message = 'We were unable to get the information for this push message';
var notificationTag = 'notification-error';
return self.registration.showNotification(title, {
body: message,
tag: notificationTag
});
})
);
});
self.addEventListener('notificationclick', function(event) {
console.log('On notification click: ', event.notification.tag);
// Android doesn't close the notification when you click on it
// See: http://crbug.com/463146
event.notification.close();
// This looks to see if the current is already open and
// focuses if it is
event.waitUntil(
clients.matchAll({
type: 'window'
})
.then(function(clientList) {
for (var i = 0; i < clientList.length; i++) {
var client = clientList[i];
if (client.url == '/' && 'focus' in client)
return client.focus();
}
if (clients.openWindow) {
return clients.openWindow('/');
}
})
);
});
Firefox 44 有 bug 1243453,这会导致 cross-origin 请求的 Origin header 在 service worker 不监听获取事件的情况下被丢弃。
该错误已在 Firefox 45 中修复,该版本将于 2016 年 3 月 8 日那一周(下周,截至撰写本文时)发布。同时,对于不立即升级到最新 Firefox 版本的用户,您可以通过将此代码添加到服务工作者来解决此问题:
addEventListener('fetch', function(evt) {
evt.respondWith(fetch(evt.request));
});
我正在使用 service worker 推送通知,遵循 this 文章。 Chrome 一切正常,但在 Firefox (v.44.0.2) 上我遇到了一个奇怪的问题。 成功登录到我的应用程序后,我注册了 service worker,它除了等待推送事件外什么都不做;我看到它已正确注册(来自一些日志记录和 about:serviceworkers)。现在,如果我刷新页面 (CTRL+R),我的所有 POST 都有 CORS 问题(缺少 Access-Control-Allow-Origin header),因为这个 service worker并且用户被重定向到登录页面;从这里开始,所有 POST 都出于同样的原因不起作用。 相反,如果我登录,取消注册 service worker,然后 then 刷新,则完全没有问题。知道发生了什么事吗?同样,我的 service worker 只处理推送事件,没有缓存,没有完成其他处理,它在 Chrome.
上完美运行这是我的 service worker 代码(SOME_API_URL 指向一个真实的 API,测试目的不需要它,因为问题发生在 service worker 注册之后,不需要推送事件)
self.addEventListener('push', function(event) {
// Since there is no payload data with the first version
// of push messages, we'll grab some data from
// an API and use it to populate a notification
event.waitUntil(
fetch(SOME_API_URL).then(function(response) {
if (response.status !== 200) {
// Either show a message to the user explaining the error
// or enter a generic message and handle the
// onnotificationclick event to direct the user to a web page
console.log('Looks like there was a problem. Status Code: ' + response.status);
throw new Error();
}
// Examine the text in the response
return response.json().then(function(data) {
if (data.error || !data.notification) {
console.error('The API returned an error.', data.error);
throw new Error();
}
var title = data.notification.title;
var message = data.notification.message;
var icon = data.notification.icon;
var notificationTag = data.notification.tag;
return self.registration.showNotification(title, {
body: message,
icon: icon,
tag: notificationTag
});
});
}).catch(function(err) {
console.error('Unable to retrieve data', err);
var title = 'An error occurred';
var message = 'We were unable to get the information for this push message';
var notificationTag = 'notification-error';
return self.registration.showNotification(title, {
body: message,
tag: notificationTag
});
})
);
});
self.addEventListener('notificationclick', function(event) {
console.log('On notification click: ', event.notification.tag);
// Android doesn't close the notification when you click on it
// See: http://crbug.com/463146
event.notification.close();
// This looks to see if the current is already open and
// focuses if it is
event.waitUntil(
clients.matchAll({
type: 'window'
})
.then(function(clientList) {
for (var i = 0; i < clientList.length; i++) {
var client = clientList[i];
if (client.url == '/' && 'focus' in client)
return client.focus();
}
if (clients.openWindow) {
return clients.openWindow('/');
}
})
);
});
Firefox 44 有 bug 1243453,这会导致 cross-origin 请求的 Origin header 在 service worker 不监听获取事件的情况下被丢弃。
该错误已在 Firefox 45 中修复,该版本将于 2016 年 3 月 8 日那一周(下周,截至撰写本文时)发布。同时,对于不立即升级到最新 Firefox 版本的用户,您可以通过将此代码添加到服务工作者来解决此问题:
addEventListener('fetch', function(evt) {
evt.respondWith(fetch(evt.request));
});