You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

147 lines
3.7 KiB

  1. /* global WIKI */
  2. const express = require('express')
  3. const ExpressBrute = require('express-brute')
  4. const BruteKnex = require('brute-knex')
  5. const router = express.Router()
  6. const moment = require('moment')
  7. const _ = require('lodash')
  8. const bruteforce = new ExpressBrute(new BruteKnex({
  9. createTable: true,
  10. knex: WIKI.models.knex
  11. }), {
  12. freeRetries: 5,
  13. minWait: 5 * 60 * 1000, // 5 minutes
  14. maxWait: 60 * 60 * 1000, // 1 hour
  15. failCallback: (req, res, next) => {
  16. res.status(401).send('Too many failed attempts. Try again later.')
  17. }
  18. })
  19. /**
  20. * Login form
  21. */
  22. router.get('/login', async (req, res, next) => {
  23. _.set(res.locals, 'pageMeta.title', 'Login')
  24. if (req.query.legacy || req.get('user-agent').indexOf('Trident') >= 0) {
  25. const { formStrategies, socialStrategies } = await WIKI.models.authentication.getStrategiesForLegacyClient()
  26. res.render('legacy/login', {
  27. err: false,
  28. formStrategies,
  29. socialStrategies
  30. })
  31. } else {
  32. res.render('login')
  33. }
  34. })
  35. /**
  36. * Social Strategies Login
  37. */
  38. router.get('/login/:strategy', async (req, res, next) => {
  39. try {
  40. await WIKI.models.users.login({
  41. strategy: req.params.strategy
  42. }, { req, res })
  43. } catch (err) {
  44. next(err)
  45. }
  46. })
  47. /**
  48. * Social Strategies Callback
  49. */
  50. router.all('/login/:strategy/callback', async (req, res, next) => {
  51. if (req.method !== 'GET' && req.method !== 'POST') { return next() }
  52. try {
  53. const authResult = await WIKI.models.users.login({
  54. strategy: req.params.strategy
  55. }, { req, res })
  56. res.cookie('jwt', authResult.jwt, { expires: moment().add(1, 'y').toDate() })
  57. res.redirect('/')
  58. } catch (err) {
  59. next(err)
  60. }
  61. })
  62. /**
  63. * LEGACY - Login form handling
  64. */
  65. router.post('/login', bruteforce.prevent, async (req, res, next) => {
  66. _.set(res.locals, 'pageMeta.title', 'Login')
  67. if (req.query.legacy || req.get('user-agent').indexOf('Trident') >= 0) {
  68. try {
  69. const authResult = await WIKI.models.users.login({
  70. strategy: req.body.strategy,
  71. username: req.body.user,
  72. password: req.body.pass
  73. }, { req, res })
  74. req.brute.reset()
  75. res.cookie('jwt', authResult.jwt, { expires: moment().add(1, 'y').toDate() })
  76. res.redirect('/')
  77. } catch (err) {
  78. const { formStrategies, socialStrategies } = await WIKI.models.authentication.getStrategiesForLegacyClient()
  79. res.render('legacy/login', {
  80. err,
  81. formStrategies,
  82. socialStrategies
  83. })
  84. }
  85. } else {
  86. res.redirect('/login')
  87. }
  88. })
  89. /**
  90. * Logout
  91. */
  92. router.get('/logout', function (req, res) {
  93. req.logout()
  94. res.clearCookie('jwt')
  95. res.redirect('/')
  96. })
  97. /**
  98. * Register form
  99. */
  100. router.get('/register', async (req, res, next) => {
  101. _.set(res.locals, 'pageMeta.title', 'Register')
  102. const localStrg = await WIKI.models.authentication.getStrategy('local')
  103. if (localStrg.selfRegistration) {
  104. res.render('register')
  105. } else {
  106. next(new WIKI.Error.AuthRegistrationDisabled())
  107. }
  108. })
  109. /**
  110. * Verify
  111. */
  112. router.get('/verify/:token', bruteforce.prevent, async (req, res, next) => {
  113. try {
  114. const usr = await WIKI.models.userKeys.validateToken({ kind: 'verify', token: req.params.token })
  115. await WIKI.models.users.query().patch({ isVerified: true }).where('id', usr.id)
  116. const result = await WIKI.models.users.refreshToken(usr)
  117. req.brute.reset()
  118. res.cookie('jwt', result.token, { expires: moment().add(1, 'years').toDate() })
  119. res.redirect('/')
  120. } catch (err) {
  121. next(err)
  122. }
  123. })
  124. /**
  125. * JWT Public Endpoints
  126. */
  127. router.get('/.well-known/jwk.json', function (req, res, next) {
  128. res.json(WIKI.config.certs.jwk)
  129. })
  130. router.get('/.well-known/jwk.pem', function (req, res, next) {
  131. res.send(WIKI.config.certs.public)
  132. })
  133. module.exports = router