Zoeken op website

typescript - Geen toegang tot de variabele vóór initialisatie in getServerSideProps NextJS


Ik werk met Firebase en initialiseert de API's en functies om de gegevens die ik nodig heb op te halen in firebase.tsx en importeer ze daarna in mijn pages/index.tsx-bestand maar kan de exports niet openen na de initialisatie van de Firebase-app

services/firebase.tsx:

import firebase, { FirebaseOptions } from 'firebase/app'
import { getAuth } from 'firebase/auth';
import { collection, doc, setDoc, getFirestore, query, where, getDocs, orderBy } from "firebase/firestore";
import { getStorage } from 'firebase/storage';
import { getAnalytics } from "firebase/analytics";

import config from '../config';

import Blog, { blogConverter } from "../models/Blog";

export const yo = 'yo'

if (!firebase.getApps().length) {
    firebase.initializeApp(config.firebaseConfig as FirebaseOptions);
}

export const auth = getAuth();
export const firestore = getFirestore();
export const storage = getStorage();
export const analytics = getAnalytics();

/**
 * Get all blogs from firebase
 * @returns {Promise<Blog[]>} A promise that resolves to an array of Blog objects
 */
export const getBlogs = async (): Promise<Blog[]> => {
    const q = query(
        collection(firestore, "blogs"),
        where("status", "==", "published"),
        where("publish_date", "<", new Date().toUTCString()),
        orderBy("publish_date", "desc")
    ).withConverter(blogConverter);

    const querySnapshot = await getDocs(q);
    if (querySnapshot.empty) return [];

    const allBlogs: Blog[] = querySnapshot.docs.map(doc => doc.data());
    return allBlogs;
}

pagina's/index.tsx

import type { NextPage } from 'next'
import Head from 'next/head'
import Image from 'next/image'
import styles from '../styles/Home.module.css'
import { GetServerSideProps } from 'next'
import { getBlogs, yo } from '../services/firebase'

import Link from 'next/link'

import Blog from '../models/Blog'

export const getServerSideProps: GetServerSideProps = async (context) => {
  console.log(yo)

  const blogs = await getBlogs()
  return {
    props: {
      blogs
    }
  }
}

interface Props {
  blogs: Blog[]
}

const Home: NextPage<Props> = ({ blogs }) => {
...
}

Wanneer ik export const yo='yo' na regel 15 verplaats, krijg ik een 'kan 'yo' niet openen voor initialisatie', maar waar het nu staat, krijg ik dat niet.

Het lijkt erop dat het initialiseren van Firebase de initialisatie van exports vertraagt tot daarna, maar ik heb andere mensen hetzelfde patroon zien volgen?

Wat mis ik?

Foutmelding

Antwoord #1

Firebase JavaScript SDK (≥ v 9.0) introduceert de nieuwe modulaire API en bevat ingrijpende wijzigingen. Als je versie 8 gebruikt, moet je je code bijwerken zodat deze nog steeds werkt met versie 9.0.0 en hoger. Hoewel het merendeel van de versie 9 SDK dezelfde patronen volgt als versie 8, is de organisatie van de code anders. Het is dus zeker geen probleem met de imports in versie 9, maar eerder een nieuwe manier van de imports te hebben.

Bijvoorbeeld, de point chaining van versie 8, zoals firebaseApp.auth(), wordt in versie 9 vervangen door één enkele getAuth()-functie die firebaseApp neemt en een Authentication-instance retourneert. Dit betekent dat webapplicaties die met versie 8 of eerder zijn gemaakt, moeten worden herzien om gebruik te kunnen maken van de modulaire benadering van versie 9. Firebase biedt compat-bibliotheken om die overgang in v9 te vergemakkelijken. Zoals je zei, moet je je imports bijwerken.

Van

Voor: versie 8

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

Naar

Na: versie 9 compatibel

// v9 compat packages are API compatible with v8 code
import firebase from 'firebase/compat/app';
import 'firebase/compat/auth';
import 'firebase/compat/firestore';
 

Je kunt je code ook herstructureren volgens de modulaire stijl, wat weer een beetje anders is dan de compat-versie. Dit alles is hier gedocumenteerd. Ga erdoorheen om een duidelijk begrip van de verschillen te krijgen.

Antwoord #2

Ook, gelieve hieronder te worden geïnformeerd zoals hier vermeld.

Houd er rekening mee: de compatbibliotheken zijn een tijdelijke oplossing die volledig zal worden verwijderd in een toekomstige grote SDK-versie (zoals versie 10 of versie 11). Je uiteindelijke doel is om compatcode te verwijderen en alleen versie 9-modulaire code in je app te behouden.

Dus, "compat" is slechts een tijdelijke oplossing om je v8-code werkend te krijgen met v9 zonder al te veel herwerking. Uiteindelijk moet je de code refactoren naar een modulaire stijl.