我已经创建了一个项目与下一步,我试图使用Firebase的通知服务。问题是,我找到了这篇文章,但我得到了一个关于getMessaging()方法的错误。
我package.json
{
"name": "firebase-noti",
"version": "0.1.0",
"private": true,
"scripts": {
"dev": "next dev",
"build": "next build",
"start": "next start",
"lint": "next lint"
},
"dependencies": {
"bootstrap": "^5.1.3",
"firebase": "^9.9.0",
"next": "12.2.2",
"react": "18.2.0",
"react-bootstrap": "^2.4.0",
"react-dom": "18.2.0"
},
"devDependencies": {
"eslint": "8.20.0",
"eslint-config-next": "12.2.2"
}
}
我firebase.js
import { initializeApp } from "firebase/app";
import { getMessaging, getToken, onMessage } from "firebase/messaging";
var firebaseConfig = {
apiKey: "AIzaSyAjWIJe9AaL6fDZVn9tRajF-BUexEPFZyA",
authDomain: "react-notif-40228.firebaseapp.com",
projectId: "react-notif-40228",
storageBucket: "react-notif-40228.appspot.com",
messagingSenderId: "790644971731",
appId: "1:790644971731:web:dc0c5d007d2b961af3dc26",
};
const firebaseApp = initializeApp(firebaseConfig);
const messaging = getMessaging(firebaseApp);
export const fetchToken = (setTokenFound) => {
return getToken(messaging, { vapidKey: "BHGPr3pJQSflJAJtTIVXbmcEXlPV_HP29TZQRcqrGCN10gKIa-ojIJmtvM9kQGcsNKsWIA6ezKFG8Bd6LTjaVc0" })
.then((currentToken) => {
if (currentToken) {
console.log("current token for client: ", currentToken);
setTokenFound(true);
// Track the token -> client mapping, by sending to backend server
// show on the UI that permission is secured
} else {
console.log(
"No registration token available. Request permission to generate one."
);
setTokenFound(false);
// shows on the UI that permission is required
}
})
.catch((err) => {
console.log("An error occurred while retrieving token. ", err);
// catch error while creating client token
});
};
我index.js
import styles from "../styles/Home.module.css";
import { useState } from "react";
import "bootstrap/dist/css/bootstrap.min.css";
import { fetchToken } from "./firebase";
export default function Home() {
const [show, setShow] = useState(false);
const [isTokenFound, setTokenFound] = useState(false);
fetchToken(setTokenFound);
return (
<div className={styles.container}>
<main className={styles.main}>
{isTokenFound && <>Notification permission enabled 👍🏻</>}
{!isTokenFound && <>Need notification permission ❗️</>}
</main>
</div>
);
}
代码总是抛出这个错误Service messaging is not available
但当我console。log firebaseApp是ok
FirebaseAppImpl {
_isDeleted: false,
_options: {
apiKey: 'AIzaSyAjWIJe9AaL6fDZVn9tRajF-BUexEPFZyA',
authDomain: 'react-notif-40228.firebaseapp.com',
projectId: 'react-notif-40228',
storageBucket: 'react-notif-40228.appspot.com',
messagingSenderId: '790644971731',
appId: '1:790644971731:web:dc0c5d007d2b961af3dc26'
},
_config: { name: '[DEFAULT]', automaticDataCollectionEnabled: false },
_name: '[DEFAULT]',
_automaticDataCollectionEnabled: false,
_container: ComponentContainer {
name: '[DEFAULT]',
providers: Map(8) {
'platform-logger' => [Provider],
'heartbeat' => [Provider],
'fire-core-version' => [Provider],
'fire-core-esm2017-version' => [Provider],
'fire-js-version' => [Provider],
'fire-js-all-app-version' => [Provider],
'app' => [Provider],
'messaging' => [Provider]
}
}
}
我很失落,我不知道它是否关于下一个或firebase问题,因为这段代码在React项目上工作。
所以我也不是专家,但是getMessaging在服务器端调用时会给出错误,因为它需要访问"窗口";对象。如果不正确,请纠正我的术语
我创建了一个单独的函数,我从客户端的布局文件中调用它,它运行得很好。
const firebaseCloudMessaging = {
init: async () => {
try {
const messaging = getMessaging(app)
// const tokenInLocalForage = await localforage.getItem('fcm_token')
// if (tokenInLocalForage !== null) {
// return tokenInLocalForage
// }
const status = await Notification.requestPermission()
if (status && status === 'granted') {
const fcmToken = await getToken(messaging, { vapidKey: process.env.NEXT_PUBLIC_FIREBASE_CLOUD_MESSGING_PUBLIC_KEY })
if (fcmToken) {
localforage.setItem('fcm_token', fcmToken)
return fcmToken
}
}
} catch (err) {
console.log(err)
return null
}
}
}
差不多。