Why not just send HTML as a single response at this stage? Sometimes it feels like we are doing web development more complex than it needs to be.
Why not just send HTML as a single response at this stage? Sometimes it feels like we are doing web development more complex than it needs to be.
Younger developers scoff at us fossils and the olden ways, but this is exactly how this ignorance of classic, tried-and-true, performant patterns results in atrocious complexity and performance, only because "this is how things are done".
It HAS to be a BFF, it HAS to be 15 different microservices and 20 different AWS toys, right? There is no other way? Are you sure?
It seems like we are talking about the whole industry, but it's largely he Node ecosystem in my experience (which is effectively - the industry). It's not like there is not Rails development being done out there, with nothing but a trusty Postgres database.
Ironically, our existing architecture patterns are beginning to resemble J2EE - a bulky, slow, expensive, boiler-plate-laden process where a simple site costs one million dollars and performs like shit.
I also partly blame the careerist obsession around always learning new technology, because it’s becoming obvious that a lot of the “new stuff” over the last decade created more problems than solutions. Don’t get me wrong, learning is an important part of the job, but we’ve created a culture of constantly pushing new technology to pad resumes and feed our insecurities around irrelevance instead of solving problems.
It becomes something akin to a religion - after all, 2 billion Christians can't be wrong, can they?
More seriously: once a bit of tech becomes mainstream, it becomes politically easier to use it. Your manager has not heard of <cool tech>, but he did read about React in some business magazine. So when the choice is between React and bheadmaster's Funky Funkness Framework, he'll go with React.
Or do you consider my point about network effect in tech stacks being similar to religious beliefs to be antagonistic by itself?
If PP had used that, would it have been antagonistic? Racist?
https://en.wikipedia.org/wiki/50,000,000_Elvis_Fans_Can%27t_...
It’s not just that. There are practical reasons to choose the bandwagon, even if you know it’s not the technically optimal approach.
If you’re planning on hiring junior and mid level engineers, for example, it’s a great help if they already know the technologies involved. Your hiring pool for React is a lot bigger than for a more obscure tool. Additionally, the popular tools also tend to be stable and long lasting, with good support.
So, there are compelling business reasons to choose what’s popular, even if you aren’t making assumptions about the technical quality just because its popular.
Ok. Yeah that's only for huge scale things.
Having a native app out there in the wild on customer computers that is coupled to a bunch of different microservices is hell for when you want to change your backend without breaking your customers' experience and forcing them to update.
Backend that handles all the microservices so the frontend isn't doing that job, sure. I didn't even consider doing it differently than that.
When a partner team filed a feature request on our team, and I gave them an API that just does exactly what they need, they were like "that's it? No 1GiB graph response to DFS through?"
https://www.freedesktop.org/software/polkit/docs/latest/polk...
https://discourse.ubuntu.com/t/use-of-javascript-rules-in-po...
We are not at that point nor we were ever at that point, or close to it.
Server-side rendering has been a hot topic in JavaScript framework circles for over a decade, and React famously solved that problem so well that it is now a standard, basic technique.
Also, just because you throw the same buzzword around that does not mean the problem stayed the same. Reassembling a javascript-generated DOM with a coherent state is not the same as sending a HTML document down the wire. And you know why people started assembling DOMs with JavaScript? Because sending HTML documents down the wire was too slow and did not allowed for any control over aspects that dictate perceived performance.
Demand for interactivity. A real demand - that’s why desktop apps are now web apps.
It can be over applied, sure, but there are great reasons not to serve html templates. The trend is not some massive incompetence.
In my experience, the percentage of large react sites where someone sat down and seriously considered using old fashioned server side rendering, but decided on React because the site actually required a huge amount of interactivity is close to zero.
Every React site I’ve ever been involved with in in the last say 7 years was using React because “that’s the way it’s done”, and anything else was just a post hoc justification.
So many websites now pretend they're in the former category, but would work just fine if they implemented a less-interactive form. That's how it was done in the old days! "No, you can't have that. Here's the best we can do." "Oh, that's fine."
But I expect more of what's driving complicated backend/frontend split design these days is shipping the org chart (in companies large enough to have frontend and backend teams) and technology-by-consultant (where the right technology is whatever you can get a consultant in).
I actually somewhat knew React before this project but besides not wanting to overcomplicate things I was hesitant because I didn't like pure client-side rendering. Then I learned NextJS makes it easy to mix/match client-side rendering and server-side rendering so I just switched to that.
So now, even for a simple website, I'll probably start with React because I don't want to dig myself into a needless hole.
I wrote about the experience here:
https://www.billprin.com/articles/why-i-ditched-django-for-n...
And yes that post upset some people who thought I should use htmx, but React is actually pretty easy and simple. Now most of my websites are React because I know it so it's easy and simple to use what you're used to.
Also, "I did it in React because that's the way it's done" isn't the worst reason because you benefit from that popularity, e.g. some library you need will have clear examples of integrating with React.
I think the frontend and JS community have certainly gone off some crazy rails at points, but I also think there's a popular sentiment on HN exaggerating how off-the-rails things have gone, usually expressed by people who don't actually develop many modern-looking websites. Most of the trends have gotten popular for somewhat rational reasons, and even that stuff that has gotten a little crazy like an explosion in dependencies, is really just about tradeoffs e.g. lots of dependencies cause lots of problems but also enable code re-use so it has pros and cons.
But I've been doing this for a long time, and that's what everyone says. I've heard this argument at least 100 times when someone is trying to defend their decision to build something overcomplicated. The number of times they ended up actually being justified is so small that I'm very suspicious of this argument.
If you're not expecting to need fancy client side stuff, does next.js give you as good a server side development experience as Django/Rails/Laravel? At that point, it would seem worth it "just in case", as you suggest, but in the past when I looked at it, the SSR stuff still felt a little cobbled together and experimental. I would love to hear from someone with firsthand experience switching, though!
I think Next has a great DevEx, but I'm just using it for some projects as a solo dev without a ton of traffic so perhaps there's some rough corners I haven't experienced yet.
I do think they are going down some risky paths where they do things like rewrite your code files depending on whether you're on server or client, and in general with "framework-defined infrastructure" where if you write certain functions the framework "knows" that it's supposed to be on the server or in a background job or whatever. But so far I've gotten the benefits without the drawbacks, though I might be jynxing myself.
You write all the code in one language (C#), and it streams the changes to the clientside as needed automatically. It means you can call the database in your 'frontend' HTML layouts directly and gets rid of all the glue code. You have no serialization problems because you are using the same classes everywhere, and the component structure keeps things very clean.
I would say I am about 5x more productive in Blazor Server than any other frontend technology. You don't need to write APIs at all. It's just like writing static server side rendered pages but you can do dynamic stuff. It is honestly like magic.
It does come with some huge downsides though, in that it needs to keep a websocket open to stream all the DOM changes from the server, and this also has memory/performance issues on the server (needs to keep state on the server all the time). Which basically rules it out of anything that needs to work over intermittent connections (mobile), and very high scale stuff (probably could be done with enough server RAM, but it's not the right tool for that).
However, it's perfect for boring line of business applications that will only be accessed on solid internet connection, which is many of them.
There is also Blazor Webassembly which removes the websocket part, and lets you code frontend and backend in C# still, sharing a lot of classes, though you do need some glue code to connect the database. I've heard people are having good results with gRPC for that; but haven't looked into it much (blazor server works fine for most apps IMO).
If so that sounds like a very nice model that would make it a lot easier to get back to just using simple HTML and delegate the complexity to the framework or server process. Are there other projects beside Blazor that use this type of approach?
Since HTML never had a proper way to compose content from multiple sources-- frames being as close as it got-- we have to instead punt this, like so much else, to JavaScript hairballs to glue it all together.
Using most static page frameworks is like using ColdFusion for your career advancement.
Job security is relative.
This new world sucks for the interactive user in a browser (which is me often enough), but it's great for the guy who wants to treat a website as just a remote provider of some kind of data or service (also me often enough).
A very basic example is if I have a checkbox that allows the user to subscribe to push notifications. On click I sent a xhr request to the backend POST `/subscribe/1234` which registers the subscription. Next time I'll check `/subscriptions` or similar to see if the checbbox is in "checked" state (i.e. we are subscribed). This is basic functionality which requires a concise REST/JSON API, and has nothing todo with your page/route layout à la /page/a, /page/b etc.
We do this for SPA. The POST can be supported just like you explained. Then you can either reload the "page" to see that the checkbox is checked, because backend will include that as part of the page, or (as an optimization) reload just that checkbox if you created a specialized resource for it. The entire page is still there for you to fetch upon transitions.
Among pages, you will still need a few individualized resources sprinkled around for optimizations/reloads/fragment-paginations. The difference between that and a complete API is that they will be entirely design driven. If a table needs paginating, and is built with data from multiple resources, you will not provide 2 resources, and expect front-end to paginate and glue them together. Instead, you provide a complete paginated resource for this table, where data is ready to be displayed as-is.
- I don't like page (re)loads. They are usually slower and more likely to fail, compared to a lightweight request. Especially in scenarios with a bad connection
- If they fail, it's harder to retry, I see a connection timeout page. With a SPA I see an error message, potentially with a retry button. Or even better: the SPA retries for me a few times.
- I can continue to see all the rest of the page while the action is running
- I can potentially start other actions in parallel
- I prefer to not lose any progress of things on the side, e.g. text-boxes where I already entered/changed some text
- It's easier to inspect what goes wrong by looking at the network tab. Okay, most users don't do that, but for me it's still a pro
There are also advantages, but I think nowadays the cons outweight those for me.
Absolutist statements like "no, you should not do a full form post just to toggle a checkbox" are just silly. There is no minimum bound beneath which a standard web browser form submission doesn't make sense, and writing extra JavaScript code to not only manage an asynchronous network request but also handle subsequent behaviours for success, failure, timeout, etc., is additional complexity which incurs additional cost and a greater potential for system failure.
Sometimes these implementation details and associated costs are necessary, but in most cases they aren't, and it's not an ideal perspective economically to default to the more expensive and complex implementation, especially for dubious benefit.
That is because you didn't read or accept the frame that I set initially. I was very clearly refering to web apps that are SPAs (not websites!). Within that context, that statement is less absolutist and still true in 95% of the cases.
If you don't want to hear an answer, maybe you should just not ask.
You’re talking past people, not taking the time to understand what they’re saying, and then being dismissive when they reply.
I believe I have indeed taken the time to understand what people are saying in these comments specifically and on this topic more broadly. And I just don't agree with the opinions presented. I think they're silly, in the same way that microservices are almost always adopted for silly reasons. The popularity of either approach doesn't negate their silliness.
For more on this topic, this article is good: https://www.timr.co/server-side-rendering-is-a-thiel-truth/
Need page b? Copy page-a.asp to page-b.asp, gut the page-a logic, and put in the page-b logic.
Before you get too nostalgic for these simple days, do we rememember why we stopped developing web pages that way?
Because we needed an API for our mobile apps, and once we had that, SPAs seemed convenient.
It was definitely, absolutely NOT because the page-centric way of building sites didn't work (it does), or because SPAs are better (they aren't).
SPA? I can serve the whole thing with static files and remove 90% of the traffic from my web server. The API can be served from a different path from the static files. API requests are super tiny and more tolerant to fluctuating network conditions, and you can hide a lot of that with Javascript.
So instead I combined it into various JSON files. Now I have a SPA downloading the JSON as necessary, and don't need any API/backend/database. I'm considering moving to sqlite now there are official WASM builds.
Could have stopped here
The vast majority of the time, the browswer is infact going to be the only client.
once you reach the point where its not, then build the api to suit the new client rather then trying to build one that does both.
But on the other hand, you can have a iOS or Android based app that depends on the same data. So the browser is not the only client in general, especially nowadays, I think?
Dramatically more important than any theoretical, abstract consideration in deciding whether this can work is what your teams look like. The client team should almost certainly own the BFF API, which has implications for skillsets and maturity.
If so, that doesn't handle the general case (native apps for instance)
In fact, you can see it as 2 decoupled kinds of database:
- the storage database
- the working in-memory UI database that holds the data represented (e.g. on your screen (GUI)).
The goal in general is to modify the data contained in this UI database and then to push the changes to storage.
Nothing prevents the main response from being served as regular HTML and subsequent XHR request for some parts of a page being JSON or some such data format. In fact I bet that sending server-side rendered HTML is faster than sending a full structured page as JSON which has to be decoded, parsed, and then converted to HTML.
We do use a templating engine and separate CSS files, so no, not at all, all static files does not need updating on every change.
> Caching becomes also a challenge and the so does the performance
Not at all, not even on black fridays.
> That would be really hard with a server side rendered html.
Why do you pose that hypothetical when our real-world experience is easy?
We eventually trimmed what was returned a bit, but just getting rid of the page transition was 90% of the work.
This was the original design of REST as applied to the web. It was explicitly designed in such a way that it was forbidden to reload parts of the page. This makes it so that every state has it's own URL and you therefore can link to every state. Deep linking if you wish, for all of the web.
Granted, this requires JavaScript on the front end, but it's a framework that can be shared between different websites, so you're not writing any custom JavaScript for your site.
No matter of JSON or HTML don't built a general purpose API if it's only your frontend.
Is it time to discover memcache again? I think it's about time.
That said, a lot of companies have front-end teams, and those front-end teams commit years to building React components. So even if you render server-side, this is how you'd put data into those components. I'm a backend dev. I don't like some of what frontend is doing, but you gotta work with people, right?
1. The backend can be entity centric, like it does best 2. The frontend can request a page worth of data from diverse entities in a single go.
There’s nothing wrong with a web server serving HTML; that’s their whole purpose.