I'm off boarding this week from my current job, and I wanted to write up the technical directions and learnings I'd acquired building the design system. It's part personal philosophy, part lessons learned.

Learn CSS grid

Build flexible components and avoid blackboxes

In the same way and html component, like <select /> with <option /> gives you components to mix and match, React components should follow a similar design pattern. It will allow for use cases to expand easily. Avoid black boxes that do a lot of work for you, and are controlled by an ever-expanding amount of props and overrides.

Write clear, user focused unit tests

One big exception to DRY is in tests. Cleverness should generally be avoiding because reading and updating a test can be a high-stress scenario. Make sure your setup, descriptions, and assertions are all clear and human readable. Follow the behavior-driven-development style of Given, When Then and more to the point - Arrange, Act, Assert.

Read about and plan accessibility before/as you're building

Check out sites and guides like https://inclusive-components.design and Smashing Magazine to figure out what you need for accessibility, and how to get there before you start coding.

Resist using third party solutions

They're always tailored for someone else's use case, so build your own UI components. With cross-browser standards and compatibility at an all-time high, and really good layout techniques like css grid, there's never been a better time to wain off pre-existing open source solutions.

Make it reusable

We've probably all heard don't repeat yourself, but sometimes we do. With atomic css, like in the design system, and modular components we're building, let's keep things clean and in one place.

Keep bundle sizes small

Make sure we're only bundling what we need to, take advantage of features like code splitting (see the styleguide) and externalizing dependencies and "production mode" optimizations like those from webpack.

Keep up to date

Your dependencies, your feature use, your skills. Use fallbacks and progressive enhancements while you build for modern and up-to-date browsers and frameworks. For example, allow React components to return Arrays and Fragments, but provide a div-based fallback for projects that use older versions of React.

IE11 doesn't handle flex values in the same way that newer browsers do. Normally the value flex: 1 is a shorthand for flex-grow: 1. But in IE11, that affects the flex-basis, and it was throwing my sizing off.

I thought using the flex shorthand would be safe, and I normally consider shorthand an anti-pattern, since it makes refactors or overrides harder. But you never know what you'll find in Internet Explorer!

And on each item (<li>), I needed to increment the counter and set the content from the current counter result. I chose to format it as decimal-leading-zero (the second argument to counter; any valid list-style-style will do). All together it looks like:

Harry at CSS Wizardy writes (below) about building in safe guards to a system, versus excluding "forbidden" use cases. It resonated a lot with me, since I've been building a design system. Flexibility and pragmatism have been design principles from the beginning, so that we build a system that outlives us, or at least, any use case we can think of right now.

I found out the hard way that IE11's implementation of CSS Grid (the old spec) doesn't support auto placement. It was the one feature my project needed to maintain the same layouts in IE11 as the evergreen browsers.

So I came up with a "polyfill" script that finds grid containers, and on each of its rows, it derives their column spans and positioning, and sets their IE-specific css properties.

There are a few places to tweak if you want to drop this in your project – the logic for figuring out column spans checks for css classes, with each span having their own class, which is specific to my use case. And your project might not also care about manually adding gutters. My hope is that this will at least get you going in the right direction.

I started working on a lazy image loading component today. There are several pre-existing solutions on the internet, but nothing I found took a modern approach. That is, there's a new API called the Intersection Observer that makes in-view checking really simple.

First, you create the observer with a callback:

const observer = new IntersectionObserver(callback)

Then start observing a DOM node (e.g., one with ID my-element):

observer.observer(document.getElementById('my-element'))

Now, when that element goes in or out of view, the callback (above), is fired with an array of Intersection Observer entries (one entry for each item you're observing).

So, when the callback gets called, you can check if the element is intersecting:

I'm using CSS modules and testing with Jest in my latest project, 'cuz they're the best. But I kept wanting more from the css mocking experience in unit tests. The recommended solution using identity-obj-proxy wouldn't do it for me, because I had lots of duplicate classNames (e.g., height.one, fontSize.one) that led to ambiguity in unit tests.

I started by building a jest transform, then realized that was the wrong approach, because js files importing the css were being processed by babel-jest.

So, I went to looking back at moduleNameMapper in jest's config. I knew that I could manually read the directory of css files I wanted transformed, and build an object from that (with inspiration from Brent Jackson's css-to-object).

And I did it, and it worked! I ran it against an existing test suite to reveal any stress cases, and tweaked accordingly (looking at you breakpoints, pseudo classes, dashes in selectors).

It's up and public in its raw and newborn state as a gist, here. Aiming to open source it as a module once the dust settles.

