getMessaging 失败 - 未捕获语法错误:无法在模块外部使用 import 语句(位于 firebase-messaging-sw.js:1:1)

twe*_*ypi 5 javascript firebase typescript service-worker next.js

我正在尝试将 firebase 消息传递集成到我的 NextJS Web 应用程序中,但收到的错误可能看起来像是来自服务器端。为了让注册在 _app.tsx 中工作,我执行以下操作:

  useEffect(() => {
    if ("serviceWorker" in navigator) {
      window.addEventListener("load", function () {
        const config = process.env.NEXT_PUBLIC_FIREBASE;
        navigator.serviceWorker.register("/firebase-messaging-sw.js?firebaseConfig=" + Buffer.from(config).toString('base64'), {
          type: 'module'
        }).then(
          function (registration) {
            console.log("Service Worker registration successful with scope: ", registration.scope);
          },
          function (err) {
            console.log("Service Worker registration failed: ", err);
          }
        );
      });
    }
  }, [])
Run Code Online (Sandbox Code Playgroud)

其中 NEXT_PUBLIC_FIREBASE 是 firebase 配置对象。

然后在 public/firebase-messaging-sw.js 中我有这个:

import { initializeApp } from "https://www.gstatic.com/firebasejs/9.8.1/firebase-app.js";
import { getMessaging } from "https://www.gstatic.com/firebasejs/9.8.1/firebase-messaging.js";

const swScriptUrl = new URL(self.location);

const base64Config = swScriptUrl.searchParams.get('firebaseConfig')
let decoded = atob(base64Config);

const firebaseConfig = JSON.parse(decoded);
const app = initializeApp(firebaseConfig);


// Retrieve an instance of Firebase Messaging so that it can handle background
const messaging = getMessaging(app);
Run Code Online (Sandbox Code Playgroud)

当调用 getMessaging 时,我收到此错误:

Uncaught SyntaxError: Cannot use import statement outside a module (at firebase-messaging-sw.js:1:1)
index.esm2017.js?f614:823 Uncaught (in promise) FirebaseError: Messaging: We are unable to register the default service worker. Failed to register a ServiceWorker for scope ('http://localhost:3000/firebase-cloud-messaging-push-scope') with script ('http://localhost:3000/firebase-messaging-sw.js'): ServiceWorker script evaluation failed (messaging/failed-service-worker-registration).
    at registerDefaultSw (index.esm2017.js?f614:823:1)
    at async updateSwReg (index.esm2017.js?f614:847:1)
    at async getToken$1 (index.esm2017.js?f614:910:1)
    at async FirebaseMessagingWeb.getToken (web.js?00d2:24:1)
registerDefaultSw @ index.esm2017.js?f614:823
Promise.then (async)
asyncGeneratorStep @ ios-notification.ts?89f7:2
_next @ ios-notification.ts?89f7:2
eval @ ios-notification.ts?89f7:2
eval @ ios-notification.ts?89f7:2
addListeners @ ios-notification.ts?89f7:4
eval @ notification-context.tsx?dccb:38
Promise.then (async)
registerForNotifications @ notification-context.tsx?dccb:37
registerForNotifications @ notification-context.tsx?dccb:62
onClick @ profile-box.tsx?a1b7:280
callCallback @ react-dom.development.js?ac89:4161
invokeGuardedCallbackDev @ react-dom.development.js?ac89:4210
invokeGuardedCallback @ react-dom.development.js?ac89:4274
invokeGuardedCallbackAndCatchFirstError @ react-dom.development.js?ac89:4288
executeDispatch @ react-dom.development.js?ac89:9038
processDispatchQueueItemsInOrder @ react-dom.development.js?ac89:9070
processDispatchQueue @ react-dom.development.js?ac89:9083
dispatchEventsForPlugins @ react-dom.development.js?ac89:9094
eval @ react-dom.development.js?ac89:9285
batchedUpdates$1 @ react-dom.development.js?ac89:26096
batchedUpdates @ react-dom.development.js?ac89:3988
dispatchEventForPluginEventSystem @ react-dom.development.js?ac89:9284
dispatchEventWithEnableCapturePhaseSelectiveHydrationWithoutDiscreteEventReplay @ react-dom.development.js?ac89:6462
dispatchEvent @ react-dom.development.js?ac89:6454
dispatchDiscreteEvent @ react-dom.development.js?ac89:6427
firebase-messaging-sw.js:1 Uncaught SyntaxError: Cannot use import statement outside a module (at firebase-messaging-sw.js:1:1)
Run Code Online (Sandbox Code Playgroud)

我已经检查了配置对象,它绝对是正确的,并将其发送给服务工作人员(也尝试仅复制配置但无济于事)。

尝试让它在本地和 https 服务器上工作但无济于事,我还尝试了 none 模块导入,它产生了相同的错误。

小智 3

同样的事情也发生在我身上,第一个是使用 importScripts ,第二个是降级到 8.0.0 并稍微更改函数调用。正如我在下面向您展示的:

   importScripts("https://www.gstatic.com/firebasejs/8.0.0/firebase-app.js");
   importScripts("https://www.gstatic.com/firebasejs/8.0.0/firebase-messaging.js");
    
    const swScriptUrl = new URL(self.location);
    
    const base64Config = swScriptUrl.searchParams.get('firebaseConfig')
    let decoded = atob(base64Config);
    
    const firebaseConfig = JSON.parse(decoded);
    const app = firebase.initializeApp(firebaseConfig);
    
    
    // Retrieve an instance of Firebase Messaging so that it can handle background
    const messaging = firebase.messaging();
Run Code Online (Sandbox Code Playgroud)