Initializers in React.js? - javascript

I am using react 0.13.1 in a rails 4.2.1 application with react-rails and browserify-rails. I am not doing a single page application, but instead adding react components on rendered pages and using the rails routing system.
When I load a page, I want to initialize a few things, but I'm not sure where this code should go. Does react have a initializer function that it always calls before rendering components or does it always render the first component first such that I can just add initializer code to the first component?
How would I go about putting react initializer code in my multi page rails application? (should work for client or server rendered react code)
Note: Assume only react and plain javascript is being used.
Edit: not asking about initializing on each component, but rather initializing code after page load, but before react starts going through and rendering any components.

The entry point to initialize React is the call to React.render(), so you should perform any initialization before that call. If the initialization is async, just call React.render() in the callback.
And there's also the componentWillMount method on every component which can be used for component specific initialization.

Yeah it's all there in React's documentation. Each component has a getInitialState which is called when the object is first requested, you then have oncompentdidmount and another for when the component is dismounted. It's all JavaScript code so initialization code can be done inside each component or just declared globally before or after the React code is executed.
I have a similar setup with Django, where I use Django for it's strengths. Routing, Sessions, Authentication, Rest API ect... and have Django render a bar bones template which loads the React UI. This process seems to work really well, it's greatly sped up my site from where it was before, and the UI is awesome.
So in one particular case with my django app I need certain data to be initialized before the React components try to render themselves. therefore I wrap the initialization code into a function which is called on page load, then as a callback after that function has completed I call another function that actually add's my react components to the page. From there each component has it's own initialization which you've said you're not interested in at the moment, but that is how I handled the situation.

Related

Syncing Larvel Debugbar to Vue's UI

We are making an axios call that pulls in a gigantic object which is used to render a very lengthy UI using Bootstrap Vue.
The issue is that the UI continues to be rendered well after the axios call has been received.
Is there a way to check if everything is done rendering in Vue? The mounted hook does not work here.
More context:
The Laravel Debugbar gives me the best feedback here. When #6 AJAX is done, I know that the UI is done rendering. But how I can sync Laraven's debugbar with Vue's hooks?
Maybe to try with this.$nextTick inside updated hook
There is another lifecycle hook in vue beside mounted
The updated lifecycle hook is fired everytime a component reactive property changes and the virtual dom is updated.
To react to virtual dom changes inside the updated hook you can use nextTick()

Modifying a React component with a user script

Short version
How can I modify a React component with a user script (e.g. code injected by Tampermonkey) without breaking the app when I don't have access to the original source?
Longer version
Modifying the DOM of a React component directly can break the app because the reconciliation algorithm can get confused by manual DOM changes. Hence, I would like to modify a React component in my user script so React can keep rendering unhindered.
In a simple setup, React discovers components in the global namespace, and we can modify a component easily (see this fiddle for a working example):
oldComponent = Component
function Component(props) {
// modify the props to change the appearance of the component
return oldComponent(modifiedProps);
}
However, the situation is more complex when the application is deployed because the components are typically bundled using webpack. How would I be able to reproduce the example above in an application whose components have been bundled?

How do I create a hook for React Router Dom without any third party libraries?

I need a hook for React Router whereby everytime a user navigates to page analytic data is sent to our server.
This needs to be on every page so I want to abstract this network call away from the developer so it all happends in the background. I don't want developers to have to manually put an analytic event on every Route they create. I need some kind of middleware for react router.
We are currently using the react-router-dom library. I looked through the source code but I could not find any methods to hook into events; or any notion of events at all.
I see their are react-router-hook but it looks like that package depends on the react-router package, which we don't use. And honestly I am not thrilled about introducing a new external library just for what should be simple behavior.
I suppose I could always just import the native Route object from react-router-dom and create a wrapper for it which would allow me to implement my own behavior. I would prefer not to extend a third party library unless it was absolutely necessary though.
How do I create a hook for React Router Dom without any third party libraries?
Wrapper is one option, you named it.
However, I would go for a hook in my top (<Application />) component to detect route changes and send events.
componentWillReceiveProps(nextProps) {
if (this.props.location !== nextProps.location) {
sendEvent(); // location has changed, do your work
}
}
PS. Depending on your setup, you might need to wrap in withRouter to make it aware of location changes.

Server rendering with react-router v4 and prefetching data

I worked a lot with server side rendering with RR 3 so I wanted to see how it works in the context of v4. I followed the tutorial from the website, but because the rendering is happening now together with the route match, there's no way to implement prefetching data as before.
Here's how I used to do server rendering with v3:
https://github.com/alexnm/react-seed/blob/master/server/index.js
Based on the match function, I would call all the prefetch functions from all the component tree and then wait with a Promise.all for them to finish, then trigger the renderToString function and return the html.
In RR4, we have only the <ServerRouter> component, so the current solution I came with is duplicating the render code:
https://github.com/FortechRomania/react-redux-complete-example/blob/master/src/server/index.js
I'm also using the render function on the <Match> tag to trigger the prefetch actions. It's ugly and introduces all sorts of dependencies in the parent component of the page I want to render with prefetched data.
What am I missing here? Has anyone found a better solution for this scenario? I haven't found anything useful yet.
The new RR4 documentation has a working example: https://reacttraining.com/react-router/web/guides/server-rendering/data-loading

How to do url/view routing with Mobservable, React and possibly React-Router?

I'm looking into mobservable but I'm having some trouble coming up with a good model to do url routing.
Because of how mobservable works with React using a standard react-router does nothing when you change the url. Only if we crudely pass the url path down into the Handler stack to make them reactive do I see some changes.
I feel this needs a different approach. Of course I could hack some custom thing but I kinda like react-routers way of nesting the urls and the solid Location/Link features.
I'm working a (non public) project that uses both mobservable and react-router. That setup is basically as follows:
Create all your routes, but give them all the same handler, your root component.
Introduce reactive state that stores your ui state (like, currently open document for example)
in the router.run callback, use the data that is passed in (the second argument) to update your ui state and to kick off the necessary data retrieval and such. In the end of the callback, just render your handler. Depending on your further setup of the root component you want to pass it the ui state or nothing at all.
For us that setup worked fine so far, so please let me know if you run into any trouble.
EDIT
Another setup using Director can be found in the Mobservable TodoMVC example
Linking this because I found it helpful. I am basically following the approach out here: https://github.com/contacts-mvc/mobx-react-typescript/blob/master/src/components/ContactDetails/index.tsx.
Initialize the store/model in the app's index page or wherever the routes are defined. Then pass the initialized store to the component. Inside the component componentWillMount grab the ID off the route and pass it to a function to load your data.
If you already had data loaded then make a method that changes the selected item. Make sure that select item property is observed and it should automatically update the UI. I think that is what #mweststrate means by UI state.

Categories

Resources