Ask HN: Hunting for a Framework
My primary background is in desktop development and my knowledge of web development is a little rusty by now. I know about Node.JS, Angular, React, Express and the like and have done a few small projects with these technologies. So far, I have implemented the below requirements for each project myself or copied them from previous projects. Now I am looking for a reasonable fullstack framework with the following requirements:
- A central definition of data schemas. I don't want to define my schema or validation twice, once in the frontend and once in the backend.
- Automatic generation of REST endpoints. I hate boilerplate code and don't want to reimplement Get/GetOne/Add/Update/Delete and Websocket for each data model. Even better would be a GraphQL interface.
- Authorization and Authentication
- No manual HTTP calls for standard cases. I want to define my model at the server and have the data available in an array at the client. As soon as a client inserts a record in his list I want that automatically a POST with the new record is sent to the server, it verifies the model and the authorization and inserts the record into the database. Then the server notifies the other clients about the change using websockets. The other clients see the new data record in their array without having to write a single manual HTTP call or websocket connection.
- Open Source Only. No Firebase or similar.
I've been searching for a while, but haven't found anything that seems reasonable. If I don't find anything I will write a small framework myself. I apologize if I seem lazy and don't want to search myself, but I'm really getting desperate. I want to spend as little time as possible on writing boilerplate and instead write business logic. There are thousands of javascript frameworks out there but none of them seem to handle these simple standard cases very well. They all require manual implementation of CRUD for each model or manual data fetching and subscription. Please make suggestions for frameworks and help me to see through the framework jungle!
69 comments
[ 5.1 ms ] story [ 135 ms ] threadmeanwhile, try: Hasura, postgraphile or RedwoodJS
if you want a lower-level framework: tRPC, GraphQL Yoga
recently, there's also grafbase.com
1. Hasura - DB + Basic APIS
2. Ory.sh for Auth/Authz
3. React on the frontend
4. Windmill.dev for Scheduling/Batch processing/ Background tasks
5. Docker for deployment
6. Fastify + Node JS for glue code (can use Windmill for Glue code too)
I have used Hasura extensively at 2 companies. It's well done and saves a ton of time.
You might also want to look at Retool (and its open-source alternatives). Web dev has become simpler now.
----
If you like code-focused solution: Rails, Laravel and Django are good options.
Great choices!
3. React on the frontend
Here I'd go with Elm, and a generated GraphL API client. Here an example to play with (which btw also includes ZomboDB for ElasticSearch integration into Postgres)
https://github.com/cies/low-code-backend-dockered
> 4. Windmill.dev
Look awesome, never heard of it. Tnx
> If you like code-focused solution: Rails, Laravel and Django are good options.
I think Kotlin/KTor, while not as full featured, is a much better alternative due to the strong typing discipline.
This is not just FP, this is "no runtime errors possible" FP.
With Elm-GraphQL your QUERY BUILDER is even fully type safe!
Robust productivity for the masses.
On top of that, do you typically parse these Hasura Apollo into your client models? Or do you use the fragments directly in UI code since it already support types.
Link to docs: https://hasura.io/docs/latest/remote-schemas/remote-relation...
What you're describing sounds very nice though.
I've often wanted a VB6 equivalent for the web, but open source.
https://anvil.works/
open source.
https://anvil.works/open-source
i should be a paid for how much i recommend looking at them, but i've never used it for anything production.
For anyone looking, here's installing via pip: https://github.com/anvil-works/anvil-runtime#using-the-stand...
The code is GNU AFFERO GENERAL PUBLIC LICENSE Version 3.
That's Gambas, it can create web apps.
https://gambas.sourceforge.net
Some more links here:
https://github.com/wekan/hx/tree/main/prototypes/ui/gambas
Code has moved to GitLab https://gitlab.com/gambas/gambas
Web based bugtracker is made with Gambas.
I have no idea what the status of MeteorJS is, but looks like it could fit your requirements.
Depending on the language/framework used it'll validate too - e.g. the python backend framework connexion (a thin wrapper around flask) will 500 if you return a non-conforming response, and 400/405/etc. if the request doesn't fit the declared schema, automatically.
You may never find “the” framework.
Lately my default has been AspNet Core and C# (or F# if I’m feeling frisky). Not because it’s the ultimate framework for me (although it _is_ very good), but it’s what I learned, thanks to learning on the job.
I remain a microsoft skeptic though. I continue to dabble in other tooling just in case they lock down the framework or tools in the future. I like django, for example.
The realtime aspect of what you are looking for is the hard part. The only options I know of are the remix stack above (you still have to do some extra plumbing), elixir/Phoenix (or other turbo links like options but most aren't fast enough). To do realtime updates natively you need to move to evented data front to back and that is a very big move away from models the way we normally think of them. Check out eventide or resolv.js.
Phoenix specifically doesn't work like turbolinks. LiveVIew in Phoenix uses a websocket to transport data, morphdom to patch the dom, and a light process on the server to manage state. It's as fast as the internet connection for insertions into a list. In fact it is quite capable of parallel data loading just like remix, and the server can work share in parallel across as many cores as you have available on the server.
> 2.5 GHz Quad-Core Intel Core i7 16 GB 1600 MHz DDR3
Obviously memory starts to be a constraint for doing anything meaningful, but you can squeeze a lot out of 32gb of ram.
[1]https://phoenixframework.org/blog/the-road-to-2-million-webs...
[2]https://josephmate.github.io/2022-04-14-max-connections/
Remix makes things that were simple hard (apparently with the goal of doing _everything_ on the server again).
https://create.t3.gg/
https://github.com/t3-oss/create-t3-app
I hadn't touched much webdev for a few years, the ecosystem / build tooling has gotten a LOT better. It's back to being fun and painless to spin up a new webapp.
Both got error, which seems to be due to next/next auth dependency breaking. So it's not that painless I guess.. I found this situation quite often with nextjs example template
T3 author is very responsive though, so my issue resolved quickly
You can better fo with Remix+prisma. You probably don't need REST endpoints just fetch, post using remix.
[0] https://github.com/t3-oss/create-t3-app
Is there a specific reason that you need to have an SPA framework?
Do NOT make your own framework, that is a doom loop of death. Lots of smart (and not smart) people have created frameworks for you..... focus on productivity only.
You put Firebase in with open source only - would you consider an open source Firebase like Supabase? You can host it yourself and it’s open source.
The next is Actix[1] based on Rust. There are many frameworks in Rust and most of them have not reached 1.0 And which framework will survive becomes a question.
Other not so well-known is Wt[2] based on C++. This actually is created for programmers who are not web developers. The development experience is similar to desktop app development like Qt.
If that is not acceptable then Django[3], based on Python, is the one that will be good for you.
For the front-end I would recommend Flutter[4]. As much as I dislike getting tied to a single company for whom the framework is not their bread-and-butter, I don't see any other viable options to Flutter that will cover all web, mobile and desktop out of the box.
For databases, I would recommend BedrockDB[5], if you are not averse to SQLite. Or FoundationDB[6], if you want NoSQL. But if you are not concerned about horizontal scalability or okay with self-managing database availability, then PostgreSQL[7] is a very good option.
For push notifications, PushPin[8] is a good option.
[0] https://vapor.codes
[1] https://actix.rs
[2] https://webtoolkit.eu
[3] https://www.djangoproject.com
[4] https://flutter.dev
[5] https://bedrockdb.com
[6] https://www.foundationdb.org
[7] https://postgresql.org
[8] https://pushpin.org
Typically using something like Auth0, Cognito, Firebase Auth, FusionAuth, Clerk or many of the other authentication services will get you a full feature set for user management with little to no work.
On the authorization front consider a similar approach of decoupling the the component out of your codebase where the permissions logic is defined as policy rather than code. I work on Cerbos[1] which is an open-source, decoupled authorization layer for your software which does exactly this.
[1] https://cerbos.dev
Auth code is undifferentiated, but if you have experience building apps it’s also not particularly difficult. I’d recommend either picking an open source solution that you host yourself or just taking a few days to grind it out.
* don’t try to implement the hard/annoying bits (strange access detection, account recovery, sending emails, password storage)
* keep ownership of your user list and users’ capabilities
It depends on the use case.
[1] https://herbsjs.org/
Disclaimer: Herbs JS author here
For example, if you don’t want to make any manual HTTP requests to fetch data then the logical alternative is to fetch it automatically. What should be the trigger for your ideal framework to do that? Without any extra information, the framework can only know you need the data when your other code asks for it. It will have to fetch everything on demand, in real time, and that could be extremely inefficient both in terms of the number of requests you’re making over your HTTP channel and the database queries that will ultimately run on your servers. Even if the framework somehow has perfect caching on the client side and it pushes notifications when cached data needs to be refreshed, there will still be questions around which notifications to push to which clients, because in general the server will have no way to know which data that was requested earlier is still relevant to each client at some later time.
You’d also like updates sent to the back end automatically when you change your front end data structures, and not only that, you’d like them propagated out to other clients automatically as well. How would your ideal framework manage what is now shared mutable state? For example, maybe there are constraints in your data model and you need transactional behaviour that updates multiple data points at once to avoid violating those constraints. In general, the framework can’t know when you’ve finished making a set of related changes that should be batched up and sent back to the server, unless you tell it explicitly. And when you do, how would your ideal framework resolve conflicting updates if multiple clients are sending incompatible changes around the same time? What happens if communication links break down and you have to deal with the CAP Theorem? There are no universal “right answers” to any of these questions, and the behaviour you want will often be highly specific to an individual application and its particular data model.
I fear the reason you haven’t found what you’re hoping for is that no framework exists that can magic away all these practical questions about building a distributed system. Even specifying the required behaviour in a realistic application is a non-trivial problem, never mind implementing that specification once you’ve decided what it should be.
So for whatever it’s worth, my advice would be to lower your expectations a little. It’s very reasonable to want a single source of truth for your data models and to generate the types and the simple cases for REST/GraphQL endpoints, DB queries, HTTP request wrappers on the client, API documentation, etc. It’s also very reasonable to want some standard mechanism for authentication and authorisation checks, possibly using middleware in your own code or other facilities provided by any cloud hosting service you’re using, that can be applied on top of the above. But maybe look for a starting point that can handle a lot of the boilerplate for you and leave you free to concentrate on the more difficult questions, rather than hoping to achieve everything you described out of the box.
It's far from production ready, but it's already working reasonably well.
I tried HotWire but it didn't feel right to me because I'm used to React.
Reactivity is not an issue anymore with the HOTWIRE stack in rails or there's the even better StimulusReflex gem that you can use for reactivity and realtime features.
- ActiveRecord is wonderful for data schemas: https://guides.rubyonrails.org/active_record_migrations.html
- ActiveRecord form validations is excellent and defined only on the model
- Scaffolds automatically generate create/read/update/delete endpoints: https://guides.rubyonrails.org/v3.2/getting_started.html#get...
- Websocket-driven updates provided by Hotwire / Turbo Streams: https://turbo.hotwired.dev/handbook/introduction
- Authorization and Authentication by Devise: https://github.com/heartcombo/devise
HAML is wonderful as a templating language as well.
It's Next.js, Typescript, TailwindCSS, Prisma, NextAuth, tRPC.
> I know about Node.JS, Angular, React, Express
You already know just JS. Stick with JS framework, not these Rails suggestions. Next.js is by far the biggest JS framework (ChatGPT page? half the recent YC co's? Next.js), the rest are the niceties around it to get to a full solution.
> A central definition of data schemas. I don't want to define my schema or validation twice, once in the frontend and once in the backend.
T3 stack uses Prisma, a JS/TS "ORM". Your data schema will live in a .prisma file.
> Automatic generation of REST endpoints. I hate boilerplate code and don't want to reimplement Get/GetOne/Add/Update/Delete and Websocket for each data model. Even better would be a GraphQL interface.
Includes tRPC setup. Give the automated tRPC endpoints a whirl. It's not auto-gen get/delete/etc. (like Django/Rails models) on the server, but the endpoint you create on server very quickly will auto-gen the func call available on the frontend.
> Authorization and Authentication
Includes NextAuth.js setup