I’ve got a project starting for a client. We’re gonna be developing a full stack web application, and I’ve decided the backend will be a Node.JS serverless application, using the Serverless framework and hosted on AWS Lambda.
I will be defining the architecture and leading the development team, three developers will work on the project, and I want to make sure that they have a good developer experience, because that will lead to good quality code and high speed of development! I’ve chosen this stack for the backend because I’ve already used it in 3 production projects, out of which one is HUGE, with traffic in the millions. I’ve learned a lot about it in the meantime and I have a pretty well structured skeleton already, that I’d like to package in an easy to set-up and update boilerplate.
In the future I would like to ask my clients to publicly talk about their projects on my blog, but for now I can’t do that, so I’ll be omitting all details of the projects.
One of the issues I’ve had until now is that generic boilerplate and project specific code are all mixed together, making it quite hard to update the boilerplate one all projects that are using it together. I’d like in future projects to be able to share updates on the boilerplate between them. So that if I make an improvement to the boilerplate in one project, the other ones can make use of it as well without me having to repeat myself. I think the solution to this could be to have all the code that should be shared between the projects in an NPM module or a git submodule.
I want to figure out what responsibilities the boilerplate should take care of.
- Serverless framework / AWS Lambda related boilerplate
- Input validation and documentation generation boilerplate
- Database interaction
- Code generation (plop) still to decide wether benefits outweigh costs
What should go in the boilerplate and what shouldn’t?
I think Authentication and Database interaction are too different from project to project to think about including them in the boilerplate. Everything else goes in.
So I can start from the latest iteration on this project skeleton and strip it off of all project logic.
I’ve created a new folder, initiated a new npm project and set up typescript. Now I can run
npm link to install the npm package inside the clone of the existing project that I want to turn into the boilerplate and I can start moving logic from the project to the module.
Serverless Configuration Generation
The boilerplate will expose a serverlessConfig function which takes care of good part of the Serverless framework configuration. Things like looking for all the function handlers in the source code and exposing them to Serverless.
One of the useful features of this project is the function wrapper, which takes care of handling thrown errors, parsing json body, and other things like that. The part that I least like of the current implementation is the amount of boilerplate that you need to duplicate for each function. But because I don’t have much time to look into it right now I’ll leave improving that part for another time.
Error handling is currently handled by the function wrapper. Instead the function wrapper should expose a way of installing middleware, and let whoever is implementing it install the error handling middleware, which is really simple anyways.
This post is WIP.