I’m not sure javascript islands is that but I appreciate a new approach to an old pattern.
I originally started as a web developer during the time where PHP+jQuery was the state of the art for interactive webpages, shortly before React with SPAs became a thing.
Looking back at it now, architecturally, the original approach was nicer, however DX used to be horrible at the time. Remember trying to debug with PHP on the frontend? I wouldn’t want to go back to that. SPAs have their place, most so in customer dashboards or heavily interactive applications, but Astro find a very nice balance of having your server and client code in one codebase, being able to define which is which and not having to parse your data from whatever PHP is doing into your JavaScript code is a huge DX improvement.
I do remember that, all too well. Countless hours spent with templates in Symfony, or dealing with Zend Framework and all that jazz...
But as far as I remember, the issue was debuggability and testing of the templates themselves, which was easily managed by moving functionality out of the templates (lots of people put lots of logic into templates...) and then putting that behavior under unit tests. Basically being better at enforcing proper MVC split was the way to solve that.
The DX wasn't horrible outside of that, even early 2010s which was when I was dealing with that for the first time.
Modern PHP development with Laravel is wildly effective and efficient.
Facebook brought React forth with influences from PHPs immediate context switching and Laravel’s Blade templates have brought a lot of React and Vue influences back to templating in a very useful way.
True, don't remember doing much unit testing of JavaScript at that point. Even with BackboneJS and RequireJS, manual testing was pretty much the approach, trying to make it easy to repeat things with temporary dev UIs and such, that were commented out before deploying (FTPing). Probably not until AngularJS v1 came around, with Miško spreading the gospel of testing for frontend applications, together with Karma and PhantomJS, did it feel like the ecosystem started to pick up on testing.
> Astro find a very nice balance of having your server and client code in one codebase, being able to define which is which and not having to parse your data from whatever PHP is doing into your JavaScript code is a huge DX improvement.
the point is pretty much that you can do more JS for rich client-side interactions in a much more elegant way without throwing away the benefits of "back in the days" where that's not needed.
More and more logic moved to the client (and JS) to handle the additional interactivity, creating new frameworks to solve the increasing problems.
At some point, the bottleneck became the context switching and data passing between the server and the client.
SPAs and tools like Astro propose themselves as a way to improve DX in this context, either by creating complete separation between the two words (SPAs) or by making it transparent (Astro)
How much of the frontend and how much of the backend are we talking about? Contemporary JavaScript frameworks only cover a narrow band of the problem, and still require you to bootstrap the rest of the infrastructure on either side of the stack to have something substantial (e.g., more than just a personal blog with all of the content living inside of the repo as .md files).
> while avoiding the hydration performance hit
How are we solving that today with Islands or RSCs?
In terms of the front-end, there’s really no limit imposed by Next.js and it’s not limited to a narrow band of the problem (whatever that gibberish means), so I don’t know what you’re even talking about.
> How are we solving that today with Islands or RSCs?
Next.js/RSC solves it by loading JavaScript only for the parts of the page that are dynamic. The static parts of the page are never client-side rendered, whereas before RSC they were.
This is fine generally because you have the choice to pick the right tool for the job, but in the context of "a single, cohesive unit" you can only get that with Next.js if you all that you care about are those specific abstractions and want your backend and frontend to be in the same language. Even then you run into this awkwardness where you have to really think about where your JavaScript is running because it all looks the same. This might be a personal shortcoming, but that definitely broken the illusion of cohesion for me.
> The static parts of the page are never client-side rendered, whereas before RSC they were.
Didn't the hydration performance issues start when we started doing the contemporary SSR method of isomorphic javascript? I think Islands are great and it's a huge improvement to how we started doing SSR with things like Next.js Pages Router. But that's not truly revolutionary industry wide because we've been able to do progressive enhancement long before contemporary frameworks caught up. The thing I'm clarifying here is the "before RSC" only refers to what was once possible with frameworks like Next.js and not what was possible; you could always template some HTML on the server and progressively enhance it with JavaScript.
Isn't that basically just what Symfony + Twig does? Server-side rendering, and you can put JS in there if you want to. Example template:
<html>
<head>[...]</head>
<body>
{% if user.isLoggedIn %}
Hello {{ user.name }}!
{% endif %}
</body>
</html>
The syntax is horrible, and seeing it today almost gives me the yuckies, but seems like the same idea to me, just different syntax more or less. I'm not saying it was better back then, just seems like very similar ideas (which isn't necessarily bad either)Best of them all has to be hiccup I think, smallest and most elegant way of describing HTML. Same template but in as a Clojure function returning hiccup:
(defn template [user]
[:html
[:head [...]]]
[:body
(when (:logged-in user)
[:div "Hello " (:name user)])])
Basically, just lists/vectors with built-in data structures in them, all part of the programming language itself.Have a look at: https://www.gnu.org/software/guile/manual/html_node/SXML.htm... or https://docs.racket-lang.org/sxml/SXML.html
And as you say, part of the language itself, which means no need to learn something different, and no need to learn a pseudo-HTML or lookalike like with JSX, which then needs to be actually parsed by the framework (or its dependencies), unlike SXML, which is already structured data, already understood perfectly in the same language and only needs to be rendered into HTML.
That is a perfect description of it, released 1996. So far ahead of its time it’s not even funny. Still one of the best programming environments I’ve ever used almost <checks calendar> 30 years later.
You'd render templates in Jade/Handlebars/EJS, break them down into page components, apply progressive enhancement via JS. Eventually we got DOM diffing libraries so you could render templates on the client and move to declarative logic. DX was arguably better than today as you could easily understand and inspect your entire stack, though tools weren't as flashy.
In the 2010-2015 era it was not uncommon to build entire interactive websites from scratch in under a day, as you wasted almost no time fighting your tools.
I think we are overdue for a rediscovery of object oriented programming and OOP design patterns but it will be called something else. We just got through an era of rediscovering the mainframe and calling it “cloud native.”
Every now and then you do get a new thing like LLMs and diffusion models.
Another one: WASM is a good VM spec and the VM implementations are good, but the ecosystem with its DSLs and component model is getting an over engineered complexity smell. Remind anyone of… say… J2EE? Good VM, good foundation, massive excess complexity higher up the stack.
Astro's main value prop is that it integrates with JS frameworks, let's them handle subtrees of the HTML, renders their initial state as a string, and then hydrates them on the client with preloaded data from the server.
TFA is trying to explain that value to someone who wants to use React/Svelte/Solid/Vue but only on a subset of their page while also preloading the data on the server.
It's not necessarily progressive enhancement because the HTML that loads before JS hydration doesn't need to work at all. It just matches the initial state of the JS once it hydrates. e.g. The <form> probably doesn't work at all without the JS that takes it over.
These are the kind of details you miss when you're chomping at the bit to be cynical instead of curious.
Sending functional HTML, and then only doing dynamic things dynamically, that's where the value is for web _apps_. So if what you point out is the value proposition for Astro, then I am not getting it, and don't see its value.
Just compare the two cases, assuming 100ms for the initial HTML loading and 200ms for JS loading and processing.
With full JS, you don't see anything for 300ms, the form does not exists (300ms is a noticeable delay for the human eye).
With frameworks such as Astro, after 100ms you already see the form. By the time you move the mouse and/or start interacting with it, the JS will probably be ready (because 200ms is almost instant in the context of starting an interaction).
This is not new at all, old school server side processing always did this. The advantage is writing the component only once, in one framework (React/vue/whatev). The server-client passage is transparent for the developer, and that wasn't the case at all in old school frameworks.
Note that I'm not seeing this is good! but this is the value proposition of Astro and similar frameworks: transparent server-client context switching, with better performance perceived by the user.
Nicely sums up a lot of interactions these days
What a value!
I guess I may be chomping at the bit to be cynical, but I have quite a bit of experience in these fields, and I don't think Astro sounds especially transformative.
I think your comment gets at a very specific and subtle nuance that is worth mentioning, namely that typically if you were a proghance purist, you'd have a fallback that did work; a form the submitted normally, a raw table that could be turned into an interactive graph, etc..
I don't think these details are mutually exclusive though, and that it was certainly valid in those days to add something that didn't have a non-js default rendering mode, it's just that it was discouraged from being in the critical path. Early fancy "engineered" webapps like Flipboard got roasted for poorly re-implimenting their core text content on top of canvas so they could reach 60fps scrolling, but if JS didn't work their content wasn't there, and they threw out a bunch of accessibility stuff that you'd otherwise get for free.
Now that I'm thinking back, it's hard to recall situations *at that time* where there would be both something you couldn't do without JavaScript and that couldn't also have a more raw/primitive version, but one example that comes to mind and would still be current are long-form explanations of concepts that can be visualized, such as those that make HN front page periodically. You would not tightly couple the raw text content to the visualization, you would enhance the content with an interactive visual, but not necessarily have fallback for it, and this would still be progressive enhancement.
Here's another good example from that time, which is actually only somewhat forward compatible (doesn't render on my Android), but the explanation still renders https://www.ibiblio.org/e-notes/webgl/gpu/fluid.htm
Edit: according to WP history, around December 2020
https://en.wikipedia.org/w/index.php?title=Hydration_(web_de...
Second edit: "Streaming server rendering", "Progressive rehydration", "Partial rehydration", "Trisomorphic rendering"... Seems I woke up in a different universe today.
then chunking was the next step, and basically then logical endpoint is this mix-and-match strategy that NextJS is "leading" (?), by allowing things to be streamed in while sending and caching as much of the static parts up front as possible.
Quote:
2013-2015: The concept of SSR in JavaScript frameworks emerged with React (released in 2013). Initially, it was referred to as "reconciliation" or "bootstrapping" — React would match the DOM with the virtual DOM.
2015: Around the release of React 0.14 and React 15 (2016), the term "hydration" began appearing in the React ecosystem to describe the process of attaching event listeners to server-rendered markup.
The first known mention in React documentation and community discussions around 2015-2016 clarified that React would "hydrate" the HTML.
This distinguished it from full re-rendering, which would discard the server-rendered DOM.Dear God. In 20 years people will hire HTML experts as if they are COBOL experts today.
Hah, if only... Time and time again the ecosystem moves not to something that is better, but "same but different" or also commonly "kind of same but worse".
There are so many cases where the "worse" solution "won", and there is a reason "worse is better" is such a popular mantra: https://en.wikipedia.org/wiki/Worse_is_better
Back in my days we called this "progressive enhancements" (or even just "web pages"), and was basically the only way we built websites with a bit of dynamic behavior. Then SPAs were "invented", and "progressive enhancements" movement became something less and less people did.
Now it seems that is called JavaScript islands, but it's actually just good ol' web pages :) What is old is new again.
Bit of history for the new webdevs: https://en.wikipedia.org/wiki/Progressive_enhancement