Apollo-Offline proporciona una interfaz de red personalizada y un potenciador de tienda Redux que permite el desarrollo fluido de aplicaciones sin conexión utilizando el cliente Apollo GraphQL.
Apollo-Offline está construido sobre Redux-Offline (y por lo tanto hereda todas sus características).
Su objetivo es hacer uso de las características fuera de línea (-ish) existentes de Apollo (por ejemplo, almacenamiento en caché integrado y respuestas optimistas para mutaciones). Esto significa que al migrar, su código no tendrá que cambiar mucho (siempre que ya esté usando estas funciones).
Con Apollo-Offline, el código de sus consultas y mutaciones se ve exactamente como se vería sin él.
Hay una excepción a esto: la función de "búsqueda optimista" .
Lo que hace la "búsqueda optimista" es intentar leer primero la respuesta de una consulta desde el caché, pero si (¡y sólo si!) hay una conexión de red disponible obtendrá la respuesta del servidor en segundo plano y la escribirá en el caché (en ese momento por ejemplo, los componentes empaquetados de React se actualizarán por segunda vez).
Básicamente, esto significa que las consultas de su interfaz de usuario siempre funcionarán si los datos solicitados están disponibles en el caché local y siempre mantendrán los datos almacenados en caché consistentes con los datos de su servidor si se puede acceder a ellos.
Nota: En mi opinión, esto es lo que debería hacer fetchPolicy: 'cache-and-network'
(pero no lo hace: genera un error si no se puede acceder al servidor).
Para habilitarlo, agregue un campo __offline__
con un valor verdadero a las variables de consulta de esa consulta específica (es decir, variables: { __offline__: true }
).
Para obtener más instrucciones, consulte los ejemplos siguientes.
usando hilo
yarn add apollo-offline
o npm
npm install --save apollo-offline
Apollo-Offline también requiere que tengas instaladas las siguientes dependencias de pares:
apollo-client
redux
import { ApolloClient , createNetworkInterface } from 'apollo-client' ;
import { applyMiddleware , combineReducers , compose , createStore } from 'redux' ;
import config from '@redux-offline/redux-offline/lib/defaults' ;
import offline from 'apollo-offline' ;
// 1. Wrap your network interface
const { enhancer , networkInterface } = offline (
createNetworkInterface ( {
uri : `http://localhost` ,
} ) ,
) ;
// 2. Create your Apollo client
const client = new ApolloClient ( {
/* Your Apollo configuration here... */
networkInterface ,
} ) ;
// 3. Pass the client to the offline network interface
// (Optional, but needed for the optimistic fetch feature)
networkInterface . setClient ( client ) ;
// 4. Create your redux store
export const store = createStore (
combineReducers ( {
apollo : client . reducer ( ) ,
} ) ,
undefined ,
compose (
applyMiddleware ( client . middleware ( ) ) ,
// Apply offline store enhancer
// (You can pass your own redux-offline config, but the default one is a good starting point)
enhancer ( config ) ,
) ,
) ;
Nota: Una vez configurado, apollo-offline intercepta todas las consultas/mutaciones para permitir su comportamiento fluido sin conexión.
Si desea excluir selectivamente algunas consultas/mutaciones de esto, puede volver al comportamiento predeterminado de Apollo agregando un campo __online__
con un valor verdadero a las variables de consulta de esa consulta/mutación específica (es decir, variables: { __online__: true }
) .
/* Setup goes here... */
// Queries
client . query ( { query : /* Your query here */ } ) ;
// - Using optimistic fetch feature
client . query ( {
fetchPolicy : 'network-only' ,
query : /* Your query here */ ,
variables : {
__offline__ : true , // Enable optimistic fetch
} ,
} ) ;
// Mutations
client . mutate ( {
mutation : /* Your mutation here */ ,
optimisticResponse : /* Your optimistic response here */ ,
update : /* Your update resolver here */ ,
} ) ;
En su punto de entrada:
/* Setup goes here... */
import { ApolloProvider } from 'react-apollo' ;
import { connect } from 'react-redux' ;
import App from './App' ; // Your main application component
// Component to postpone render until after Redux state has been rehydrated
const Rehydrated = connect ( ( { rehydrated } ) => ( { rehydrated } ) )
( ( props ) => props . rehydrated ? props . children : props . loading ) ;
const Loading = ( ) => < div > Loading... </ div > ;
ReactDOM . render (
< ApolloProvider client = { client } store = { store } >
< Rehydrated loading = { < Loading /> } >
< App />
</ Rehydrated >
</ ApolloProvider > ,
document . getElementById ( 'root' ) ,
) ;
Al envolver sus componentes:
import React from 'react' ;
import { graphql } from 'react-apollo' ;
// Queries
const wrappedComponent = graphql ( /* Your query here */ ) ( /* Your component here */ ) ;
// - Using optimistic fetch feature
const wrappedComponent = graphql (
/* Your query here */ ,
{
options : {
fetchPolicy : 'network-only' ,
variables : {
__offline__ : true , // Enable optimistic fetch
} ,
} ,
} ,
) ( /* Your component here */ ) ;
// Mutations (you will want to provide an optimistic response when executing them)
const wrappedComponent = graphql (
/* Your mutation here */ ,
{
options : {
update : /* Your update resolver here */ ,
} ,
} ,
) ( /* Your component here */ ) ;
Esto es lo que haces después de haber clonado el repositorio:
yarn / npm install
(Instalar dependencias)
Ejecutar TSLint
npm run lint
Intente corregir automáticamente los errores de linting
npm run lint:fix
Ejecute las pruebas unitarias de Jest usando
npm test
npm run test:coverage
Las pruebas se definen en el mismo directorio en el que se encuentra el módulo. Se especifican en los archivos '[módulo].test.js'.
Para construir el proyecto, ejecute
npm run build
Esto guarda el código listo para producción en 'dist/'.