Revere Cre stellt ein! Möchten Sie an der Speidekette von Frontend arbeiten?
Wenden Sie sich an [email protected], um weitere Informationen zu erhalten.
Dokumentation | Diskussion | Neueste Veröffentlichungen
relay-nextjs ist der beste Weg, Relay und Next.js im selben Projekt zu verwenden! Es unterstützt inkrementelle Migration , ist spannend und wird von großen Unternehmen in Produktion betrieben .
relay-nextjs -Seitenkomponenten, eine GraphQL-Abfrage und einige Helfermethoden, um das Abrufen von Daten automatisch mithilfe des Relays anzuschließen. Bei der Erstladung wird eine Relaisumgebung erstellt, die Daten werden serverseitig abgerufen, die Seite wird gerendert und der resultierende Zustand wird als Skript-Tag serialisiert. Auf dem Start im Client werden mit diesem serialisierten Zustand eine neue Relay -Umgebung und eine vorinstallierte Abfrage erstellt. Die Daten werden mit der clientseitigen Relaisumgebung für nachfolgende Navigationen abgerufen.
HINWEIS: relay-nextjs unterstützt derzeit den NextJS 13 App-Router im Moment nicht.
Installieren Sie mit NPM oder Ihrem anderen bevorzugten Paketmanager:
$ npm install relay-nextjs relay-nextjs müssen in _app so konfiguriert werden, dass sie das Routing ordnungsgemäß abfangen und verarbeitet.
Grundlegende Informationen zur Relay -Umgebung finden Sie in den Relay -Dokumenten.
relay-nextjs wurde sowohl für clientseitige als auch mit serverseitigem Rendering entwickelt. Daher muss es in der Lage sein, entweder eine clientseitige oder serverseitige Relay-Umgebung zu verwenden. Die Bibliothek weiß, wie man mit welcher Umgebung umgeht, aber wir müssen sagen, wie diese Umgebungen erstellt werden. Dazu werden wir zwei Funktionen definieren: getClientEnvironment und createServerEnvironment . Beachten Sie die Unterscheidung-Auf dem Client wird jemals eine Umgebung erstellt, da es nur eine App gibt. Auf dem Server müssen wir jedoch eine Umgebung pro Render erstellen, um sicherzustellen, dass der Cache nicht zwischen Anfragen geteilt wird.
Zuerst definieren wir getClientEnvironment :
// lib/client_environment.ts
import { Environment , Network , Store , RecordSource } from 'relay-runtime' ;
export function createClientNetwork ( ) {
return Network . create ( async ( params , variables ) => {
const response = await fetch ( '/api/graphql' , {
method : 'POST' ,
credentials : 'include' ,
headers : {
'Content-Type' : 'application/json' ,
} ,
body : JSON . stringify ( {
query : params . text ,
variables ,
} ) ,
} ) ;
const json = await response . text ( ) ;
return JSON . parse ( json ) ;
} ) ;
}
let clientEnv : Environment | undefined ;
export function getClientEnvironment ( ) {
if ( typeof window === 'undefined' ) return null ;
if ( clientEnv == null ) {
clientEnv = new Environment ( {
network : createClientNetwork ( ) ,
store : new Store ( new RecordSource ( ) ) ,
isServer : false ,
} ) ;
}
return clientEnv ;
} und dann createServerEnvironment :
import { graphql } from 'graphql' ;
import { GraphQLResponse , Network } from 'relay-runtime' ;
import { schema } from 'lib/schema' ;
export function createServerNetwork ( ) {
return Network . create ( async ( text , variables ) => {
const context = {
token ,
// More context variables here
} ;
const results = await graphql ( {
schema ,
source : text . text ! ,
variableValues : variables ,
contextValue : context ,
} ) ;
return JSON . parse ( JSON . stringify ( results ) ) as GraphQLResponse ;
} ) ;
}
export function createServerEnvironment ( ) {
return new Environment ( {
network : createServerNetwork ( ) ,
store : new Store ( new RecordSource ( ) ) ,
isServer : true ,
} ) ;
}Beachten Sie in der Beispielserver -Umgebung, die wir mit einem lokalen Schema ausführen, aber Sie können auch von einer Remote -API abrufen.
_app // pages/_app.tsx
import { RelayEnvironmentProvider } from 'react-relay/hooks' ;
import { useRelayNextjs } from 'relay-nextjs/app' ;
import { getClientEnvironment } from '../lib/client_environment' ;
function MyApp ( { Component , pageProps } : AppProps ) {
const { env , ... relayProps } = useRelayNextjs ( pageProps , {
createClientEnvironment : ( ) => getClientSideEnvironment ( ) ! ,
} ) ;
return (
< >
< RelayEnvironmentProvider environment = { env } >
< Component { ... pageProps } { ... relayProps } />
</ RelayEnvironmentProvider >
</ >
) ;
}
export default MyApp ; // src/pages/user/[uuid].tsx
import { withRelay , RelayProps } from 'relay-nextjs' ;
import { graphql , usePreloadedQuery } from 'react-relay/hooks' ;
// The $uuid variable is injected automatically from the route.
const ProfileQuery = graphql `
query profile_ProfileQuery($uuid: ID!) {
user(id: $uuid) {
id
firstName
lastName
}
}
` ;
function UserProfile ( { preloadedQuery } : RelayProps < { } , profile_ProfileQuery > ) {
const query = usePreloadedQuery ( ProfileQuery , preloadedQuery ) ;
return (
< div >
Hello { query . user . firstName } { query . user . lastName }
</ div >
) ;
}
function Loading ( ) {
return < div > Loading... </ div > ;
}
export default withRelay ( UserProfile , UserProfileQuery , {
// Fallback to render while the page is loading.
// This property is optional.
fallback : < Loading /> ,
// Create a Relay environment on the client-side.
// Note: This function must always return the same value.
createClientEnvironment : ( ) => getClientEnvironment ( ) ! ,
// variablesFromContext allows you to declare and customize variables for the graphql query.
// by default variablesFromContext is ctx.query
variablesFromContext : ( ctx : NextRouter | NextPageContext ) => ( { ... ctx . query , otherVariable : true } ) ,
// Gets server side props for the page.
serverSideProps : async ( ctx ) => {
// This is an example of getting an auth token from the request context.
// If you don't need to authenticate users this can be removed and return an
// empty object instead.
const { getTokenFromCtx } = await import ( 'lib/server/auth' ) ;
const token = await getTokenFromCtx ( ctx ) ;
if ( token == null ) {
return {
redirect : { destination : '/login' , permanent : false } ,
} ;
}
return { token } ;
} ,
// Server-side props can be accessed as the second argument
// to this function.
createServerEnvironment : async (
ctx ,
// The object returned from serverSideProps. If you don't need a token
// you can remove this argument.
{ token } : { token : string }
) => {
const { createServerEnvironment } = await import ( 'lib/server_environment' ) ;
return createServerEnvironment ( token ) ;
} ,
} ) ;