1. 37
    1. 13

      Yes, the vast majority of customers use less than 10% of the features of the Microsoft Office suite, but it’s a different 10% for each customer.

      There is another layer on top of this, too – I think the author is being very charitable towards these “lean” alternatives, and the lean-base-with-complex-extensions model.

      I know a guy who worked on a bunch of cool microelectronics-related CAD/CAM stuff way back in the eighties. By his own recollection, that period was pretty gruesome, as the market was still fairly volatile and everyone was rushing to add new features and keep up with developments on the manufacturing end, and computational power was not exactly cheap or plentiful, either.

      It’s not just that a lean program that only did “the necessary 10%” was a tough sell because not everyone used the same 10%. It’s also that the 10% at the customer end is rarely static, as it tends to expand along with their activity. So even if your software did just “the necessary 10%”, and you have customers who use like 10% of that, unless you keep up in terms of capabilities, it’s only a matter of time until they’ll expand to just 1.1% of what $market_leading bloated software does. That 1.1% in turn will consist of the 1% that yours does, and an additional 0.1% which it doesn’t, is critical to their new endeavours, and will absolutely prompt them to switch, unless you’ve locked them in with terrible licensing, muscle memory and lots of money sunk in training and workshops.

      But there is something worse that you can do besides shrugging that extra 0.1% off as an irrelevant niche case that can be easily implemented through extensions. You can, in addition to that, focus development effort on “reinventing” that 1% to make it “streamlined” it and give it a “modern touch” and so on. When you do that, you throw “good” lock-in factors (users’ accumulated expertise, continuing education etc.) out the window, and you’re left with are the bad ones (licensing, unportable data formats, poor migration workflows). That quickly turns happy customers into grumpy, hostile Grinches – for entirely legitimate reasons! – who will absolutely ditch your shit the first chance they got, because if they have to throw away most of what makes them productive, they might as well throw it away in favour of the thing that does all they need.

    2. 10

      A design pattern I like (yes, I know that it has huge drawbacks, and OP (fantastic post, btw) gets into some of them, like “Users cannot use a feature if they haven’t discovered it”), is this:

      Have a simple interface with the most common settings and doodads, and then also provide your about:config, your Regedit, your .emacs, your User Script, your .zshrc style more advanced level conf settings.

      I know that Donald Norman famously argued against this pattern in The Design of Everyday Things using the example of some stereo (or whatever it was) that looked simple on the outside but hid away some arguably pretty everyday stuff mixed into a complicated array of thingamajigs under a panel.

      His main schtick is that every function should have one widget, a one-to-one mapping. And that’s great for everyday things, but not for systems. And arguably Emacs or a browser or even a VCR is a system. (I think some stereos are systems too.) The VCR I had in my first apt had a wonderful UX with easy&common button and weird power-user buttons on the back. The same pattern that was such a catastrophe on Norman’s stereo ended up being implemented better and worked better on the VCR. (My take is that that stereo had culled too much, i.e. been too trigger happy with what it moved behind the panel, while the VCR did a better job at making the front panel reasonably complete for basic stuff.)

      Make easy things super easy and make unusual things possible albeit a bit “under the hood”. Yes, this risks falling into the “but they all use different 10%” trap but there’s hopefully a pareto principle here where most people only need to go into the Cumbersome Jungle for a handful of things, or for nothing. Maybe among all those different 10%, there’s a core of stuff that most people do (editing in an editor, browsing in a browser, listening to music in a music player) and making that core more immediately accessible and uncluttered can be pretty good.

      The English language is actually set up similarly. It has a couple of closed word classes, like articles and prepositions, (there’s not gonna be a new “the” any time soon) and a limitless amount of verbs, nouns and adjectives.

      I’ve always like the Alternate Hard and Soft Layers pattern and this reminds me of that in spirit if not technically. There is this curated interface but you also ship a loosey-goosey layer of “🤷🏻‍♀️ we trust you, go ham” flexibility that you can access if you just scrape the surface a little bit.

    3. 5

      To the extent possible, features must be pay to play. If a user isn’t using a given feature, it should not impact performance, security, or reliability.

      It’s worth explicitly calling out the supply chain here. If a feature is adding to your list of dependencies, it’s not pay-to-play.

      1. 2

        I dislike such blanket pooh-pooing of dependencies. There are plenty of fantastic dependencies that give you advantage of other people’s time and expertise. Even for not-so-fantastic dependencies it’s very often much quicker to review their code than to write your own from scratch. Your own code is a liability too, so you have to weigh on case-by-case basis whether risks and benefits of a dependency are better than your own development and maintenance cost, and your lost opportunity on reinventing something that has already been done.

        1. 2

          My statement is in OP’s frame of reference to the point of tautology, so I don’t understand what blanket pooh-poohing you’re reading into it. If you write your own code you’ll be more likely to know if somebody inserts malicious code into it. You don’t need to download it from a third party, subscribe to a new mailing list for security patches. Therefore you’re introducing a new kind of risk compared to ambient first-party liability. If it’s doing so for a reason only a subset of your users care about, it’s not pay-to-play. All your users are paying the cost. This reasoning isn’t helped by a disclaimer about how fantastic some possible dependencies might be.

    4. 7

      I miss the times programming blogs/websites had this high standard. Articles with loads of information. Everything analysed pragmatically, from multiple angles, comparing the pros and cons, without an agenda. So much wisdom in this article!

    5. 4

      I quite agree with these thoughts. When I have a program and need an extension to get it to do what I want, the first thought is “How can I know that this extension is safe to use?”. And since it’s hard for me to judge that, there’s always a bad feeling when installing an extension. I am a fan of small and simple programs, but then sometimes I also value a program with lots of features of which I only use a few which are lacking from the simpler competitors.

      I would say it is a similar trade-off as in other situations:

      • Monolith vs Microservices
      • Programming language with large standard library or with all libraries as external packages
      1. 4

        The concept of being “safe to use” is multi-faceted and applies to built-in features and extensions equally, and that can only be answered by careful code review, if at all. The only facet of it that is almost always unique to extensions is whether it’s intentionally doing anything malicious. Everything else has many degrees and I’ve seen examples of built-in features being completely unstable and risky to use.

        “Will it work as advertised” is a universal concern. Extensions by definitions can be guaranteed to meet the standards of the host program maintainers, but different areas within the same codebase can also have vastly different quality and maintenance activity level.

        “Will it still work in new versions” isn’t a trivial question either. Some programs have very stable extension APIs, while others will casually break their built-in features as well. Even prior history of compatibility isn’t always indicative: if you aren’t actively watching a codebase, you never know if there’s a big rewrite/redesign on the horizon.

        I agree that on average, it’s safer to count on built-in features than on extensions, but nothing is absolutely so.

        1. 6

          The concept of being “safe to use” is multi-faceted and applies to built-in features and extensions equally

          The aspect of this question that deals with how much risk you are taking on that the feature might contain malware, isn’t the same for first party and third party code. You’re already exposed to the first party anyway because you’re running their program. But the third party vendor is a second separate entity that might be malicious or not, independently from the first party. Having two vendors involved gives you two opportunities to get betrayed.

    6. 3

      I perceive the two terms orthogonal. ‘Batteries included’ to me means you can immediately start using it. Without unmet dependencies (= missing batteries). While ‘bloated’ means a lot of promises or weight.

      So they are not related at all and versus makes no sense.