Here is how SV.CO is engineering a digital platform for student startups
by Hari Gopal
Using React to build a dashboard for founders
At the start of 2017, we introduced a new feature to the SV.CO platform: the founder dashboard. It was designed to be a central interface where founders can see targets that they needed to work on while going through our 6-month program.
This was a major change from our earlier design where the startup’s timeline page acted as the location where founders interacted with the website. On the startup timeline, targets were tacked on as an addition — while here, on the dashboard, targets are the focus. This approach clarified our position that SV.CO’s six-month program is about getting real work done — while being mentored by our faculty along every step of the way.
The interface, rendered on the server, was laid out such that targets were grouped and assigned to weeks, displaying a temporal progression through the program.
Growing pains
As the weeks passed for our newest batch, it became evident that the load-time for the page was getting worse. The number of targets being loaded (and rendered server-side), and the individual statuses being computed for each target was having an ever-increasing hit on the server’s time to render the page. At the peak of the performance hit, average render time hovered around 12 seconds.
Simple caching was not an option because most of the data being rendered included components unique to the signed-in founder. We mitigated the issue with a quick-fix by deferring the loading of data — only the latest week’s targets were loaded when serving the initial request, and the rest were loaded when the founder scrolled to the bottom of the list. This brought the initial render time back to sub-second levels, but it also meant that subsequent requests would take additional time, affecting user-experience. We also realized that the simple vertical list of targets would become unwieldy as the weeks progressed and the list of targets became longer.
Performance profiling showed view rendering as the single-most expensive operation that the server was engaged in, taking up over 90% of the render time. The dashboard was iterating over a large number of nearly identical elements, and all of that was adding up at the server, delaying response.
Time to Level Up
Apart from the performance concerns, our team also realized that the dashboard was not serving our founders as best as it could. The 6-month program we’d envisioned was structured to support a regular pace of development, with new content being released weekly. However, we noticed that not all teams move through the program at the same pace. While some progressed along with our release of new content, others took periodic leaps in completing targets. Hence we decided to switch away from a linear-format of releasing tasks, to a level-based one.
Teams now level-up to unlock new tasks when they complete milestone targets — essential achievables at their level that they needed to complete, to mark their progression in the SV.CO program. We also realized that tasks that were currently displayed in a single list, could use better categorization.
Switching to React
Given the performance concerns and the need to overhaul the structure of dashboard, it seemed like the ideal time to rebuild the dashboard using React JS, an open-source library for building user interfaces, maintained by Facebook and Instagram. We’ve been using React for the past few years to build complex Javascript components that were difficult to manage using jQuery. The timeline builder component is a prime example — founders use it to complete targets, submitting entries to their startup’s timeline.
The second version of the founder dashboard is rendered entirely using React, client-side. The server’s role is reduced to generating the data required to render the interface, resulting in significant speed up, while delivering the same amount of data on-load as the first version of the dashboard.
Tasks have been split into targets, chores, and sessions — new targets are unlocked when founders level up (by completing milestones), chores are one-off tasks, and sessions include regularly scheduled interactions with the faculty and stored videos of past sessions.
Knowing that iteration is a core part of developing any product, we also decided to introduce a Restart option. Restarting allows founders to return to a previous level, resetting their target completion progress and to iterate — to go over and redo past work to improve their product and personal abilities.
This revised tasks structure allows founders to focus on what they need to do at their current level, instead of being tied to a timed program that moves on regardless of whether or not they’re ready to progress. This is aligned with our observation that different teams move at different speeds.
The React library is a great option when rendering interfaces that contain repeating elements that have unique characteristics. The server now delivers all the data required to render the page during load, instead of deferring it to reduce time-to-render. React then renders the task components on the dashboard — which is the same across targets, chores and sessions — they’re just supplied different data, allowing them to be rendered much faster than was possible before.
Next Level?
The latest version of the dashboard is still too slow — the average render time hovers around 2 seconds, well over the 1-second mark that we think is acceptable for a _heavy_ page. However, this is a massive improvement over the 10-second-plus time of the server-side implementation, delivering equal (or more) amount of information in a single request. We’ve identified a number of instances where optimized querying could cut short the time required to build the data populating the React-powered interface.
The imminent release of Rails 5.1 also brings support for rails/webpacker, which uses the excellent yarn JS dependency management system to integrate JS libraries with a Rails repository. One of the current limitations of react-rails, the library that allows us to use React with Ruby on Rails, is its poor support for third-party React modules. Using React _natively_ with Yarn could sidestep this issue entirely, and allow us to unify and clean up JS dependency management on our repository.
There’s lots to look forward to!