This repository has been archived on 2024-04-29. You can view files and clone it, but cannot push or open issues or pull requests.
node-fftcg/inc/fftcgdb.coffee

80 lines
1.9 KiB
CoffeeScript

# libraries
bcrypt = (require 'bcrypt')
sqlite3 = (require 'sqlite3').verbose()
# bruteforce countermeasure
saltRounds = 13
FFTCGDB = (filename) ->
@filename = filename
@db = new sqlite3.Database @filename, (err) ->
if err
console.error err.message
@db.run """
CREATE TABLE IF NOT EXISTS users (
login text NOT NULL COLLATE NOCASE,
pwdhash text NOT NULL,
session text,
UNIQUE(login)
);
"""
console.log "[FFTCGDB] Connected to '#{@filename}'"
return
FFTCGDB::close = ->
new Promise (resolve, reject) ->
@db.close (err) ->
if err
resolve "[FFTCGDB] Error closing: '#{err.message}'"
else
reject "[FFTCGDB] Closed '#{@filename}'"
FFTCGDB::register = (login, password) ->
that = @
new Promise (resolve, reject) ->
# validate username
# hash password
bcrypt.hash password, saltRounds, (err, hash) ->
reject 'hash' if err
# try creating row in users table
that.db.run "INSERT INTO users (login, pwdhash) VALUES ('#{login}', '#{hash}');", (err) ->
if err
if err.code == 'SQLITE_CONSTRAINT'
reject 'existence'
else
reject 'db'
else
# registration successful
resolve @lastID
FFTCGDB::login = (login, password) ->
that = @
new Promise (resolve, reject) ->
# validate username
# get users table row
that.db.all "SELECT rowid, pwdhash FROM users WHERE login = '#{login}';", (err, rows) ->
if err
reject 'db'
else if rows.length == 0
# hashing the password for timing attack reasons
bcrypt.hash password, saltRounds, (err, hash) ->
reject 'existence'
else
row = rows[0]
bcrypt.compare password, row.pwdhash, (err, res) ->
reject 'hash' if err
if res == true
resolve row.rowid
else
reject 'login'
module.exports = FFTCGDB