Api, that supports JWT authentication and allows to create, read, update and delete users.
Implements custom micro framework using zod, fastify, fastify-type-provider-zod, @fastify/swagger and @fastify/swagger-ui.
Tested using NodeJS v18.
- Clone the repository
- Run
yarnin the main directory to install dependencies - Configure by running
yarn setup:prodcommand. Setup will ask configuration settings for env file and create it. - Run
yarn start - Open swagger UI in your browser by navigating to
http://{host}:{port}/documentation, where host and port are values entered in setup step.
This will open api testing page.
You can use /auth/ call with credentials created in setup step to get access token. Use access token from the response to authenticate (use the button in the UI) to be able to access other api routes.
- Run
yarnin the main directory to install dependencies - Configure by running
yarn setup:testcommand. Keep in mind that the database you set will be cleaned up on every tests run, so use a different one from production. - Run
yarn test
- Run
yarnin the main directory to install dependencies - Configure by running
yarn setup:devcommand - Run
yarn start:dev
Directory structure is configured as a monorepo.
Currently has only server project.
Additional projects can be added by creating a new directory with tsconfig and appending it to the main tsconfig.ts file.
Directories:
scripts- contains scripts that can be run usingyarntypes- contains typescript definitions for libraries that doesn't support typescriptserver- contains API project
Server project directory structure:
framework- generic things required to run the server, such as server, controller and actionsmodels- data schemasrepositories- objects, that interact with data storesservices- objects, that contain business logiccontrollers- objects, that contain actions. Action handles http requests.
Framework consists of 3 things:
server, defined inframework/server.ts. Sets up and controls http server.controller, defined inframework/controller.ts. Groups actions and adds route prefix to them.action, defined inframework/action.ts. Action is an http request handler. They are typed using zod and does automatic type inference based on givenparam,query,bodyandoutputparameters.
Example of basic public controller with GET action that reverses a given string in a query ?str=:
export default Controller('/strings', { reverseString: Action.publicGet( { route: '/reverse', summary: 'Reverses a given string', query: { str: z.string().nonempty().describe('String to reverse') }, output: z.string().describe('Reversed string'), }, (userId, { str }) => str.split('').reverse().join(''), ), });
All actions requires authentication by default: Action.get, Action.post, etc.
To make action accessable without authentication, use public actions: Action.publicGet, Action.publicPost, etc.
- Add better database abstraction, maybe even some query builder
- Add http rate limiting using
Fastify-rate-limitlibrary - Add cors configuration using
fastify-corslibrary - Add middleware support
- Separate action input by their sources