1.0.0 • Published 6 months ago

@uscreen.de/fastify-mongo-auth v1.0.0

Weekly downloads
-
License
MIT
Repository
github
Last release
6 months ago

fastify-mongo-auth

Test CI Test Coverage Known Vulnerabilities NPM Version

Stateless session backed by authentication against mongodb collection

Provides:

  • fastify.auth - the authentication adapter with it's api (see below)
  • req.session - as provided by @fastify/secure-session
  • req.user - (default, customize by decorateRequest option) will be a current authenticated user account

Uses secure-password for hashing and verification

Install

$ yarn add @uscreen.de/fastify-mongo-auth

Add Dependencies

$ yarn add @fastify/mongodb @uscreen.de/fastify-mongo-crud

The session package @fastify/secure-session (see @npm) requires a secret or key. We stick to recommended setup with a generated key below, so you should generate one too:

$ secure-session-gen-key > session-key

Example

Setup within a plugins/mongo.js file to resolve required dependencies before:

import fs from 'fs'
import path from 'path'
import fp from 'fastify-plugin'
import mongodb from '@fastify/mongodb'
import crud from '@uscreen.de/fastify-mongo-crud'
import auth from '@uscreen.de/fastify-mongo-auth'

/**
 * mongodb related
 */
export default fp(async (fastify, opts) => {
  /**
   * 1) setup mongodb connection
   */
  await fastify.register(mongodb, {
    url: opts.mongoUri
  })

  /**
   * 2) setup CRUD factory
   */
  await fastify.register(crud)

  /**
   * 3) enable authentication
   */
  await fastify.register(auth, {
    key: fs.readFileSync(path.join(fastify.root, 'session-key')),
    decorateRequest: 'account'
  })
})

Prepare account within a service/accounts.js file:

export default async fastify => {
  const { auth } = fastify

  /**
   * registration
   * -> body.{username, password}
   * <- account.{username, _id}
   */
  fastify.post('/register', async req => ({
    account: await auth.collection.create({
      hash: auth.createHash(req.body.password),
      username: req.body.username.toLowerCase()
    })
  }))
}

Usage within a services/auth.js file:

export default async fastify => {
  const { auth } = fastify

  /**
   * authentication / login
   * -> body.{username, password}
   * <- account.{username, _id}
   */
  fastify.post('/login', auth.loginHandler)

  /**
   * authentication / logout
   * -> {} - no payload required
   * <- {} - no payload returned
   */
  fastify.post('/logout', auth.logoutHandler)

  /**
   * authentication / check currentUser
   * <- account.{username, _id}
   */
  fastify.get(
    '/currentUser',
    {
      preHandler: auth.authorized
    },
    auth.currentUserHandler
  )
}

Options

OptionDescriptionDefault
collectionName of the mongodb collection the accounts are stored in."accounts"
cookieOptions for session cookie as listed here cookie.{ path: '/' }
keyPath to file of session-key @fastify/secure-session uses to ensure secure stateless cookie sessions.""
decorateRequestProperty providing current authenticated account object within request object. (ie.: req.user as default)"user"
usernameToLowerCaseShould usernames be treated case-insensitive (by lower-casing all queries) or not.true
usernameFieldName of property for usernames. Affects mongodb documents and the login handler (see below)."username"
passwordFieldName of property for passwords."password"

API

get collection()

Returns the fastify-mongo-crud collection object where the accounts are stored.

authorized(req, res, next)

PreHandler validating authentication. Throws an 401 Unauthorized error on unvalid authentication.

createHash(password)

Creates a hash from given password. Useful when creating a new account or changing an account's password.

verifyHash(password, hash)

Verifies the given password to the given hash.

async loginHandler(req)

Handler for logging in to an account (i.e. called by POST /login). Expects a req object with a body containing credentials as configured in Options, defaults to:

{
  "username": "a user's name",
  "password": "a user's password"
}

async logoutHandler(req)

Handler for logging off from an account (i.e. called by POST /logout). Expects a req object without a body.

async currentUserHandler(req)

Handler returning the current authenticated account (i.e. called by GET /currentUser) or an empty object if no account is authenticated. Expects a req object without a body.


Roadmap

  • test
  • docs
  • improved dependency handling
  • improved onboarding
  • maybe add more handler (register, reset, etc.)?
  • maybe add routes?

Changelog

v1.0.0

Changed

  • switch to ESM only
  • upgrade to fastify@4.x

v0.2.0

Added

  • cookie options (see cookie defaults to { path: '/' }

v0.1.0

Changed

  • uses lower case usernames by default
  • preHandler stops logging empty session as error

Added

  • new option usernameToLowerCase to disable case-insensitive usernames (defaults to true)

v0.0.0

  • init

License

Licensed under MIT.

Published, Supported and Sponsored by u|screen

1.0.0

6 months ago

1.0.0-3

1 year ago

0.3.18

1 year ago

1.0.0-2

1 year ago

1.0.0-1

1 year ago

0.3.17

1 year ago

0.3.16

2 years ago

0.3.15

2 years ago

0.3.14

2 years ago

0.3.13

2 years ago

0.3.12

2 years ago

0.3.11

2 years ago

0.3.10

2 years ago

0.3.9

2 years ago

0.3.8

2 years ago

0.3.7

2 years ago

0.3.6

2 years ago

0.3.5

3 years ago

0.3.4

3 years ago

0.3.3

3 years ago

0.3.2

3 years ago

0.3.1

4 years ago

0.3.0

4 years ago

0.2.1

4 years ago

0.2.0

4 years ago

0.1.4

4 years ago

0.1.3

4 years ago

0.1.2

4 years ago

0.1.1

4 years ago

0.1.0

4 years ago

0.0.2

4 years ago

0.0.1

4 years ago

0.0.0

5 years ago