@mersocarlin/node-server
v1.1.0
Published
Enhanced fastify server cookie-parser, cors, helmet, rate-limiter and opt-in Mongo DB connection.
Downloads
26
Maintainers
Readme
@mersocarlin/node-server
Enhanced fastify server with cookie-parser
, cors
, helmet
, rate-limiter and opt-in Mongo DB connection.
Motivation
Whenever I write a new node server, I end up creating the same boilerplate using similar express middleware: cookie-parser
, helmet
, cors
, express-rate-limit
... not to mention the default error handler for express apps.
Just thought about extracting all that into a single package so I can focus only on the api routes + business logic of my node-server and leave common config to be handled somewhere else.
Install
yarn add @mersocarlin/node-server
npm i @mersocarlin/node-server
What's included
fastify-cookie
fastify-cors
fastify-helmet
fastify-rate-limit
mongoose
connection (opt-in)- basic repository for CRUD entities
Usage
import { FastifyInstance } from 'fastify'
import { createServer } from '@mersocarlin/node-server'
/**
* Setup custom routes and/or plugins
**/
function onRegisterPlugins(fastifyInstance: FastifyInstance) {
fastifyInstance.post('/signin', async () => {
return {
loggedIn: true,
}
})
fastifyInstance.get('/users/:userId', async (request) => {
return {
id: request.params.userId,
}
})
}
import { createServer } from '@mersocarlin/node-server'
const fastifyServer = createServer({
appName: 'my-custom-server',
onRegisterPlugins,
version: '1.0.0',
})
async function startServer() {
try {
await testFastifyServer.listen(PORT, '0.0.0.0')
} catch (err) {
testFastifyServer.log.error(err)
process.exit(1)
}
}
Note: If you have a single node-server you might not need this package at all. In my case though, I have a few APIs spread across different repos and I realised they all share the same initial config.
Mongo repository
Create Entity types
import { Document } from 'mongoose'
interface IEntity {
name: string
value: string
}
// Used for querying DB
interface IEntityQuery {
name?: string
value?: string
}
interface IMyDocument extends Document {
name: string
value: string
}
Create schema and model
import mongoose, { Schema } from 'mongoose'
const MySchema = new Schema({
name: { type: String, required: true },
value: { type: String, required: true },
})
const myModel = mongoose.model<IMyDocument>('mymodel', MySchema)
Create repository and start CRUD
import { createRepository } from '@mersocarlin/node-server'
const modelRepository = createRepository<IMyDocument, IEntityQuery, IEntity>(
myModel
)
// Save to DB
const dbEntity = await modelRepository.create({
name: 'Test',
value: 'Some value',
})
// Update
await modelRepository.update(dbEntity._id, {
name: 'New Name',
value: dbEntity.value,
})
// List
const allEntities = await modelRepository.find({})
const byName = await modelRepository.find({ name: 'New name' })
// Delete
await modelRepository.remove(dbEntity._id)
Response Time
Built-in
import { createServer } from '@mersocarlin/node-server'
import appRoutes from 'path/to/appRoutes.js'
const app = createServer({
appName: 'my-custom-server',
onResponseTime: ({ duration, requestName }) => {
console.log(`${requestName} took ${duration}ms`)
},
routesHandler: appRoutes,
version: '1.0.0',
})
API
createServer
| Prop | Type | Default | Description |
| ----------------- | -------- | ---------------------------------------- | ---------------------------------------------------------------------------------- |
| appName | String | | Your server or app name. Ex: my-rest-service
|
| healthcheckPath | String | /healthcheck
| Defines healthcheck endpont for node server |
| mongoDBConfig | Object | | Defines Mongo DB configuration for database connection |
| onResponseTime | Function | | Custom callback to track response time of each request |
| onRegisterPlugins | Function | | Custom callback setup your custom routes and plugins |
| rateLimitConfig | Object | { windowMs: 15 * 60 * 1000, max: 100 }
| Rate limit config as described in https://www.npmjs.com/package/express-rate-limit |
| version | String | | Your server's version printed out in healthcheckPath
endpoint |