Our app is wrapped in validation. Our public routes are always available, but the core app isn’t rendered at all until a user has a validated session. Sub-apps are segmented into the individual use case of each app, in this case they break down into tabs in the main app. Our teams sub app has a few aspects that may be of interest and illustrates our approach clearly.

Only a single view is necessary in this sub app. The main view is responsible for making the initial data fetch for the teams this user belongs to or has invites for. These are called in componentDidMount using promise.all , since our main TeamsGrid element is wrapped in our WithLoader component we can condition it’s render on those calls coming back from the API.

Handling the data up front allows us to make some cleaner components that are unencumbered by the initial API calls and data structure changes that may have to happen.

Our TeamsGrid component renders out three other components- CreateTeam which is responsible for team creation, InviteCard which renders teams a user does not have access to yet but is invited to, and TeamCard showing what other users are on a team and what instances the team is assigned to.

Each of these components deals only with a thin slice of the state, and only use actions pertaining to that slice. The segmentation helps keep the development process simple, these concerns have been decoupled and therefore are autonomous pieces.

For a moment let’s look at how this might work in a tightly coupled scenario. I am a user, I have a team that I am working with. I go to see who has accepted their team invitations and see that ‘George’ has joined my Developer team for a project I am very excited about.

At this point the App has fetched my team members for this team, and also the instances we are assigned to work on. I click through to one of the instances my team is assigned to sending me over to the Instances sub-app. I am brought to the instance overview for that instance which also has to make API calls.

This component does not know that I’ve just come through from the Teams sub-app and that I already have the team data, and so it waits for that information to come back from the API to render.

This is a waste of network resources as we have now made duplicate calls in rapid succession. We have also wasted precious milliseconds waiting on information that could easily be referenced from another place in the global state. Not only is there the practical advantage here of having a global state to call upon, but this is an asset for a mental model as well.

In working on this app we were able to build out components, with concern for how they will work with each other, not having to concern ourselves with the data flow.