I wasn’t at this conference, so I have very little context. Normally, I’d consider it a sin to weigh in on a subject brought up by looking at two out-of-context slides, but I’m only weighing in out of interest and to continue the conversation.
The idea seems to be that if you need to select an element in the DOM with JavaScript, don’t use the same selector as you would in CSS.
So if you have…
<article class="article">
</article>
…and you need to apply an event listener to that article for some reason, then don’t use…
$(".article")
(or querySelector or whatever, I assume.)
Instead, apply an attribute intended just for the JavaScript to target, like…
The idea is that you can separate jobs. The class has the job of styling, and the data attribute has the job of JavaScripting. Both can change without affecting each other.
Seems reasonable to me.
Also seems like there is plenty to talk about here. Performance, I suppose, but that’s probably the least-interesting thing since selectors are generally pretty damn fast these days. We could continue the conversation by talking about:
What naming convention?
Should you be naming events?
What if it needs to be selected for different reasons multiple times?
Can you or should you use IDs?
Is it worth avoiding DOM selection at all if you can?
There comes a time in any young app’s life when it will have to monetize. There are a number of ways to become profitable, but accepting cash is a surefire way to make this more direct. In this four-part tutorial, we’ll go over how to set up a serverless function, make it talk to the Stripe API, and connect it to a checkout form that is setup as a Vue application. This may sound daunting, but it’s actually pretty straightforward! Let’s dig in.
We’ve covered serverless concepts before but, in case you haven’t read that article, let’s talk for a minute about what we mean by „serverless” because it’s a bit of a misnomer.
The promise of serverless is to spend less time setting up and maintaining a server. You’re essentially letting the service handle maintenance and scaling for you, and you boil what you need down to functions that run certain code when a request is made. For this reason, people may refer to this as FaaS. This is really useful because you pay for what you use, rather than a large container that you might not need in its entirety. You also primarily hunker down and focus just on the code you need to run instead of babysitting a server, which really appeals to a lot of people who’d like to get up and running quickly.
But FaaS isn’t always the right tool for the job. It’s really useful for small executions but, if you have processes that might hold up resources or a ton of computation, being able to communicate with a server as you normally do might be more efficient.
What we’re going to make is a perfect use case for going serverless. Stripe checkouts are pretty seamless to integrate on both the client and server side, but we do actually need to execute some logic on the server, so we’ll use Azure to help us with this. The portal and Github integration are pretty quick to manipulate, as long as you know where to go. So by all means, let’s make it happen!
Sign up for Stripe
First, we’ll create a Stripe account. We verify our new account via email and then we’ll head over to the API section, where we can retrieve two keys. You’ll note that we’re in test mode right now, which is good! We’ll keep it like that for testing, and unveil the testing key token to use while we set up the application.
Once you’re signed in, go to the API section of your dashboard to retrieve your key.
Setting up Our Serverless Function in the Azure Portal
First, we’ll head over to the portal, (or if you don’t already have an account, you can sign up for a free trial here) and select New > Serverless Function
Setting up a new Servless Function in Azure
When we click on the Serverless Function app, we’ll be taken to a panel that asks for details to help with the setup. As you can see in the screenshot above, it will autofill most of the fields just from the app name, but let’s go over some of these options quickly:
Add in a unique name
A Resource Group (if you don’t already have one, create one)
I use the Windows OS because the Linux is still in preview, so Windows will be more stable
I use the Consumption Plan because this is the one that will have payments that scale with the use, and it will also scale automatically. The other option, App Service Plan, is good for people who prefer everything to be a bit more manual.
Choose a location that is close to your customer base, or a midpoint between two customer bases
Choose a storage, or create one as I’ve done
I’ll also check Pin to Dashboard because I want to be able to retrieve my function quickly later
This will bring you back to the main portal dashboard and let you know that your function is deploying. Once it’s done, it take you to a main screen that has all of your options. From here, we’ll want to create our function, and it will be an HTTP trigger.
We’ll select Functions under our function name, and you’ll see a little table with a plus that says “New Function”:
Once we click here, we have a few options on what we can create. We’ll pick HTTP Trigger:
We’ll be able to select the language (pick „JavaScript”) and then „Create”:
The Default Testing Function
From here, we’re given a default testing function which helps us see how this all works. If we open all of these panels and hit the Run button, we’ll see the output in logs.
Running the function in a test environment
Here’s the code we were given:
module.exports = function(context, req) {
context.log('JavaScript HTTP trigger function processed a request.');
if (req.query.name || (req.body && req.body.name)) {
context.res = {
// status: 200, /* Defaults to 200 */
body: 'Hello ' + (req.query.name || req.body.name)
};
} else {
context.res = {
status: 400,
body: 'Please pass a name on the query string or in the request body'
};
}
context.done();
};
You’ll see here that we’re passing in the context. That allows us to log, which will be shown in the lowest panel below. In the Test panel on the right, we can pass in a request body that can be used to test our application. When it runs, we see the output with a 200 status and know that everything is working. We also have a context.log for the case that it gives us a 400 error. If you’d like to play around with a serverless function and see it in action for yourself, you can create one with a free trial account.
Next Up…
Now that we have the base of our serverless function, let’s set up what we’ll need to communicate with Stripe! More to come in the next post in this series.
MDN released a comprehensive guide to Flexbox with new and updated materials by Rachel Andrew. The guide includes 11 posts demonstrating layouts, use cases and everything you could possibly want or need to know on the topic. All of the related Flexbox properties are nicely and conveniently attached to the table of contents, making this extremely easy to use.
In this post, Rachel adds helpful thoughts and context about Flexbox. Her comment on Flexbox initially being treated as a silver bullet solution for all our layout issues struck me:
Prior to Grid shipping, Flexbox was seen as the spec to solve all of our layout problems, yet a lot of the difficulty in using Flexbox is when we try to use it to create the kind of two-dimensional layouts that Grid is designed for. Once again, we find ourselves fighting to persuade a layout method to do things it wasn’t designed to do.
Guilty as charged. I remember being so eager to ditch floats and learn a new syntax that I treated Flexbox as a square peg trying to be fit into a round hole. That definitely bit me on at least one project.
Most importantly about this guide is that it forms a sort of trifecta of reference materials on layout specifications provided by CSS: Flexbox, Grid and other Box Alignment properties.
Oh, and while we’re on the topic, we have Flexbox and Grid guides right here on CSS-Tricks. You can never learn too much, right?
My latest realization is that delivering a performant, accessible, responsive, scalable website isn’t enough: I also need to consider the impact of third-party scripts. No matter how solid I think my prototype is, it doesn’t absolve me from paying attention to what happens during implementation, specifically when it comes to the addition of these third-party scripts.
I recently had a conversation with a friend working on quite a high profile e-commerce site. They were hired to develop the site, but particularly with performance in mind. They were going the PWA route, but were immediately hamstrung by third-party scripts. One of them, apparently unavoidably, couldn’t be HTTPS, meaning the site was immediately disqualified from being a PWA. They could still do a good job in many other areas, but right and left their great performance work was slaughtered by third-party scripts. I don’t envy being in that position.
It’s often the fault of „tag managers.” There are a bunch of them out there. Here’s a marketing pitch for one of them:
Marketers want tag management that’s simple, reliable, and integrates easily with existing systems … You’ll launch programs faster, so you can make swifter decisions.
In other words, „Give your marketing team the ability to add whatever third-party JavaScript they want quickly without having to go through your normal deployment process.” I can understand why they are needed in some organizations, but it still sends chills up my spine.
Third-party scripts could conceivably be a part of a design style guide. Right alongside your buttons and modals could be a list of the third-party scripts in place on a site. Brad Frost:
The idea is that someone (or as Trent points out, some *thing*) could hypothetically crawl through all the included scripts on a site, and display them in the in style guide alongside all the color swatches, icons, UI components, etc. After all, they affect the end user experience just as much (if not more) than all those other design elements. You can visually weight them based on how gnarly they are and thus have thoughtful conversations with your team — especially those folks are carelessly chucking in all these performance-damning scripts — about the pros and cons of each script that gets included.
Third-party scripts are probably the #1 cause of poor performance and bad UX on the web. It’s no wonder things like AMP exist. The fact that it disallows third-party scripts is probably the largest contributor to it making sites fast. Controversial as hell, though, in its other choices.
As fate would have it, third-party JavaScript is even more dangerous than it ever has been, thanks to Spectre and Meltdown. Jorgé:
Q: Is JavaScript vulnerable in my browser?
A: Yes, browsing a web can give access to third parties to your machine’s memory beyond the browser.
😳
More on Third-Party JavaScript
If you, like Trent, are planning to bone up on your third-party JavaScript chops, here’s a bunch of stuff from other developers in the past few years digging into it all. Some of this is targeted at you being the deliverer of the third-party JavaScript.
Third Party JavaScript (In the Third Person) Slides by Alex Sexton
On Third-Party Javascript – The Principles by Gergely Nemeth
When serving third-party JavaScript applications the size of it and the cache policy are crucial, as both not just affect the time your users have to wait to see the application, but also your monthly bills.
Third-Party Javascript by Ben Vinegar and Anton Kovalyov
Things to Know (and Potential Dangers) with Third-Party Scripts by Yaphi Berhanu
The web is full of third-party scripts. Sites use them for ads, analytics, retargeting, and more. But this isn’t always the whole story. Scripts can track your behavior, your preferences, and other information.
Ain’t No Party Like A Third-Party JS Party by Rebecca Murphey
You thought you had the hang of this whole JavaScript thing, but now you’re in the world of third-party JavaScript, where all you control is a single script tag and where it’s all but impossible to dream up every hostile environment in which your code will be expected to work. „It works on my machine” has never rung quite so hollow. In this talk, we’ll take a look at some of the delightful bugs we’ve had to solve at Bazaarvoice while working on the third-party JavaScript app that collects and displays ratings and reviews for some of the world’s largest retailers.
For a beginner, accessibility can be daunting. With all of the best intentions in the world, the learning curve to developing compliant, fully accessible websites and apps is huge. It’s also hard to find the right advice, because it’s an ever-changing and increasingly crowded landscape.
I’ve written this post to give you some tips on small things that can make a big difference, while hopefully not affecting your development process too much.
Let’s dive in!
Document Structure and Semantics
It probably doesn’t come as much of a surprise that structuring your HTML in an organized, semantic way will make a big difference. Screen readers rely on a well-structured document in order to follow a coherent narrative, so make sure that you’re using the elements that the HTML5 spec provides responsively and effectively.
Let’s look at three specific things that can help ensure a well-structured and semantic document.
Use a Single <main> Element
A good example of building a responsible, semantic document structure is only using one <main> element. This should serve as a signpost for the most important content of the page for your user.
Add an ID to it and offer a skip link in your main <header> like so:
<header role="banner">
<h1>Your main page title</h1>
<a href="#main-content">Skip to the main content</a>
</header>
<!-- Further down the document -->
<main id="main-content">
<!-- Put your main body of content in here and other really important stuff -->
</main>
This little trick should help your screen reader users out in a big way, because they can go ahead and skip the fancy bits and dive right into your important content. It’s also great for keyboard users for the same reason.
Another nice touch is to add a :focus style to the skip link that makes it visible. Try pressing your tab key on GitHub.com. Pretty neat, right?
Use Elements Appropriately
So, <button> elements are a pain in the butt to style right? That doesn’t mean you should attach your JavaScript events to a <div> or an <a href="#"> though. You see, when you use a <button>, you get keyboard events for free. You’re also helping screen reader users out because it’ll announce the element correctly. Check out this example:
If a user focused on that button and hit the enter key, that event would fire. That makes both yours and the users’ lives a bit easier. Well worth it, right?
It’s really common for screen reader users to navigate a page by using the heading structure. That means we should help them out and create a nice hierarchy for them. Let’s take a look at a standard blog post:
<main id="main-content">
<article>
<!-- The page title is up in the main <header> in this instance -->
<h2>My awesome blog post</h2>
<p>Vestibulum id ligula porta felis euismod semper.</p>
<p>Vestibulum id ligula porta felis euismod semper.</p>
<h3>A sub-section of this post</h3>
<p>Vestibulum id ligula porta felis euismod semper.</p>
<h4>A sub-section of the sub-section</h4>
<p>Vestibulum id ligula porta felis euismod semper.</p>
</article>
</main>
With that sample, the user can navigate to the start of „My awesome blog post” and then have the ability to skip to sub-sections and nested sub-sections easily. They can also skip back up. It’s just a nice way of helping them consume the content you’ve produced as easily as possible.
It can be recommended that a page has a single <h1> element, even though the W3C HTML5 spec says you can have many. I personally agree with the use of a single <h1>, but you can have many, as long as you follow a nice structure and hierarchy. That’s the key here.
Get Your Color Contrast Right
To be WCAG 2.0 AA compliant, you need to have a contrast ratio of 4.5:1 for normal text. This is your paragraphs, buttons, navigation, etc. You need to go for a ratio of 3:1 for larger text, such as headings. I’d say this should be your minimum as it’s incredibly achievable with tools such as Tota11y, Contrast and the WebAim contrast checker. You can still get plenty of color balance and variation in your design too.
The reason that contrast is so important is because there’s so much variation in environment that you probably don’t even consider, such as bright sunlight and poor quality displays. Add this to a visual impairment or, say, a migraine and you’re potentially causing problems for your users.
Getting the contrast right will have a huge, positive effect across a wide spectrum of your users.
Responsible Text Labels
We’ve all built out a list of items with a non-descriptive, but visually appealing „More” button, right? More what though? We need to be more responsible with this and provide some context.
One way to achieve this is by visually hiding descriptive text with CSS and hiding the non-descriptive text from screen readers. It’s tempting to use display: none;, but screen readers can ignore elements with that set, so we need to be more creative. I use something like this little helper:
With this CSS in place, we can do something like this:
<a href="/link-to-your-page">
<!-- This is hidden from a screen reader, but visible visually -->
<span aria-hidden="true">More</span>
<!-- This is visible to a screen reader, but visually hidden -->
<span class="visually-hidden">Continue reading: "Your post title here"</span>
</a>
A sighted user will only see “More” and a screen reader user will hear “Continue reading: 'Your post title here.'” Both sets of users are happy.
You can also achieve the above by using an aria-label on the <a> tag. This will override the text within for a screen-reader:
<a href="/link-to-your-page" aria-label="Continue reading: 'Your post title here'">
More
</a>
Small Typography Tweaks With a Big Impact
It’s always worth remembering that people with a visual impairment or learning difficulty could be trying to read your content, so some small tweaks to your typography can go a long way.
A body of content such as an article should be sized at 16px (or equivalent unit) at a minimum. It’s also worth increasing your line-height to around 1.5 too. Space between lines can help readers with dyslexia to understand your content better. The combination of size and space is also great for older people and/or short-of-sight people. Even small summaries and aside content should be at least 12px (or equivalent unit). Anything smaller than that will alienate users who struggle to read.
Another trick is to highlight key words and phrases if your content is quite complex. This not only benefits users who are slightly slower at processing content but it also helps people who like to scan over an article, like I do.
Lastly on this section, I’d advise you to be careful with your font choices. Fonts with complex ligatures and decorative elements can be really distracting, so maybe limit the usage of those to key, large headings only. It’s also been advised that sans-serif fonts are better for readers with dyslexia. Check out this article for more on that and other text formatting tips.
Enhance Keyboard Support
There are a few little tweaks you can do to help users who primarily use their keyboard to navigate your website.
Say you’ve got a little button that shows a dialogue when you click it. You should attach an event to the escape key that hides it. Here’s a sample snippet:
document.addEventListener('keyup', (evt) => {
if(evt.keyCode === 27) {
// Run whatever code hides your dialogue
}
});
Another tweak you can do for our keyboard-navigating buddies is not hiding focus from them. Browsers give us focus states for free with outline. I know it can look ugly, but hot-damn it’s useful for keyboard users. If you want to get rid of that blue glow, I get it—just please use the :focus pseudo selector to add an obvious state change to it instead. Here’s a sample:
.your-element {
background: red;
}
.your-element:focus {
outline: none; /* Reset the default */
box-shadow: 0 0 0 3px black; /* A very obvious state change */
}
Don’t Rely on Color Alone to Communicate State Changes
Let’s end on a really important one. Color shouldn’t be relied upon alone to communicate state changes. Take this scenario as an example:
You’ve got a button that posts a form. You wrote some neat JavaScript that makes it go grey while it sends the data. It then either turns green or red, depending on what the status is.
For a colorblind user, this is a nightmare. To them, the button may have barely changed enough for them to notice, so they may just keep clicking and clicking while getting really frustrated. This isn’t ideal.
So, instead of relying on color, let’s enhance that with a status message that supports the button’s state on response.
That sample is a great way to quickly communicate to the user that something has changed and the use of color, text and iconography clearly communicates that change. Disabling the button whilst the response is processed is also a great help to the user.
Wrapping Up
These little tips should make a big difference to your users, and I hope you dive into your projects and implement some of them.
A grand total of 77,609 responses from WordPress users and professionals collected by Automattic between 2015 and 2017. The stats for 2015 and 2016 have been shared at the annual State of the Word address and 2017 marks the first time they have been published on WordPress News.
A few items that caught my attention at first glance:
Between 66% and 75% of WordPress users installed WordPress on their own. In other words, they were savvy enough to do it without the help of a developer. Hosting providers were next up and clocked in at 13-14% of installs.
WordPress professionals described their clients as large and enterprise companies only 6-7% of the time. I guess this makes sense if those companies are relying on in-house resourcing, but I still would have pegged this higher.
What do users love most about WordPress? It’s simple and user-friendly (49-52%). What frustrates them most about it? Plugins and themes (19-28%). Seems like those two would go hand-in-hand to some degree.
I’m not a statistician and have no idea how much the results of these surveys accurately reflect the 26% of all sites on the internet that are powered by WordPress, but it sure is interesting.
Tom Warren’s „Chrome is turning into the new Internet Explorer 6” for The Verge has a title that, to us front-end web developers, suggests that Chrome is turning into a browser far behind in technology and replete with tricky bugs. Aside from the occasional offhand generic, „Chrome is getting so bad lately,” comments you hear, we know that’s not true. Chrome often leads the pack for good web tech.
Instead, it’s about another equally concerning danger: developers building sites specifically for Chrome. In theory, that’s not really a thing, because if you build a website with web standards (of which there isn’t really much of an alternative) it’ll work in Chrome like any other modern web browser. But it is a thing if you build the site to somehow block other browsers and only allow Chrome. Warren:
Google has been at the center of a lot of “works best with Chrome” messages we’re starting to see appear on the web. Google Meet, Allo, YouTube TV, Google Earth, and YouTube Studio Beta all block Windows 10’s default browser, Microsoft Edge, from accessing them and they all point users to download Chrome instead. Google Meet, Google Earth, and YouTube TV are also not supported on Firefox with messages to download Chrome.
I wouldn’t call it an epidemic but it’s not a good trend. Best I can tell, it’s server-side UA sniffing that entirely blocks the sites:
Sheesh.
If anything, I’d think you’d just let people use the site and display a warning if you’re really worried some particular feature might not work. Or even better, fix it. I have no behind-the-scenes knowledge of why they made the choice to block certain browsers, but it’s hard to imagine a technical limitation that would force it. And if it is, I’d suggest letting it be very publicly known to incentivize the other browsers to support what is needed, assuming it’s an established standard.
Even more concerning than browser-specific websites is seeing browsers ship non-standardized features just because they want them, not behind any vendor prefix or flag. There was a time when web developers would have got out the pitchforks if a browser was doing this, but I sense some complacency seeping in.
These days, the vibe is more centered around complaining about other browsers lack of support for things. For example, one browser ships something, we see one green dot in caniuse, and we lambast the other browsers to catch up. Instead, we might ask, was it a good idea to ship that feature yet?
No modern browser is shipping vendor prefixes anymore since we all ultimately decided that was a bad idea. A side effect of that is that shipping a new feature in CSS or JavaScript is all the riskier. I would think shipping an unprefixed feature to a stable version of the browser would mean the feature is standardized and not going to significantly change. Yet, it’s been happening.
In CSS, Chrome shipped motion-* properties, but then that all changed to offset-*, and the old motion-* properties just stopped working. That’s more than just annoying, that kind of thing helps developers justify saying, „I just build this site for Chrome, if you wanna use it, use Chrome.” Fine for a demo, perhaps, but bad for the web industry as a whole. Again, I have no special insight into why this happens, I’m just a developer looking in from the outside.
Here’s another CSS one I just saw the other day. People are excited about text-decoration-skip: ink; because it looks great and helps people. They are using it a lot. But apparently, that’s not the correct name for it? It’s been changed to text-decoration-skip-ink: auto; and so Chrome 64 is canningtext-decoration-skip: ink;. This stuff is hard to keep up with even while actively trying.
Over the past few years, I’ve increasingly seen articles with headlines that run something like, “New Feature Coming To the Web” — followed by content which described how Chrome had implemented an experimental new feature. “You’ll be able to use this soon!” has been the promise.
The reality is a bit more complicated. Sometimes, ideas the Chrome team pioneers make their way out to the rest of the browsers and become tools we can all use. Sometimes… they get shelved because none of the other browsers decide to implement them.
Many times, when this latter tack happens, developers grouse about the other browser makers who are “holding the web back.” But there is a fundamental problem in this way of looking at things: Chrome isn’t the standard. The fact that Chrome proposes something, and even the fact that a bunch of developers like it, does not a standard make. Nor does it impose an obligation to other browsers to prioritize it, or even to ship it.
This isn’t all to throw Chrome under the bus. I’m a Chrome fan. I’m sure there are examples from all the major vendors in the same vein. I’d just like my two cents to be careful now. The web is the best platform to build for and generally heading in a direction that makes that even truer. The easiest way to screw that up is not being careful with standards.
A lot has happened since I wrote that article in 2015, and this follow-up has been in the works for a good six months. I ended up, not with a solution for the job titles conundrum or a manifesto about the importance of HTML and CSS, rather a simple, honest story about my roller coaster ride.
Okay, enough dilly-dally. Let’s go!
<story>
In the aftermath of the FizzBuzz drama in 2015, I doubled down on my freelance business and did really well. I got a great contract gig with startup in New York refactoring a Haml/Bootstrap situation that paid the bills and then some. I hired an assistant and started the Tackle Box, an online school sort-of-thing where I taught web development and WordPress. I made a little money off that one, too. I spoke at a handful of conferences and meetups, taught a bunch of classes, and generally had the pedal to the metal.
Then I got really, really tired.
I was sick of writing emails, sick of sending invoices, and sick of being on the computer all the damn time. I wanted to go to work and then leave work at work; something that is very hard to do in our industry, and extra difficult when you are your own boss. I enjoyed coding sometimes, but it was all about the billable hour. Why should I write code or be on the computer at all if I’m not being paid for it? This was burnout, that thing that’s become a weird, convoluted rite of passage in our industry.
I wanted to shut down Lara Schenck, LLC and be a ski bum. And you know what? I did. It was time for a break, and I took one for about six months.
Ski Bum Sabbatical
I left New York City in August of 2016 and moved back to my family’s farm near Pittsburgh. I got a job cleaning horse stalls for $7/hr at the stable where I used to ride when I was a kid. My plan was to gradually ramp down business while I lived rent-free and prepared myself for the simple life. That December, I would be starting work as a bartender at Goldminer’s Daughter Lodge in Alta, Utah, a tiny ski town outside of Salt Lake City. Room and board were included in the job; I’d make enough pocket money for booze, and my life would consist of skiing, sleeping, and socializing. No emails.
Just down the winding road from Alta Ski Area.
The simple life was okay for a little bit, but bartending at a 3:2 beer bar and skiing every day wasn’t as fulfilling as I’d hoped. I cut the season short and moved to Los Angeles in March with my partner at the time. We had a mutual friend with an open room in Hollywood, and I was starved for city-living. (I have since learned that LA is not the city-living I expected, at all, but that’s another conversation.)
Time to Get a Job (for real this time)
I formally announced I was back on the scene, reached out to old clients and people from my New York network, and was even on a podcast out of the gate. None of that translated into much paying work. Luckily, I had a cushion of savings to float me for a few months (Freelancing Rule #1: You must have savings), but my heart just wasn’t in the freelance hustle this time. The prospect of negotiating contracts and engaging new leads was nauseating rather than exciting, and the small business website work I did was no longer the challenging and invigorating experience it had been before.
I decided to get a full-time job, for real this time. Once again, I wanted to work on a team and on bigger projects. I was tired of doing everything myself, and I wanted to learn from and share my experience with others. And, you know, a regular paycheck.
I set to work applying for jobs, putting long hours into carefully crafted cover letters. I had several promising interviews, got my hopes way up a couple of times, and received zero job offers. For one particular role, I’d gotten as far as discussing salary requirements and start dates, and was expecting an offer letter within the week. Then, the next week they were all of a sudden no longer hiring. I didn’t run into any FizzBuzz, for better or for worse.
I started to question why my designer/developer skillset appeared to hold so little value now when I’d felt so in demand just a year ago. I stubbornly refused to learn React just so I could have it on my resume—I’m great at other important things, why can’t people see that?! I wondered whether the five years of self-employment was a hindrance, or was there something fundamentally wrong with how I interviewed? Did I shoot myself in the foot with this whole „non-unicorn” thing in the first place?
These months were a major ego-check. It turns out, full-time jobs aren’t something you can just „get.” It’s just not that easy, for me at least.
The Value of HTML and CSS
Responding to job posts with those carefully crafted cover letters had a very low return on investment so I decided to change my approach. Instead of putting my time into writing said cover letters, I would focus on writing about real things and becoming a better developer, and the jobs would come to me. I launched a well-thought-out redesign of my website, published a Reverse Job Post, and buckled down on my JavaScript studies.
This was right around the time Mandy Michael wrote „Is there any value in people who cannot write JavaScript?” which hit the nail on the head. I wrote a question into ShopTalk show about this phenomenon and mentioned to Chris that I’d love to come on the show and talk about it if they’d like. The next day, Chris invited both Mandy and me to come on the show and hash it out:
HTML and CSS are valuable, but intimate knowledge of them has become more of a specialist role. Perhaps, one can position their skills as HTML, CSS, plus something else (e.g. UI design or WordPress). The nature of products and rapid feature releases deem quality HTML and CSS an afterthought at many companies so at the moment, maybe the demand just isn’t there. Perhaps the rise in accessibility awareness, design systems, and time lost debugging bad CSS will change the tide?
The episode was well received; I was obviously not the only one struggling with this issue. I made a Github repository called Front-end Discourse with the intention of gathering and synthesizing opinions and coming up with a plan of action on the job titles front. Chris even wrote about the job titles conundrum here on CSS-Tricks. The momentum was there; this could be my thing!
But then…I let it die.
An Unexpected Twist
A few days after the ShopTalk episode came out, I received this tweet:
Umm…that’s a link to a Google job post.
I thought it was a joke at first, but nope, the tweet author sent me an email later that day, and it was the real deal! They’d been referred to me by a benevolent figure in the web industry whom I’d never met. I had a call with them and another member of their team, and it was magical. They told me all about a new team starting within Developer Relations at Google that would be working to improve the „Web Content Ecosystem.” Web Content Ecosystem? That’s WordPress! And they were recruiting me! Holy sh#t, this actually happens!
This was my dream job, not a front-end designer/developer role. I didn’t even know this was a job! I had already been doing this work on my own time for several years: teaching and speaking about WordPress, writing informational blog posts, recording videos, and helping people use WordPress more responsibly. And they would move me to San Francisco! I was not a huge fan of Los Angeles.
Unfortunately, Google doesn’t just „give” people jobs…you have to interview.
Computer Science Bootcamp
Now we have me, the designer who applied for a JS job and failed FizzBuzz, preparing for the Google interview otherwise known as the grandparent of all technical white-boarding interviews. It was time to swallow any feelings I had toward this interviewing style and get to work.
I had three weeks until a „coaching call” that would unofficially determine whether or not I could skip the technical phone screening and jump straight to the day of on-site interviews because, duh, this was meant to be. Luckily, this coincided with a lull in freelance work, which had also been picking up, so for about a week and a half, I put myself through a self-directed computer science bootcamp. On the way, I wrote a bunch of blogposts about what I learned.
Oh, how I longed to write that Tales of a Non-Unicorn: I GOT A JOB AT GOOGLE, F@#KERS!!! follow-up for all those Reddit haters after it was said and done!
The day of the coaching call arrived, and it was fantastic! I was a little slow on the coding question, but it wasn’t as hard as I’d thought, I aced the role-related questions, and the interviewer was excellent. I heard back from the recruiter who was coordinating with me, and he said I could go straight to the on-site interviews.
In the meantime, I went to WordCamp US in Nashville where this particular team at Google was a sponsor. I got to meet a few of the folks I’d be working with, and it seemed like such a great fit. This Google interest and being at WordCamp made me question why, at the beginning of my job search, I had seen my knowledge of WordPress as such a secondary skillset. WordPress is everywhere! And its awesome! I mean, sure, it’s not that „cool” yet, but mark my words, it will be in the „cool” ranks soon enough.
The Non-Unicorn Interviews at Google
In the week leading up to the interview, I focused on researching the role and beefing up my passion for improving WordPress and helping those who work with it. This was not a software engineering role, after all; in Developer Relations, passion for and knowledge of your subject is more important than knowing binary tree traversal, right?
Google flew me to San Francisco and put me up in a nice hotel. I had a full day of four interviews—usually, it’s five, one was canceled—and a long, enjoyable lunch with the folks I’d been in touch with from the get-go. I didn’t feel great about my performance in the technical parts of the interviews, but I did my best and my strategy was to come off as a great coworker who knows when to ask for help. When in doubt, I remembered the strong correlation between „hard interview” and „received offer” on Google’s Glassdoor profile.
Back in LA, freelance work kept me busy while I waited for a verdict, which wasn’t long. I felt relatively zen about the whole thing. Yes, I had my hopes up, but if it didn’t work out, I at least had work to pay the bills, and it wasn’t going half-bad. I’d been contracting with an agency and learning a lot; it wasn’t the small business WordPress sites I’d been building all by myself previously.
The Thursday after my Monday interview, I got a call from my recruiter contact. They were not going to proceed with the approval process at this time. He said I showed some very promising „Google-y” qualities, but my performance in the coding portion of the interviews wasn’t strong enough. He said he had it in his calendar to reconnect with me in six months, and that he would keep an eye out for less technical roles that might be a better fit.
…oof.
Incredibly, I was able to fend off the majority of the anger and the „I’m a failure and I suck at everything” thoughts that go hand-in-hand with rejection, maybe in part because I received such a nice email from one of the people I’d been in touch with throughout the process. He had applied three times before he got a job there—which apparently is not uncommon—and this simply meant I’d be taking a slightly different path. They were all bummed I didn’t make it.
This brings us back to the present. I don’t feel sour about algorithms or white-boarding interviews…I have another one to get ready for in six months! Unless, of course, another really awesome opportunity comes my way in the meantime. Who knows.
This whole job search has been such a ridiculous roller coaster of hopes slowly going up then crashing down. If there’s one thing I’ve learned, it’s that I still don’t know where I’ll end up, but I’m doing my best and I’ll keep doing it until the right thing comes along.
</story>
Whew, that was a lot! Thanks for making it this far. A+ for you, reader!
Post-Mortem
Before I wrap this thing up, I want to make a few observations about this whole job searching process that I hope can help others on their roller coaster ride.
Algorithms and white-boarding interviews aren’t necessarily bad. I think they can be implemented badly. The Big Tech Companies are fully aware that they miss out on great candidates because of algorithm questions, but this interviewing strategy is so good at filtering out bad candidates that they keep it around. It sucks for us, but I don’t see that changing anytime soon. Plus, I learned a hell of a lot of stuff preparing for it, and it’s made me a better developer and better human being.
Write a „Reverse Job Post.” I don’t recall where I learned about it, but here’s mine for reference. Even if no one reads it, it’s a great way to figure out what type of job and company you are looking for, and you could totally paste a link to it in the cover letter field for an application and call it a day.
Learn computer science fundamentals. I know we are already inundated with things to learn, so it’s hard to preach this, but having context for what the tools we use actually are has helped me a lot. For example, two months ago I would have had a hard time wrapping my mind around GraphQL, but in my interview preparation I learned about graphs and tree data structures, so I was able to understand the concept relatively easily. Cracking the Coding Interview is not a good place to start, BaseCS and the Impostor’s Handbook are. Also, stay tuned for some relevant articles here on CSS-Tricks, from yours truly!
Don’t spend all of your time on job boards. It’s a crapshoot. I think there are great job boards, but in general, no matter how quality the listing, whether or not the position is actually available or accurately represented in the post is a toss-up.
Be vocal. I doubt any of this Google stuff would have happened if I hadn’t written into ShopTalk show and asked Chris to have me on the episode. If you have an impulse to write something or have a question or feel the urge to tweet at someone you don’t know, do it (but be a good person about it, obviously). The more web people that know you exist, the more likely it is that something will come your way.
Those are some things that helped me, but I still don’t have a job, so maybe don’t listen to what I say. I don’t know. It’s an incredibly difficult and demeaning process, and there’s no secret sauce that works for everyone. Our industry is a young one, and as far as I’m aware, there is no such thing as a surefire career path in web development.
I hope I don’t write another „Tales of a Non-Unicorn” installment. The whole idea of a „unicorn” is bogus, anyway. We are all just people, with different levels of knowledge in different areas, and if you can honestly say you’re doing your best then I think that’s all you can do.
What I will be writing, however, are some „Computer Science Study Guides” for the self-taught developer, here on CSS-Tricks, and maybe some stuff about how cool WordPress is nowadays. At the very least, „Intro To Algorithms” will be coming at you, soon!
How about you, reader?
Have you been on this roller coaster ride, too? Where did you end up? What advice can you offer to those of us who are still in the midst of our journey?
It used to be that designers designed and coders coded. There was no crossover, and that’s the way it was. But with the advent of CSS transitions and animations, those lines are blurring a bit. It’s no longer as simple as the designer dictating the design and the coder transcribing—designers must now know something about code, and coders must know something about design in order to effectively collaborate.
As an example, let’s say a designer asks a developer to make a box bounce. That’s it—no additional instruction. Without some cross-knowledge and a common vocabulary, both sides are a little lost in this communication: the developer doesn’t have enough information to fully realize the designer’s vision, but the designer doesn’t really know what the options are and how to communicate them. With a very basic interpretation, you might end up with something that looks like this:
Not very exciting. Although, to be fair, this does meet all of the criteria given. We can definitely do better than this, though.
The first thing to look at is the timing function. In the above example, we’re using a linear timing function, which means that the box is constantly moving at the same speed. In some cases, this is desirable; however, in the real world, motion usually doesn’t work like that.
An easy fix is to simply change the timing function to ease. This makes the beginning and ending of each animation a little slower than the middle part, which adds a more natural look to some animations. Here’s the box with the easing function turned on:
This is a slight improvement, but there’s still a lot of work to be done. The box still looks mechanical and stiff, with the same animation occurring in the same timeframe over and over. Adding a slight delay between bounces adds some visual contrast that seems a little more natural:
The box now looks like it’s jumping rather than simply moving up and down. There’s a little wind-up and cool-down between jumps that mimics what a live creature might do if given the same instruction. Even though we have no reference for what a jumping box would look like, we all have a pretty good idea of what a jumping creature would look like. Because we know what would happen in nature, by mimicking that, the animation feels more natural. But we can do more to make that wind-up feel a little more weighty.
If you watch cartoons, you’ll notice that natural movements are often exaggerated, creating a caricature of real life. When done well, this can feel just as natural as something in the real world, with the added bonus of infusing a little charm and character into the animation.
At this stage, collaboration between the designer and developer is crucial — but many designers may not even be aware that these options exist. It may be up to the developer to pitch this possibility to the designer.
By adding some subtle distortion to the scale of the box, we can add a lot to the animation:
Now, the box has character. It feels alive. There are many things to tweak, but this is already moving much farther than the original instruction — in a very good way!
We’re going to go a step further and add a little rebound at the end of the jump:
The second bounce is making this feel more alive, but something still seems off. The bounce looks stiff compared to the rest of the animation. We need to add another bit of distortion like we did for the wind-up:
That subtle distortion at the end makes the rebound seem much more natural. Overall, a huge improvement from our basic linear bounce in the first example.
That right there may be exactly what we’re looking for, but further tweaks to the rate of movement can be made with a custom cubic Bézier curve:
Without both the designer and the developer aware of basic animation principles and controls, this level of customization is impossible. Really, this article just scratches the surface of both fields. If you’re a web designer or a web developer who works with designers, I’d strongly urge you to read up on both.
For animation principles, The Illusion of Life: Disney Animation by Ollie Johnston and Frank Thomas is a great primer on how to make that caricature of real life seem alive and real. With that common language in place, communication and collaboration between designers and developers becomes much easier.
For the technical controls and variations of CSS animation, the possibilities are nearly endless. Delay and timing are simple to adjust. As mentioned, if you don’t like the out-of-the-box ease timing function, it’s very possible to create your own using a cubic-bezier(). You can also adjust the level of distortion you want to bring the animation closer to or further from reality. The important thing is that both the designer and developer are thinking about these variations rather than blindly taking everything without customization. Shared knowledge and collaboration can make even simple animations into great ones.