Jason Charnes

Embracing Modern JavaScript (with Ruby on Rails)

When I learned jQuery, I was on top of the world.

All the fantastic things like animations and manipulating the DOM were at my fingertips. The late 00’s were a tremendous time of learning frontend development for me.

Then, I no longer cared about frontend development. In 2012 I started learning full-stack web development. I was more interested in server-side code than frontend code. After all, I could do what I “needed” to with jQuery.

About the time I entered full-stack development, modern JavaScript frameworks started a buzz. Job interviewers asked if I knew Backbone or similar “MV*” JavaScript frameworks.

Well no, I didn’t.

To be honest, I didn’t have a desire to learn those frameworks. In hindsight, the lack of desire was because I had yet to work on a project that required much interactivity.

Blindly Rejecting JavaScript Frameworks

I worked on my first complex advanced frontend project in 2014. Angular 1 and Backbone were still relatively popular at the time. But, I deemed JavaScript frameworks too complicated for my needs. After all, I could just use jQuery inside a Ruby on Rails application and be able to meet the requirements.

Things started well. Using my Ruby on Rails monolith, I was able to mock up the application quickly. I dropped in some jQuery, and voila- a working web application.

This approach worked for the first iteration, but requirements quickly changed. The result came out to ~1000 lines of JavaScript in a single file. Wrapped in a jQuery “document ready” function was a barrage of AJAX calls, nested callbacks, and exhaustion.

The code, though messy, worked. However, it made tracing down bugs difficult. There were no tests. I wouldn’t even know where to begin testing that.

That experience taught me the need for JavaScript frameworks.

That project should have taught me that, but it didn’t.

Rejecting Modern JavaScript

While buried in my Rails applications, JavaScript exploded (in a 👍🏻 way). As a frequent reader of blog posts, I kept up with the rise of JavaScript. But, I had an excuse ready for everything I read.

I once attempted to build an Ionic app using Angular 1. This experience left a bad taste in my mouth. I was (still am) unsure of what belonged where in Angular 1.

The tooling around JavaScript scared me even more. It took a lot of work to get a simple JavaScript application up and running. Not to mention, a simple NPM install polluted my project with tons of NPM Modules. Using “this” (pun) new era of JavaScript seemed too complicated for my taste.

I was content building my Rails applications and sprinkling in jQuery and CoffeeScript. My JavaScript setup felt dirty. I didn’t love it, but rather than try again I just wanted to write off JavaScript as bad.

At the cost of my arrogance, I was ignoring an opportunity to yet again, fall in love with programming.

Starting to Soften My Heart Towards Modern JavaScript

A lot of people I follow in the Laravel community began to evangelize Vue.js. I thought, well if they like it, I’ll love it. (I know, I need to work on following blindly.)

Around this time, I had the perfect use case for a JavaScript framework. A client required a small frontend application integrated into an existing e-commerce system. I thought this would be the ideal opportunity to give a Javascript framework another go. I wrote the app in ES5, still neglecting modern Javascript. But, something unusual happened.

I enjoyed it! For a myriad of reasons.

Most notably, though, I enjoyed how easy it was to build an interactive frontend application. Instead of having to manipulate the DOM with jQuery, I was working with data.

The data drove the application!

I built a couple of more small Vue apps for clients. I created them with vue-cli. The CLI allowed me to work with more modern JavaScript tooling (like Webpack!) without any configuration. The CLI provided the joy of Rails-like convention over configuration within a Vue application.

That experience taught me the need for JavaScript frameworks.

👆🏻 This lesson was real, now. Except, I still didn’t know how JavaScript belonged in my Rails applications.

Embracing Modern JavaScript

I told myself a lie. In fact, I don’t think I ever heard this myth, I just assumed it.

Geez, telling you this next part is embarrassing. 😊

I believed the only way to benefit from a JavaScript framework was to build an API and a frontend separately.

I’d watched people implement JavaScript frameworks inside Rails applications (pre-webpacker). It seemed more work than it was worth. Libraries like Angular 2+ come with a lot of modern tooling preconfigured and easy to use. But, it appeared to still be a mess in Rails.

“No way this provides any benefit inside Rails applications.”

One day at work we began migrating a legacy screen we use internally. It’s rather complex. The current page relies on redirections to other pages for specific actions. This setup works fine, but it slows down the employee. They use this page frequently.

The page in question doesn’t need to be a standalone application with an API. It can (and should) live in one of our existing applications.

The lead developers encouraged the use of React. Their argument for it was one that changed my entire outlook on modern JavaScript.

“We can make components for the sections of the screen that need to be interactive.”

What a great point!

DHH had just released a gem named Webpacker. Webpacker will configure and integrate Webpack (make sure not to confuse the two! 😭) into a Rails 4.2+ application.

  • The application in question is a Rails 4.2 application. ✅
  • We don’t need the entire page to be React. ✅
  • Webpacker has an installer for React. ✅

We agreed and got to work on migrating the screen.

💖 React & ES6

The first week entailed an initial learning curve of how to think in React. Since then, I’ve been writing frontend functionality at a blistering pace.

Thinking of the frontend in components wildly changed my view of the frontend. These self-contained elements make difficult functionality easy to compose. Not to mention, it makes testing much more natural (once you learn the concepts).

Alongside React, I’ve been making use of JSX, ES6 module imports, arrow functions (🙌🏻) and much more.

The benefit, to me, is that I get to keep building Ruby on Rails applications. Instead of breaking them apart, I can implement React as I need it, and continue delivering at a steady pace.

My newfound React knowledge has allowed me to work on React Native apps in my spare time.

Moving Forward with Modern Javascript

Though enamored with React, there is much more to explore.

ES6 (and beyond 🚀) is providing much-welcomed features into JavaScript. Babel is helping us use ES6. Tooling (like Prettier 😍) is helping take the burden off writing well-formatted JavaScript and letting me focus on delivering code. Tools like create-react-app (and other CLIs) remove the difficulty of starting out.

The integration we’ve done with React and Rails isn’t specific to React. I’d be happy to give Vue another go with Rails, or even Angular.

I’ve only touched the surface of modern JavaScript, but I’m happy to be here.

Please Submit a Talk to RailsConf 2018!

I’m stoked to be on the program committee for RailsConf 2018. (#blessed) One of my tracks is Modern JavaScript in Rails. Please submit all your Railsy JavaScript talks here!


If you’re in a similar boat, here are some resources I’ve found valuable:

Follow me on Twitter.