UnsuckJS: Progressively enhance HTML with lightweight JavaScript libraries
unsuckjs.com
unsuckjs.com
The move back towards small dependancy free JS libs, in combination with modern JS ES Modules, is absolutely brilliant.
I learnt web dev back in the late 90s by doing "view source", and was still learning about new things that way well over a decade later. If we can move back towards that, by not having a build step, it will be amazing for new devs starting out and learning new things.
Obviously larger apps, with many dependancies, will require all the incredible work thats gone into modern JS tooling, but for so many simpler (and not so simple) sites this process really does make sense.
Same here, and I couldn't agree more. Had minified library soup with dynamic page content been the norm back then it would've been much harder to get started, and there's a high chance I would've just given up somewhere in the process.
Having a build step also increases activation energy and friction which impedes the sort of in-the-moment tinkering that often sparks projects.
Yes this! As an interpreted language it should not need a build step. Every project should be
git clone https://github.com/user/foo && cd foo && google-chrome index.htmlAnd the tooling... my God! I know this makes me sound like an old man (because I am) but, it used to be all I needed was an editor, an FTP client, and a browser. write-upload-refresh. Today, I find VS Code, `git push`, and a browser still serves me very well.
* slow network, especially on mobile
* reduce the size of the download by minifying
* reduce the number of calls by bundling files in a single one
* Inconsistent JS and HTML feature support among browsers
* transpiling to a common older version of JS
* add polyfills to implement missing features
* add widgets to implement fucked up default implementations or widgets that are nearly impossible to standardize (date and time pickers might need tons of features and are projects on their own)
Utility classes for uniform padding, spacing, border, colours etc at brilliant. But my suggestion with x-style is that placing the actual css on an element may be better.
It's an experiment, seeing where it leads.
I wonder if there were a better way to opt-in to "use strict" (and maybe even ESM friendliness) in onclick handlers if that would have fewer CSP concerns. I doubt there are any current proposals to build such tools for HTML, though.
As a general example, despite three decades of the web existing across the world in many jurisdictions with more than one language, the solution to translation for a site is just some translation framework or tediously maintaining a whole copy of your site per language.
Literally anything that'll render HTML will suffice. Even static HTML files on a web server will do. No need for an application server at all if you're clever and your needs are simple.
You can make the left pane a list of links to dedicated pages, and then add an htmx attribute to indicate that when the user has JavaScript to instead fetch a html snippet with just full article and swap it into the right pane.
If you had a reasonably bounded set of articles you could statically generate all the /article/id.html and the /article/id/snippet.html files, though a backend probably makes sense.
Certain things like Nav menu drop downs and folding text can’t be done with native CSS and HTML.
Here’s an example: https://codepen.io/daviddarnes/pen/abVaGG
I love that the cognitive overhead for web apps now is so great many people are "returning to monke" and coding in simple HTML/CSS/JS haha.
Question: Shouldn't the items be in the row so I can see all of them at once? Why are the items in the columns? I'll open a issue (:
!React = HTML/CSS/JS
¯\_(ツ)_/¯
Maybe! I was messing with different UI approaches to relay this data and this made sense to me, but I'll see if switching to rows is more clear. Thanks for the idea!
Same. Somebody said it was done this way because of mobile. I'm not sure.
It's just weird to see "items" horizontally and properties vertically. I'm usually familiar with:
prop | prop | prop
item | value| value
item2| value| value
...IE11 hasn't been relevant on the public-web for at least a decade now, and I'm fairly sure it's now entirely gone from corporate/enterprise situations now too, given MS' even-more-aggressive-than-usual campaign to kill it off in Feburary of this year: https://www.cnet.com/tech/services-and-software/rip-internet...
...why is that there? It's weird - it's like saying iPhone 14 is not compatible with 30-pin dock-connectors.
It's also supported in Windows 10 LTSC versions for large companies.
IE 11 mode for Edge is also supported until at least 2029 on all currently in-support Windows operating systems.
So it can be very relevant if you have legacy systems that still need to be maintained.
Before I get an onslaught of downvotes: my wife is a Nurse Practitioner and her and literally every provider she knows that I have met agrees that our healthcare system is backwards, inefficient, and anything but caring for or about peoples health.
I recently moved from Gatsby, which did that — and the transitions sure are instantaneous — to Astro, which outputs plain HTML pages. Each navigation is a request to the server. Yeah, they take a touch longer. But the response is tiny.
You could always `preload`?
I worry that Astro is adding too many features and trying to become Gatsby. No thanks!
As for Astro vs SvelteKit, I generally prefer Astro's approach to filesystem based routing (no +page etc.), I prefer it's MPA approach to the clientside routing SvelteKit and others use OOTB, I like that it's very tailored towards content and being an SSG (content collections, MD and MDX support ootb, currently experimental automatic image optimization), and the "integrations" are a huge time-saver. Some common ones you can add with `astro add`, and many others are just a quick config edit away. I recently built a pretty performant portfolio site with Astro in a single day using DecapCMS and UnoCSS, both as integrations, all the client had to do was accept the invite from Netlify Identity and start adding content to their site!
I just prefer the DX of Astro and MPA routing instead of client-side.
No?
Oh yeah, I forgot that Web Components are a terrible idea that are only marginally successful because they can claim to be a “standard” when they’re not any more standard than any other JavaScript.
The new paradigm in Next.js is to have "server components" by default, which only render static HTML on the server side; and opt-in to "client components", which render on both server and client.
> With Server Components, the initial page load is faster, and the client-side JavaScript bundle size is reduced. The base client-side runtime is cacheable and predictable in size, and does not increase as your application grows. Additional JavaScript is only added as client-side interactivity is used in your application through Client Components.
https://nextjs.org/docs/getting-started/react-essentials#ser...
Really??
> Not sure why everyone wants to write a programming language inside HTML like lit does
When that's exactly what the OP's suggestion of React does.
Why do you need to host this website on a server, use Docker, etc?
My personal blog is a static site using Next.js, I pay $0 to host it on S3.
To me this is less about simplicity and more about being anti JS ecosystem, and being different just to be different.
Any legacy site probably has some kind of Javascript framework, jQuery, or something set up where adding another library on this list adds complexity. Any new site that requires a decent amount of interactivity would probably be better with a battle tested framework like React. I've tried many of the libraries listed here, have tried the view engine + Alpine approach, etc, and time and time again I find it's simpler from a development perspective to just use Next.js.
That is to say, for any hobby project, use whatever you want. Try new things. But for production apps, just use React.
Originally it _was_ just HTML + CSS, but I wanted each library's repository metadata (latest version, last commit, etc) to be dynamically retrieved and doing that client-side was brittle and way too slow. So, I used it as an excuse to see how far I could push my own personal static-site framework (https://coltrane.readthedocs.io/en/latest/).
yeah, it's bigger than most of the other libraries, but it does an absolutely excellent job on progressive enhancement
source: i'm the creator of htmx
edit: PR here: https://github.com/adamghill/unsuckjs.com/pull/13
None of the others have that I imagine. If you do need a full blown single page app, Mithril takes care of it all.
In most cases, your bottleneck won't be Mithril (or React for that matter), but instead what expensive computations you're doing in your components. While React has React.memo, Mithril has the `onbeforeupdate` hook [2] you can use to memoize components if you need it.
[1] https://carlmungazi.github.io/sourcecodeadventures/posts/pat... [2] https://mithril.js.org/lifecycle-methods.html#avoid-prematur...
We can't really put all of the different ways to use Lit on the front page, but we document how to use Lit from a CDN right on the getting started page: https://lit.dev/docs/getting-started/#use-bundles
Core - https://cdn.jsdelivr.net/gh/lit/dist@2/core/lit-core.min.js
All - https://cdn.jsdelivr.net/gh/lit/dist@2/all/lit-all.min.js
It's becoming increasingly more dangerous to use anything in the GPL family for anything but the narrowest of use cases. It's to the point that, even now, if it's GPL I refuse to incorporate it, even in personal projects. And I'm not against open source... Everything I write is MIT.
I was under the impression that nearly every Linux distro uses GPL code in the kernel and/or userland.
The GPL carves out exceptions for the use of system libraries.
But, as for the "dangerous" part:
* I work in an industry in which software patents are required to survive. Personally, I hate software patents, but it is a reality until the law changes. As such, the GPL invalidates patents, making anything GPL completely off limits. That means that I would not have a job, and then there would be fewer competitors in the marketplace, which would make prices rise considerably. Too bad, too, because we would donate back improvements that are general enough to benefit others. Rather, now we just use proprietary solutions wholly because GPL is a minefield for us.
* I have personal projects. I write code that I want to use myself as well as allow others to use. I use MIT because GPL discourages that somewhat (the point above). I may want to use my personal projects commercially some day. MIT allows that; GPL makes it impossible. In other words, if I choose GPL today, I have poisoned that code from myself for the rest of my life.
In short GPL is not "free" as in freedom, because it comes with strings attached. It's communist in philosophy, but I hesitate to say that because then everybody jumps to some *a priori* conclusion of what they are now convinced that I'm saying, without listening to what I'm actually saying.
GPL says, in short, that the software is freely available for public use, but not for private use. (Yes, there are nuances to that, so much so (and so confusing) that most people either just ignore it, or say "IANAL...") It demands that 100% of the work of anyone in the future must be donated back to the collective for free. That is not freedom.
Create as much GPL code as you like. I create MIT. You can use mine (and I'm happy for you to!), but I can't use yours because of the restrictions you put on it. We can let the future decide which is more "free".
If you're the copyright holder, the terms of the GPL don't apply to you. It's a license that you give to other people. You can't revoke the license, of course. But as long as you haven't accepted contributions from other people, you can "fork" your own project and take it closed-source.
(I agree with your analysis in general. Most people don't understand the restrictions placed by the GPL.)
And that was my thought in general... I want to write projects that others want to contribute to, without painting myself into a corner.
But the higher-level Apps we publish under GPL, so that downstream is obligated to keep it open-source (but there is no obligation to submit a PR upstream).
And there are more than a few companies that use our GPL stuff, internally and don't redistrubute and therefore don't have to make their internal modifications available under GPL -- because there is no distribution happening.
I'm not a lawyer but our decision was informed by one who has prior experience in IP, licensing and specifically FOSS-style licenses.
Suppose that my company has powerful video editing software that we sell (which is distribution). Consider that it has unique functionality and has taken a decade to develop by a team of developers, all of whom have salaries, insurance, retirement, etc. that need to be paid, otherwise the software would not exist. Proprietary code and profit are more than appropriate in this situation, as I believe that workers should reap the reward of their labor and investment.
Now, suppose that a new feature is wanted. There is a project that provides that functionality, but it is licensed GPL. Can I use it?
Absolutely not!
Because, if I do, then I am obligated to release all of my source code in addition, because it integrates with the GPL code. It is financial suicide for my business to do so (which, btw, is a political preference for many of the GPL proponents). What will I do instead? I will probably just have my developer write our own version, adding in the extra features that we need.
Contrast that with the MIT-licensed code. We can use it without fear, and we will probably even submit enhancements back to the project, simply because it makes our lives easier in the future for maintenance.
GPL poisons downstream, simple as that.
You are correct that there is no obligation to submit a PR upstream, but there is a requirement for my source code to be made available under the same GPL license. GPL is "infectious" (or "viral", take your pick of words).
The funny thing is, I believe in freedom with software, but my interpretation of "free" is vastly different than the GPL interpretation of "free". And, as I said, I put my money where my mouth is... almost everything I write (except for my job) is MIT licensed code.
In the overwhelming number of cases the party is selling something other than their software and you are equally free to negotiate a different license with the developer if you have different needs.
Also, suppose that you were to write something that interacted with the binaries of a closed-source system. That would not automatically remove the proprietary nature of your own software, so it is not infectious at all. You may not be able to distribute the proprietary software, but you could sell it as an add-on product without surrendering your IP. That's not ebola. That's a full quarantine and separation that respects the IP of individual owners.
GPL is particularly troublesome when it is a dependency of a dependency of a dependency of a dependency. You may not even know that you are using GPL code because the dependency that you are intending to use is not GPL. Again, the words "viral" and "infectious" are used because of this behavior... And this behavior was purposefully designed into the license as part of the political beliefs of the founders.
I'm not saying that GPL is useless, but rather that it is significant and potent enough that it is a single factor that will eliminate a project from consideration. Period. No if's, and's, or but's. So much so that I personally avoid GPL as much as possible in my own projects, and I distribute my projects as MIT.
Unlawfully including GPL code in your proprietary product doesn't magically make your code GPL. It can't. In fact it has the EXACT SAME EFFECT as including proprietary code it means you are committing copyright infringement by distributing the combined work. The ability to get out of jail free by complying with the GPL and releasing the combined work under the GPL or just replacing the code you never had the right to distribute without further drama or penalty are extra privileges that you will never receive if you decide to distribute proprietary software. You are confusing additional benefits for penalties and pitfalls.
Once again you don't have to release your code as GPL you can simply rewrite the portion that you didn't have a right to distribute.
> GPL is particularly troublesome when it is a dependency of a dependency of a dependency of a dependency. You may not even know that you are using GPL code because the dependency that you are intending to use is not GPL. Again, the words "viral" and "infectious" are used because of this behavior...
If you are responsible for a product knowing where the code comes from falls under the basic responsibilities of the job. Declaring in public that you own someone Elise's property because you couldn't be bothered to look is like catching a public indecency charge because you couldn't remember to wear pants that day. You put on pants and the problem goes away.
If you have followed any of the cases in which companies misused GPL code it looks metaphorically like someone following you around politely and repeatedly reminding you to cover your nudity whereas infringing on proprietary code looks more like a swat team showing and flinging flash bangs. If you are lucky if you don't end up getting shot.
In terms of marketing, GPL sets itself up to be the paragon of the open source spirit and the model that all open source licenses should follow, but it has a HUGE gotcha based on its political persuasion. It proclaims freedom, but it is most decidedly not completely free, and requires parsing of sophisticated legalese to understand the nuances. Good luck if you are a beginner, non-native speaker, or have otherwise spent substantial brainpower trying to understand the do's and don'ts. It will bite you.
You may absolutely love GPL and everything that it stands for. That's fine with me. But I don't, and I advise everyone that I know of the dangers and repercussions of using GPL dependencies. You can say that those are features and virtues, and I can say that they are dangers and liabilities, but the bare facts are the same.
But, getting back to the reason for this post, when I want to compare software packages, the license is the first thing I look at, and if it's GPL, I bail on it immediately.
Thanks for the explanation! I wonder what the industry is (maybe finance or law or ??) It seems that in most of the tech industry software patents are primarily used as a war chest for large companies or for non-practicing entities focused on litigation. Usually execution is more important.
Seriously, there's some surprising work being done in the field, and software patents play a big part for companies that are very active in the space.
It's like the stock market. A lot of millionairs have money in stocks, but so, too, does the average Wal-Mart employee (at least it was an option when I was a cashier 20 years ago!). In other words, even small companies can gain a competative advantage with just a patent or two.
I believe Github uses something like HTMX + ActionCable, and it shows how good that experience can be (and some limitations).
But I think it's in the small minority. It'd be nice to know of more examples, instead of just more libs.
In an ideal world your table would also have a first commit row that way I can better compare how well established each library is (GitHub stars mostly does this but date of first commit would help give sense of momentum too)
i.e. I would have expected the libraries as rows, rather than columns. More like such lists are typically done in Wikipedia.
Since then I exclusively use Jinja2 in my Django apps and my life is so much better.
Now i despise all the frameworks & libraries and go vanilla 9/10.
Myself I am working with HTMX and thinking about how the back end framework changes to make the most of HTMX.
For instance I have a screen that has a bunch of dropdown inputs that automatically post changes to the server when you flip them and sometimes the options change when you flip them. The dropdown is defined in a macro that can be used in a template or that can be directly sent to the server. HTMX also can update several things in one request: for instance when I add a new RSS feed to YOShInOn it has to (1) insert the item into the feed, (2) tear down a modal dialog, and (3) update the count of the number of feeds. You very much need a server-side framework that makes it routine to do all that.
To the maintainer: Cloudflare is mangling your HTML and redacting lit's `@version` with `[email protected]`.
one suggestion, on non-ultrawide screens when you scroll you no longer see the left labels, would be cool to have them float when you start scrolling left so they're always visible.
I would lobby for featuring Webreflection's uhtml it is a workhorse for me personally.
Progressive enhance HTML means whatever backend you use, it spits out html, and the HTML is rendered without Javascript. Preact fails this.
The libraries are meant to progressively enhance html by replacing or enhancing certain actions with small javascript. For example, with htmx, usually clicking on html link would load complete page, but with clever htmx directive, the link onclick will only load/replace what is needed.
Think of progressive enhance html as html first. As the page working even if javascript is disabled.
It's extremely difficult to take anyone seriously when they claim their framework is for the "artisanal web."
Not for long :-) I believe they are dropping IE11 support in a version that is coming out soon.
(But then, IE support these days is such an edge case. No pun intended.)
there are too many ways to do the same thing in webdev. it's so stressful.
each approach has its own trade-offs and edge cases you not might find until the eleventh hour..
In react, mutating a model is a bug. It's left up to the developer to remember not to do that. Outside of react, mutating a model seems like a natural fit for the way stuff actually works and it's not considered a bug.
Lit is a framework for using web components, managing state and routing, it adds lots of boilerplate and uses OOP hierarchies to couple abstractions that could be otherwise separate. Lit uses object properties to detect changes and provides rerendering of the changed parts of the app.
This combo makes it work so terrible, you're orcestrating encapsulated components within inheritance chains and each part has a lot of boiler plate code and a lot of mutation. Its separating encapsulation by technology instead of concern, and enforcing this really hard. The end result is code terrible to read and very hard to change, full of mutation bugs and broken flows that don't properly update.