Placeholder Image

字幕表 動画を再生する

  • uh, I'm here to talk today about I actually regret name of my talk, little bit advanced design systems considerations, mostly because it's a mouthful.

  • But also, I mean, advanced less like, uh, advanced math and more like advanced osteoarthritis or something, right?

  • Huh?

  • I want to talk about what the work is once you convince everyone at your company to use your design system.

  • And once you're done building out all the name brand components s o, I work, it's stripe on our design system.

  • Team were two designers to engineers and a manager for a total of five people.

  • And I just found out from Wikipedia.

  • I promise this is true.

  • That stripe is over 2000 employees now, so that's a heck of a ratio of 1 to 5.

  • That's the goal, right?

  • For design systems, their leverage dedicated team of four individual contributors can abstract and maintain the design language and technical implementation for a component library for 2000 people.

  • Now they're going.

  • It's good.

  • It's I think, uh, I think it does a good job.

  • Uh uh.

  • It's not magic, despite, uh, my most sincere efforts.

  • That was a great talk, by the way, uh, we think we create more value than we remove.

  • I believe in our goals.

  • And I think my coworkers and teammates on this team are some of the most thoughtful and capable people to be working on this problem in existence.

  • Uh, so we've done nifty work on accessible color systems, applying a lot of magic, uh, choosing one and we made building consistent strike looking interface is a little bit easier, and we have some or another version of just about every component that you can think of often to our detriment.

  • Uh, this is massive work.

  • Design systems are hardly a new concept.

  • You don't look much further than an old NASA graphic standard manual from the sixties and seventies to find cool, cool design systems.

  • But there are very new challenges, especially technical ones that compound on the old challenges.

  • The complexity is multiplied.

  • Robin Randall recently wrote an essay that compared design systems to the idea of hyper object, and that idea resonated with my team very strongly on me.

  • He's referencing a book by James Bridal called The New Dark Age.

  • It says, Ah, hyper object is gonna read to you a thing that surrounds us envelopes and entangles us that is literally too big to see in its entirety.

  • Mostly, we perceive hyper objects through their influence on other things.

  • A melting ice sheet dying.

  • See the buffeting of a transatlantic flight.

  • Hyper objects happen everywhere at once, but we can only experience them in the local environment.

  • Fact that stand outside both our perception and our measurement.

  • They exist without us because they're so close and yet so hard to see that fire ability to describe them rationally and to master overcome them.

  • Traditional sense climate change is a hyper object, but so is nuclear radiation evolution on the Internet.

  • I agree that's very dramatic.

  • Design systems are not climate change.

  • They do often feel like sneakily complex systems, like no single person can hold the whole thing in their head anymore.

  • It's like trying to figure out what shape the crop circle is from inside the cornfield.

  • You can spend an incredible amount of time softly tackling an issue, only to zoom out, zoom out again, just to see that you're working in a tiny subsection of a tiny subsection of your design system.

  • And that idea really sums up a lot of the work that's involved in the second and third waves there need to be put into a design system.

  • It's all about trying to make the entire thing useful, while all also making any arbitrary subset.

  • Equally useful, did not require each person each user of the system toe hold the entire thing in their heads.

  • There's, of course, lots of information that exists on how to create a design system, their books and tutorials and had a jump pass a lot of the difficult pain points.

  • That's not my focus here, but I certainly would be lost without all that prior art, so I'd be happy to recommend some of that.

  • If you want a chat later, you first get started on design system.

  • You have some fundamentally different and often opposite goals is when you're trying to level up on existing design system.

  • When you first get started, I want to make lots of new components.

  • Your goal is coverage.

  • You want to maximize the number of designs that are possible with your system.

  • You work on selling people to use it versus rolling their own components are doing one off designs and you actively seek real estate in your applications to see what you can replace with a cleaner design system.

  • Version of the thing.

  • You want people to be excited about using your design system.

  • Once he hit critical mass of adoption.

  • Your goals are to start your goals start shifting pretty quickly.

  • You worry more about keeping the system healthy and alive, not about selling its value directly.

  • You fight to make sure you don't become too dated, but for the most part, it a stage where your goals to blend into the platform.

  • One of my favorite 2019 goals on my team that stripe was that another team would announce a conversion of their application to our design system without thanking us at the end of the email.

  • Our goal was to become part of the expected platform rather than an exciting tool that people have to think a lot about.

  • It happened is both frustrating and very exciting.

  • Um, another surprising change in the second phase, uh, that were you once judge yourself on how many components you added in 1/4 you start valuing the opposite, whether it's crafty, old components that never did the right thing anyway Oh, are super specific components that could probably be achieved by customizing generic ones.

  • You quickly appreciate the things that reduce the system complexity.

  • Your primary goal stays.

  • The same is poor, though it's provide a system that it used to your values.

  • So the resulting you guys here to your values Really common design system thing I see sometimes even attached toe goals for your business metrics or something is the desire to add components in perpetuity.

  • I think this happens for two reasons.

  • First is the idea that the more components you make, the faster it will make developers and the more useful the library will be.

  • I think this assumption comes from a good place, but I've never seen it play out in practice.

  • Very solid core of atomic components could be well understood and composed and recomposed by your users and unlimited permutations.

  • You build them well, you won't have to fit new ideas into old components.

  • Faulty assumption is that having a component that does something close to what you want makes you faster.

  • But when I think back to the most frustrating waste of time in my career, it's almost always in trying to configure some mega component to do one thing that it wasn't quite designed to do.

  • So fight for atomic components doesn't mean your applications shouldn't make their own logic list complex, non non atomic components that they share between theat.

  • But it just means that those components probably shouldn't live in your design system.

  • The other reason I see engineers continuously add components is that they actually have a secret desire to rewrite the things that they don't own at the company.

  • I know this sounds like a conspiracy theory, uh, and I'm sorry for that, but I'm gonna keep going.

  • Uh, it does follow a pretty natural evolution.

  • First you fix all the buttons and then you fix all the menus and tabs and chords, and eventually you're out of, ah kind of the atomic seeming components.

  • You still want things to look better.

  • And so instead of stopping, you find yourself searching for any patterns that are used more than one time to turn into components.

  • Here's a person card and a detailed person card.

  • We could kind of smash those together and and retake that land.

  • Suddenly, they're pretty business specific and pretty application Pacific, Uh, and then you want the pricing page toe look nicer, but it's so entrenched in the old stack that no one will touch it.

  • So eventually throw off all pretenses of component re use, and you build the pricing banner component throat in the design system and then replace it so you don't have to look at it anymore.

  • We have.

  • I have.

  • The 37 has these urges, but I'd recommend you work these things out or get organizationally rather than declaring manifest destiny on other teams.

  • Technical debt.

  • You like your design system, or, in the end, I want to dig back into The first point I brought up there, though, is this common perception of design systems that they're intended to increase efficiency?

  • I don't think this is entirely wrong, but I think efficiency is a secondary goal of a design system.

  • The primary goal of a design system, in my opinion, is to uphold your values design systems air so you can ensure that when a developer is making tradeoffs to ship something before looming deadline, that that thing falls off the chopping block, that the thing that falls out the chopping block isn't accessibility performance or visual consistency or all attention to detail design systems air tools to uphold the quality of your product, even in the face of consuming teams that aren't paying particular attention to quality design systems.

  • Successful when someone can throw together a quick, a quick application and why, while that application may fail to achieve the specific business schools, it's still upholds the values that are otherwise left behind in crunch time.

  • It's accessible, consistent performance.

  • Whatever else you've decided, it's important to you.

  • One of my first actionable recommendations is to fight against the wrong contextual specificity and components.

  • It's very common to end up with a lot of similar components that often do almost the same thing on maybe even describe, the context that they're used in icon, but a Nikon action Icon menu icon are seemingly icons.

  • Ah, it's also common to recognize this complexity and then move everything over into a single component on and you end up with kind of like an explosion of props that all do something very specific on Lee.

  • For one use case, you can't always avoid one of these traps, but we want to move in a direction that tries to allow the context dictate the difference is not a bunch of problems s so let's see if we can contextually create a button icon, which is the one at the top there, without actually needing a component like that.

  • You notice.

  • In this example from the stripe dashboard, we have two icon types visible, uh, one icon inside the button and one outside.

  • They're mostly the same, but the one inside the button is 12 pixels, and the one outside the button is 14 pixels.

  • That's what I mean.

  • They're all so different icons.

  • But relax.

  • Uh, I'd expect many people's first generations to look something like this.

  • Um, we add a prop directly to button to declare the type of the icon would like it to contain icon equals gear.

  • You can imagine it puts a gear into the icon, But then we recognize that in order to change anything about the icon, we'd actually need to duplicate all the props from icon on the button s O.

  • If you wanted to change the size, we'd have to, like, add an icon size prop.

  • There are an icon style prop to grab them all that's possible, but, uh, not pretty.

  • It stands out to me.

  • That button also must now import icon whether you use it or not.

  • So let's try another approach to try to separate them.

  • But it directly inside the component like this s.

  • So now we put an actual icon inside an actual button.

  • This is great and we could be done.

  • But like I said sadly, icons are 14 pixels by default and the icons inside of a button 12 pixels by default, we could make a rule that says all developers must remember to change the size to 12 when they put an icon in the button.

  • But we all know how well that would go.

  • Um, our complexity of our system is leaking out.

  • We have a dependency between button icons that we're not describing well, so rather than required each developer to remember this on their own, we could make a new component that's mostly an icon, maybe even wraps an icon but sets the button defaults instead of the regular icon defaults.

  • In this case, being 12 picks is, but we're back to button.

  • I think in this is this is where we started.

  • This is the hyper object in action user of our system has to know about all the quirks involved in icons versus button.

  • Icons know that they want to put an icon into a button, and they have to actually use a different type of icon, not an icon itself.

  • Then they have to learn the specific thing about the system.

  • They have to hold AA lot more in their heads in order to use it.

  • Also, what happens if someone doesn't know about button icon and just jams an icon in there anyways?

  • Then you are mixing 14 pixel until pixel icons, uh, Shane, uh, one approach to solve this, uh, that we could take the summer in the middle of the two solutions.

  • Eyes allow regular icon to be passed into the button, but make it a problem.

  • Uh, rather than something that goes into the Children.

  • The button can safely override the icon.

  • Add the 12 12 pixel size before injecting it into the Children inside the code.

  • This was initially pretty attractive to me, but I think it's still leaks.

  • Complexity back out to the user.

  • We still have the initial problem where we have to add special icon props.

  • Um, like I composition starts to be an issue here on.

  • We still don't prevent someone who doesn't know about these props from just jammy and icon directly into the Children.

  • Ah, we can fix that problem kind of paper over a few more by getting rid of Children entirely.

  • UM, which, which is a technique that is often used.

  • We could replace the functionality with a label prop.

  • It's not.

  • It's not pretty, but it feels like it probably meets our goals in this specific case.

  • But maybe not many others.

  • I don't feel great about this.

  • It feels like Button just got a whole lot of clear on Dhe.

  • Using entire system feels less regular.

  • I think as a user, I might be compelled to just skip using the design system button and kind of roll my own.

  • I'll make one myself my point.

  • We have to work backwards from the Gold State.

  • Users can reason really well with their original solution section, not original solution.

  • But the second solution, uh, just put an icon inside the but you don't need to know anything about the system in order to write this.

  • This is just composing two atomic pieces, possibly the only too, You know, um, and if it did what we wanted, this subsystem would feel closed.

  • Uh, we have to just solve the problem.

  • The eye country be smaller when it's inside of a butt.

  • What do we do that it seems like they have to either make icon aware of when it's in a button.

  • We had to make button aware of it when it contains an icon.

  • So let's try the letter inside of a button.

  • You know, howto actually read this too closely.

  • We can enumerate each of the context that it knows about to try to render something different and adapt to its surroundings.

  • We have this kind of thing that I'm obstructing out called isn't but is this icon in a button.

  • It's not ideal if we can be rendered into multiple things.

  • There's this combinatorics logic of Am I in a card and a button and a something on.

  • It just explodes.

  • Also like, Are we doing upwards treat reversal in order to determine that it seems all pretty plainly not nice.

  • Here's a gold ST again just to try to recent dress.

  • Let's try flipping.

  • Who knows about who?

  • Maybe we can make the button find and change icons that air inside of it to be a smaller size.

  • Uh, this is actually pretty similar to our real first, uh, idea where we just added an icon prop.

  • And and that felt pretty natural.

  • But it's not a great solution for the same reason, because Button needs to know about and possibly even directly depend on icon.

  • You get some weird code like this, we have to import icon from the button, and then you have to search down into the Children to see if it contains icons like this is clearly maybe not.

  • Ah, very tenable solution about his ugly of accompanying as I could think of.

  • Actually, uh, I know I could be less obviously silly and write some CSS.

  • Um, this is, uh, better.

  • Um, but it's still pretty sad, because now, regardless of whether we need an icon or not, every time we pull in button, we also have to pull in all or part of icon, become someone clear that try and resolve.

  • This, uh, is our primary objective.

  • Sorry.

  • Uh, our primary objective is to decouple these two components.

  • Neither should depend on the other so we want to create relationships without encoding strict dependencies.

  • This is, Ah, theme.

  • This is pretty similar to the goal in de normalization in databases, so two models share common value, so we can either have them fully depend on each other being the same rose each other.

  • Or we can create a reference to a shared value, kind of like a foreign.

  • Keep.

  • To solve this, we've added a new concept to our design system.

  • Encapsulate the same idea.

  • It's a shared value.

  • He's a weak holly values tokens.

  • You don't have to, uh, certainly an overloaded term.

  • It's a tiny share dependency that holds a value, remembers the context that's set in.

  • In this case, it determines the size of an icon.

  • Either component is free to write or read from the value or stop doing anything with the value at all.

  • Um, in this specific case, we have icon size token.

  • It's 14 pixels by default.

  • Icon would use this value, determine its width and height and button would override this value for any of its Children.

  • So looks like we have an icon inside of a button, and it's going to read the value through the context of button and see that it's 12.

  • So this is our solution.

  • It also means that you can delete button entirely from your application and things keep working.

  • Or you can delete icons from your application, maybe have a weirdly named token, but everything stays working.

  • And neither file, uh, depends on on the other.

  • We still have a directed a cyclical dependency graph of the the old Dag.

  • Uh, for my graph nerds out there, uh, so these air now atomic components again, our final solution doesn't look very interesting to an end user.

  • That's the goal.

  • It's exactly this first most natural idea that we had before.

  • But now, thanks to the token, the token that encodes the relationship of a shared value user doesn't have to worry about the icon being the wrong size in the wrong spot.

  • And they also don't have to bring along their own icon.

  • Just whenever they import button, they only carry tokens.

  • They encode relationships without creating strict dependencies.

  • Our goal in separating buttons and icons like this is to make sure that each component isn't reliant on the other token ideas.

  • Just one illustrative part, not some silver bullet of creating system that doesn't leak complexity all over the users theme that arises when you think about these concepts is decentralization.

  • If your goal is to be able to avoid needing the entire system in your head, but it makes sense, the decentralization becomes a critical property of things you had to the system.

  • But centralization.

  • It's difficult to avoid, and it can be very sneaky on invite you from all over the place.

  • Consider the button and