I am a software developer. I’m good at some things (looking at you, front end & javascript), fine at other things, and meh at a couple things. I also have decent people skills. So when the right opportunity at the right company presented itself, I became a consultant.

Consultants do lots of good things – provide advice, get their hands dirty as practitioners, observe how teams and processes work, suggest change when something needs tweaking. Sound grand? Well, maybe. But those are also just good skills to have as a professional. And especially as a professional software developer.

For me, consulting is not spelled with a capital C. It’s not a noble aspiration, or a platonic ideal. Consulting is doing the right things (working hard, communicating well, continuously improving) for the right reasons (from sincere concern, for a worthwhile change, to make you and your team’s work better). And that’s no different than being a good colleague and a hard worker.

No matter what you call yourself, just make sure you're doing work you're happy with and being nice to others.

After lots of copy/pasting a small utility that makes shallow rendering a React component a little easier, I've open sourced it. It's called renderShallow, and it's now on Github and npm as render-shallow.

My motivation for it came when I started noticing that in most of the React component tests I wrote, I simply wanted a shallow rendered component to test. The ShallowRenderer API is a little verbose, between the creation and the getting of the output. So I started abstracting that (the .output returned from renderShallow). When I found myself wanting to rerender the component, either because of state or props changes, I added the ability to both re-fetch the output (rerender), or render the element again with new props (rerenderElement).

Today I was experimenting with how to get all the values in a form. The form was dynamic, so I didn't know the input and textareas that could be in it. So I turned to my old standby document.forms (supported in _all_ browsers!).

When I started iterating over the form (document.forms[formname]), which is an HTMLCollection, I noticed that all non-input or textarea elements were filtered out (even if an input was nested inside a label). That means I can easily map over the inputs, get their values, and do as I wish with them!

Today I stumbled on the DOM APIs `document.forms`, which holds a collection of all the forms on a given page. You can access individual forms, and do things like checking the validity of all its inputs. Super powerful!

Think about the user’s perspective and how they would interact with the component(s). Testing output allows you to change implementation, without affecting output. That means tests only break when there’s an actual functionality change.

Garth fears change

2. Make reusable components that can be tested in isolation

They’re easier to test and makes tracking down changes faster.

Reduce, reuse, recycle

3. Cut down on the amount of DOM rendering in tests

When setting up your tests, prefer `before` not `beforeEach` to cut down on repeat renderings. It can slow things down considerably.

Liz Lemon says "Let's do this."

4. Isolate mutations to tests contexts

Relying on other cases mutating state or DOM leads to brittle tests that are hard to refactor or reason about. Test blocks contexts should be self-sufficient. Resist the urge to share data.

Beyonce's Miss Independent

5. Be explicit and don’t abstract too much setup or repetition

By writing out and repeating steps, it’s easier to scan the code while under stress.

The Beatles, repeating

6. Choose a tool that allows you to isolate cases for a faster feedback cycle.

Have and use the ability to isolate a test or tests, without running them all. It’s easier to focus and faster to find the change.

Forever alone cat

7. Turn on source maps, if applicable

Get pointed to the source code quicker, if you’re using a compiler.

What year is it? Also, RIP Robin Williams

8. Use a headless browser and rerun tests on file change

The key to TDD is speed, speed, speed.

A headless ghost spins a pole

9. Allow for in-browser debugging

For the times you just need that Chrome dev tools. (And maybe Firefox or Safari)

A really strange web browser

10. Have consistent names for your test blocks

File names, methods, modules

Belle swings across her library on a ladder

11. Make your `describe`s, `context`s, `it`s human readable

Mad lib style: [Module name], when [state], (and), it [behavior]

It's a mad, mad, mad lib world

12. Include polyfills if testing on different browsers

Browsers behave differently, especially older versions of PhantomJS versus something like Chrome. A polyfill like es5-shim will get you to parity.

Show browser variations no mercy

13. Use a pluggable expectation system for more meaningful assertions

For example, chai-jsx (or expect-jsx or jasmine-expect-jsx), if you’re using React, allows you to assert with JSX on a component. Same goes for libraries like immutable, sinon, bluebird.

Plug it in, plug it in

14. Fail the build on console.error

A third party developer is politely telling you there’s been a horrible problem, without crashing your app (isn’t that all you can ask for in a client-side app?). This happens with prop type validation errors in React.

In vim, holding down a key can save you a lot of repeated effort. In newer versions of osx, holding down a key was disabled, to allow for a special character entry dialogue. In every blog post about disabling this feature, I found the blunt force approach of turning off it globally. It didn't sit well with me, because sometimes I do want to use special characters, and it's harder to do without the entry dialogue.

The one weird trick to disable in vim? You can turn off the press-and-hold behavior for specific applications! For vim, it's:

