【问题标题】:Where do I initialize Firebase app in React application?在 React 应用程序中,我在哪里初始化 Firebase 应用程序?
【发布时间】:2018-07-07 14:30:48
【问题描述】:

我正在尝试将 Firebase 集成到我的 React 应用程序中,在查看了各种教程之后,我似乎无法就 Firebase 初始化代码firebase.initializeApp(config) 的放置位置达成共识。

我的应用结构是这样的:

- app.js
- components
   |___Index.jsx
   |___Layout.jsx
   |___PageContent.jsx

每个文件如下所示

app.js

所有快速设置都使用服务器端渲染

Index.jsx

import React from 'react';
import Layout from './Layout.jsx';
import PageContent from './PageContent.jsx';
import './global.css';

class Index extends React.Component {
  render() {
    return (
        <Layout title={this.props.title}>
            <PageContent />
        </Layout>
    );
  }
}

export default Index;

PageContent.jsx

import React from 'react';
import ReactDOM from 'react-dom';
import LandingPage from './components/Landing_Page/Landing.jsx';

class PageContent extends React.Component {
    render() {
        return (
            <LandingPage />
        );
    }
}

if (typeof window !== 'undefined') {
    ReactDOM.render(     
        <PageContent />,
        document.getElementById('root')        
    );
}

export default PageContent;

我需要确保 Firebase 在我网站的每个页面中都可用。现在它是一个单页应用程序,但最终我会添加更多。

谁能帮助我了解我可以将数据库初始化代码放在哪里,以便在任何地方应用它?

【问题讨论】:

  • 也许在 ReactDOM.render 调用之前尝试在 PageContent.jsx 文件中

标签: javascript reactjs firebase


【解决方案1】:

创建名为 firebase.js 的文件

import firebase from "firebase/app";
import "firebase/auth";
import "firebase/firestore";

const firebaseConfig = {
  apiKey: 'AIzaXXXXXXXXXXXXXXXXXXXXXXX',
  authDomain: 'test-XXXX.firebaseapp.com',
  databaseURL: 'https://test-db.firebaseio.com',
  projectId: 'test-XXXX',
  storageBucket: 'test-bucket.appspot.com',
  messagingSenderId: 'XXXXXXX',
  appId: "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
};


firebase.initializeApp(firebaseConfig);
export const firebaseAuth = firebase.auth();
export const firestore = firebase.firestore()

然后按如下方式使用:

import { firebaseAuth } from 'firebase'
import SigninForm from 'signin.js'

const ModalSignIn = props => {

  const [email, setEmail] = useState()
  const [password, setPassword] = useState()

  const handleSubmit = e => {
    e.preventDefault()
    firebaseAuth
      .signInWithEmailAndPassword(email, password)
      .then(res => {
        console.log(res.user)
      })
      .catch(err => {
        const { code, message } = err
        console.log(code, message)
      })
  }

  return (<SigninForm/>)

【讨论】:

    【解决方案2】:

    我就是这样做的

    app.js 旁边创建文件Firebase.js 并放入您的初始化代码

    Firebase.js 文件

    import * as firebase from 'firebase';
    
    let config = {
        apiKey: "XXXXXXX",
        authDomain: "XXXXX",
        databaseURL: "XXXXX",
        projectId: "XXXXX",
        storageBucket: "XXXX",
        messagingSenderId: "XXXX"
    };
    firebase.initializeApp(config);
    
    export default firebase;
    

    然后将Firebase.js文件导入到每个你想使用的地方,例如

    import React from 'react';    
    import firebase from './../Firebase.js'     // <------  import firebase
    
    class Test extends React.Component {
    
        componentDidMount(){
            firebase.database().ref().child("X").on('value' , {...});
        }
    
        render() {
            return (
                <h1>Hello</h1>
            );
        }
    }
    
    export default Test;
    

    【讨论】:

    • 这不会多次初始化firebase吗?
    • 可以像单例export default !firebase.apps.length ? firebase.initializeApp(config) : firebase.app();一样进行初始化,避免多次初始化
    • 这似乎是一个不错的选择,但只考虑@NitishDhar 的最后一条评论以避免多个firebase 应用程序初始化。
    • 有人介意解释上述评论吗? ES6 模块不是只评估一次吗?因此,如果没有建议的单例解决方案,firebase 应用程序只会被初始化一次?
    • @NitishDhar 的建议是不必要的。 ES6 模块是单例,在运行时开始时为每个文件创建一个实例。因此initialiseApp 只会被调用一次。快乐的时光!我创建了一个简单的沙箱来显示:codesandbox.io/s/sharp-feather-9pf04?file=/src/index.js
    【解决方案3】:

    看来您想要的是 firebase 可以在全球范围内对您的反应组件可用

    在使用redux之前同样的问题,react组件是如何消耗全局状态树的?全局变量?来吧,我们会知道全局变量是邪恶的。反应道具?看起来很反应,但是从根到叶子组件传递道具并不有趣。

    Context API 前来救援。你只需要像 redux/react-router 那样做 react 的 firebase 绑定。

    假设您不想重新发明轮子,

    当然,您也可以通过刚才提到的 react 上下文构建自己的 react firebase 绑定。

    【讨论】:

    • 使用 Context API 非常有用,但是,我发现这给我带来了一个问题:我需要在我使用 Redux-thunk 的 actions.js 文件中访问 Firebase.auth 实例让用户登录并发送操作以使用 UserID 更新我的 Redux 存储。因为 Context Provider 将数据传递给一个封装的组件,所以这是不可能实现的,因为 actions.js 文件不是一个组件。我找不到任何直接访问 Provider 的方法。
    猜你喜欢
    • 2019-04-10
    • 1970-01-01
    • 1970-01-01
    • 2019-09-20
    • 1970-01-01
    • 1970-01-01
    • 2011-06-18
    • 1970-01-01
    • 2012-11-23
    相关资源
    最近更新 更多