import express from 'express'
import jwt from 'jwt-simple'
import mongoose from 'mongoose'
import bcrypt from 'bcrypt'
import { writeFile } from 'fs'

import User from '../models/user'
import config from '../config/database'

const authenticate = express.Router()

mongoose.connect(config.database, {
  connectTimeoutMS: 1000
})

function initDB() {
  User.findOne({username: "admin"}, (err, user) => {
    if (err) {
      console.log(err.toString())
    }
    if (!user) {
      console.log("Uninitialized database. Creating admin user.")
      const password = Math.random().toString(36).substr(2)
      const admin = new User({
        username: "admin",
        name: "Administrator",
        password
      })
      admin.save()
      writeFile("/admin_password", password, (err) => {
        if (err) {
          console.log(err.toString())
        }
        console.log("Wrote password in text file.")
      })
    }
  })
}

initDB()

authenticate.post('/login', (req, res) => {
  const { username, password } = req.body
  if (!username || !password) {
    console.log('parameters missing', username, password)
    return res.status(400).json({
      msg: 'Parameters username and password are required' 
    })
  }

  User.findOne({ username }, (err, user) => {
    if (err) {
      console.log('login', err)
      return res.status(400).json({ 
        msg: err.toString() 
      })
    }
    if (!user) {
      console.log('login user not found')
      return res.status(400).json({ 
        msg: 'Authentication failed. User not found.' 
      })
    }
    if (!bcrypt.compareSync(password, user.password)) {
      console.log('login password mismatch')
      return res.status(400).json({ 
        msg: 'Authentication failed. Wrong password' 
      })
    } else {
      const token = jwt.encode({
        expires: Date.now() + 24*60*60*1000,
        user: { username: user.username, name: user.name }
      }, config.secret)
      console.log('login successful', user.username)
      return res.json({ 
        token
      })
    }
  })
})

const verify = express.Router()

verify.use( (req, res, next) => {
  const token = req.headers['x-access-token']

  if (token) {
    const decoded = jwt.decode(token, config.secret)
    if (decoded.expires < Date.now()) {
      return res.status(403).json({
        msg: 'Token expired.'
      })
    }
    req.decoded = decoded
    next()

  } else {
    return res.status(403).json({
      msg: 'No token provided.'
    })
  }
})

export { authenticate, verify }