defaults write org.vim.MacVim ApplePressAndHoldEnabled -bool false

(Enter that in your terminal)

If you need to do this for other apps, check out the listings inside ~/Library/Preferences, and remove the .plist from end of the title (e.g., org.vim.MacVim.plist).

In my day to day as a software consultant, I often help evaluate new technologies (be it a framework, library, language). Over time, I noticed certain questions and thoughts continued to come up. Things like – how’s the community around it? How many people are using it? Is it easy to learn? And so on.

Below is my effort to give voice to all the subtle feelings, the small questions and thoughts and everything else that happens while researching.

Usage

It is important for a technology to have an engaged community or a strong interest in a community (i.e., React in front end dev circles). There are several ways to measure this, which include the following:

Social media engagement - People are tweeting and writing blog posts about this tech. Their tone would be one of excitement or intrigue. Others may write about how they are adopting the new tech.

Package downloads in a given month - Some package managers, like npm, give statistics on how many downloads a package will have over time. Anywhere in the thousands is good. For example, React and RxJS have ~1 million downloads per month.

Github stars and forks - Another measure of usage, and peer engagement

Amount of pull requests and their acceptance rate - Is the project actively being developed and improved? It’s also important to gauge how the maintainers regard changes. That will affect contribution, and by extension, adoption.

Amount of open issues - How many there are and what severity. This will give you a sense of how ready it is (see also: production worthiness). It is also important to gauge maintainer quality. Are they helpful and open, or closed and prickly? The project won’t get far with bad contributors.

Questions to ask

As a developer evaluating a new technology, there are a series of questions you may ask or that may be asked to you before adoption. The following questions should give you a good sense of whether or not the technology is the right choice now. The answer to each of these does not have to be a yes, but the majority of these questions should be answered positively.

Advantages

What are the technology’s advantages over the current offerings?

Also, what holes does it fill, or how does it improve current offerings?

Could you solve the same problem with an existing piece of technology? (Put another way - what else could you do?)

Design

Is the documentation good?

What does the project’s roadmap look like?

Will you write less or better code with this technology?

Does this technology align with the language or framework it is intended to be used with?

See their philosophies and design goals

Is the source code well tested?

Community engagement

What excites you about this technology?

Could you convince someone with no experience in this particular tech stack on this technology choice? (E.g., a seasoned ruby developer on webpack)

Integration

If the technology integrates into another system, do the two roadmaps and philosophies align?

Is there an escape hatch in case this technology does not work? (E.g., rendering HTML from React components)

Is it stable enough to use in production?

Will/has/could this technology require a lot of churn? (E.g., React in early versions)

How is the ecosystem surrounding this technology?

Extended usage

Besides its intended usage, can you see the technology being adopted in a different setting? (E.g., Redux in server-side apps)

Do you see yourself working with this technology in one week, one month, one year, five years?

Project adoption

How would you convince another developer to change to this technology?

What types of projects would this be useful for?

Is this easy to adopt into an existing project?

Is this easy for a junior to learn?

Could you introduce this to a skeptical team in isolated pieces? (See also: escape hatch)

It eliminates the need for copy-pasting. Any key can be referenced, beginning with "$npm_package_" and adding an underscore for every level you go down. Say you had a config object, where you stored reusable values, like a domain address, that's passed as an argument in a script:

I was continuing work on my web boilerplate (note: now moved under the stride-nyc org) when I decided to add Travis CI integration for builds.

Travis CI is triggered on pushes to certain branches and on pull requests. To configure it, you create a .travis.yml file in your repository. My tests are running using a forked PhantomJS 2 launcher with Karma, which makes running your tests against PhantomJS 2 really easy, while we wait for official support. So, what's the problem? The launcher works great locally, but doesn't work on Travis CI's Ubuntu machines.

After some Googling, I landed on a post by Mediocre Labs. It describes how to pre-install a custom built PhantomJS 2 binary on Travis CI. That part worked just fine, but I still found myself fighting with the PhantomJS2 launcher which wouldn't recognize the custom binary, as well as the PhantomJS v1 launcher, which requires an npm dependency on PhantomJS, which isn't an option.

I worked around it by explicitly pointing to the TravisCI custom PhantomJS binary in my build task. It nicely overrides the binary location for the PhantomJS2 launcher. So putting it all together, here's the build task:

I was about to start a new side project, when I realized the crazy amount of setup I'd have to do to get up and running. I wanted to use my favorite latest things, but I had nowhere to start. So I started grabbing from prior projects and some open source libs, to create my latest starter framework. I'm optimistically calling it my 2016 web boilerplate.