got something ~working with a hacks on reactrouter:react-router-ssr

This commit is contained in:
xavcz 2016-11-16 16:17:12 +01:00
parent 620572887d
commit f5ef406bf7
9 changed files with 64 additions and 65 deletions

View file

@ -105,7 +105,7 @@ rate-limit@1.0.6
react-meteor-data@0.2.9
reactive-dict@1.1.8
reactive-var@1.0.11
reactrouter:react-router-ssr@3.1.5
reactrouter:react-router-ssr@3.1.6
reload@1.1.11
retry@1.0.9
routepolicy@1.0.12

View file

@ -30,6 +30,7 @@
"immutability-helper": "^2.0.0",
"intl": "^1.2.4",
"intl-locales-supported": "^1.0.0",
"isomorphic-fetch": "^2.2.1",
"juice": "^1.11.0",
"mailchimp": "^1.1.6",
"marked": "^0.3.5",

@ -0,0 +1 @@
Subproject commit 98bc33ecb370f6fbd43faafc01ff4a042180e87a

View file

@ -4,16 +4,17 @@
// -------
// start of main-client from apollostack/meteor-integration
import ApolloClient, { createBatchingNetworkInterface } from 'apollo-client';
import ApolloClient, { createNetworkInterface } from 'apollo-client';
import { Accounts } from 'meteor/accounts-base';
import { _ } from 'meteor/underscore';
import 'isomorphic-fetch';
import Cookie from 'react-cookie';
import Telescope from 'meteor/nova:lib';
const defaultNetworkInterfaceConfig = {
path: '/graphql',
options: {},
useMeteorAccounts: true
};
export const createMeteorNetworkInterface = (givenConfig) => {
@ -27,38 +28,40 @@ export const createMeteorNetworkInterface = (givenConfig) => {
// For SSR
const url = Meteor.absoluteUrl(path);
const networkInterface = createBatchingNetworkInterface({
const networkInterface = createNetworkInterface({
uri: url,
batchInterval: 10
opts: {
credentials: 'same-origin',
}
});
if (config.useMeteorAccounts) {
networkInterface.use([{
applyMiddleware(request, next) {
const currentUserToken = Accounts._storedLoginToken();
if (!currentUserToken) {
next();
return;
}
if (!request.options.headers) {
request.options.headers = new Headers();
}
request.options.headers.Authorization = currentUserToken;
networkInterface.use([{
applyMiddleware(request, next) {
console.log('from router token', config.cookieLoginToken);
console.log('from accounts token', Meteor.isClient && Accounts._storedLoginToken());
const currentUserToken = config.cookieLoginToken ? config.cookieLoginToken : Meteor.isClient ? Accounts._storedLoginToken() : null;
if (!currentUserToken) {
next();
},
}]);
}
return;
}
if (!request.options.headers) {
request.options.headers = new Headers();
}
request.options.headers.Authorization = currentUserToken;
next();
},
}]);
return networkInterface;
};
export const meteorClientConfig = (networkInterfaceConfig) => {
return {
ssrMode: true,
ssrMode: Meteor.isServer,
networkInterface: createMeteorNetworkInterface(networkInterfaceConfig),
// Default to using Mongo _id, must use _id for queries.

View file

@ -2,7 +2,7 @@ import Telescope from 'meteor/nova:lib';
import { makeExecutableSchema } from 'graphql-tools';
import { client } from './client.js';
import { meteorClientConfig, client } from './client.js';
import { createApolloServer } from './server.js';
import typeDefs from './schema';
@ -16,4 +16,4 @@ createApolloServer({
schema,
});
export { client };
export { meteorClientConfig, client };

View file

@ -18,6 +18,7 @@ const UsersEditForm = (props, context) => {
} else {
const user = props.data.user;
return (
<Telescope.components.CanDo
action="users.edit"

View file

@ -27,7 +27,8 @@ const UsersProfileCheckModal = ({show, router, currentUser}, context) => {
collection={ Users }
document={ currentUser }
mutationName="usersEdit"
resultQuery={Users.fragments.full}
fragment={Users.fragments.full}
noRemoveMutation={true}
successCallback={ (user) => Telescope.callbacks.runAsync("users.profileCompleted.async", user) }
fields={ requiredFields }
/>
@ -40,6 +41,7 @@ const UsersProfileCheckModal = ({show, router, currentUser}, context) => {
};
const UsersProfileCheck = ({currentUser}, context) => {
debugger
return currentUser ? <UsersProfileCheckModal currentUser={currentUser} show={!Users.hasCompletedProfile(currentUser)}/> : null;
};

View file

@ -7,13 +7,14 @@ import Events from "meteor/nova:events";
import Helmet from 'react-helmet';
import Cookie from 'react-cookie';
import ReactDOM from 'react-dom';
import ApolloClient from 'apollo-client';
import { ApolloProvider } from 'react-apollo';
import { client } from 'meteor/nova:apollo';
import {getDataFromTree} from "react-apollo/server";
import { meteorClientConfig } from 'meteor/nova:apollo';
import { configureStore } from "./store.js";
Meteor.startup(() => {
Meteor.startup(function initNovaRoutesAndApollo() {
/*
Routes definition
@ -46,27 +47,21 @@ Meteor.startup(() => {
let history;
let initialState;
let store;
let client;
// Use history hook to get a reference to the history object
const historyHook = newHistory => history = newHistory;
// Pass the state of the store as the object to be dehydrated server side
const dehydrateHook = () => {
// console.log('store get state', store.getState());
return store.getState();
}
// Take the rehydrated state and use it as the initial state client side
const rehydrateHook = state => {
// console.log('rehydrated state', state);
initialState = state
};
const clientOptions = {
historyHook,
rehydrateHook,
wrapperHook(app) {
store = configureStore(initialState, history);
rehydrateHook: state => {
console.log('rehydrated state', state);
initialState = state
},
wrapperHook(app, loginToken) {
console.log('wrapper hook initial state', initialState);
client = new ApolloClient(meteorClientConfig({cookieLoginToken: loginToken}));
store = configureStore(client, initialState, history);
return <ApolloProvider store={store} client={client}>{app}</ApolloProvider>
},
props: {
@ -79,23 +74,22 @@ Meteor.startup(() => {
};
const serverOptions = {
historyHook,
htmlHook: (html) => {
const head = Helmet.rewind();
return html.replace('<head>', '<head>'+ head.title + head.meta + head.link);
},
preRender: (req, res) => {
Cookie.plugToRequest(req, res);
preRender: (req, res, app) => {
//Cookie.plugToRequest(req, res);
//console.log('preRender hook', app);
// console.log(req.cookies);
return Promise.await(getDataFromTree(app));
},
historyHook,
dehydrateHook,
// see https://github.com/thereactivestack/meteor-react-router-ssr/blob/9762f12c5d5512c5cfee8663a29428f7e4c141f8/lib/server.jsx#L241-L257
// note: can't get it working well
// fetchDataHook: (components) => {
// console.log(components[0]); // = Apollo(AppContainer)
// // console.log('this is where ssr & apollo should interact -> fetch data')
// return [components[0].fetchData({} /* should be props .. how to get them?*/, {client})];
// },
fetchDataHook: (components) => components,
dehydrateHook: () => {
console.log(client.store.getState());
return client.store.getState();
},
// fetchDataHook: (components) => components,
};
ReactRouterSSR.Run(AppRoutes, clientOptions, serverOptions);

View file

@ -1,20 +1,17 @@
import { createStore, combineReducers, applyMiddleware, compose } from 'redux';
import ApolloClient from 'apollo-client';
import { routerMiddleware } from 'react-router-redux'
// import { routerMiddleware } from 'react-router-redux'
import Telescope from 'meteor/nova:lib';
import { client } from 'meteor/nova:apollo';
// import { client } from 'meteor/nova:apollo';
const rootReducer = combineReducers({...Telescope.reducers, apollo: client.reducer()});
const configureStore = (initialState = {}, history) => createStore(
const configureStore = (client, initialState = {}, history) => createStore(
// reducers
rootReducer,
combineReducers({...Telescope.reducers, apollo: client.reducer()}),
//initial state
initialState,
// middlewares
compose(
applyMiddleware(client.middleware(), routerMiddleware(history)),
applyMiddleware(client.middleware()/*, routerMiddleware(history)*/),
typeof window !== "undefined" && window.devToolsExtension ? window.devToolsExtension() : f => f
),
);