1 | var passwordHash = require('password-hash')
|
2 | var shortid = require('shortid')
|
3 | var Promise = require('bluebird')
|
4 |
|
5 | function UsersRepository (reporter) {
|
6 | var self = this
|
7 |
|
8 | this.reporter = reporter
|
9 |
|
10 | this.UserType = this.reporter.documentStore.registerEntityType('UserType', {
|
11 | _id: {type: 'Edm.String', key: true},
|
12 | shortid: {type: 'Edm.String'},
|
13 | username: {type: 'Edm.String'},
|
14 | password: {type: 'Edm.String'}
|
15 | })
|
16 |
|
17 | this.reporter.documentStore.registerEntitySet('users', {entityType: 'jsreport.UserType', humanReadableKey: 'shortid'})
|
18 |
|
19 | this.reporter.initializeListeners.add('repository', function () {
|
20 | var col = self.usersCollection = self.reporter.documentStore.collection('users')
|
21 |
|
22 | col.beforeInsertListeners.add('users', function (doc) {
|
23 | if (!doc.shortid) {
|
24 | doc.shortid = shortid.generate()
|
25 | }
|
26 |
|
27 | if (!doc.username) {
|
28 | throw new Error('username is required')
|
29 | }
|
30 |
|
31 | if (typeof doc.username !== 'string') {
|
32 | throw new Error('username has an invalid value')
|
33 | }
|
34 |
|
35 |
|
36 | doc.username = doc.username.trim()
|
37 |
|
38 | if (!doc.password) {
|
39 | throw new Error('password is required')
|
40 | }
|
41 |
|
42 | if (typeof doc.password !== 'string') {
|
43 | throw new Error('password has an invalid value')
|
44 | }
|
45 |
|
46 | delete doc.passwordVerification
|
47 |
|
48 | doc.password = passwordHash.generate(doc.password)
|
49 |
|
50 | return self.validate(doc)
|
51 | })
|
52 | })
|
53 | }
|
54 |
|
55 | UsersRepository.prototype.validate = function (user) {
|
56 | return this.find(user.username).then(function (user) {
|
57 | if (user) {
|
58 | return Promise.reject(new Error('User already exists'))
|
59 | }
|
60 |
|
61 | return true
|
62 | })
|
63 | }
|
64 |
|
65 | UsersRepository.prototype.authenticate = function (username, password) {
|
66 | return this.usersCollection.find({username: username}).then(function (users) {
|
67 | if (users.length !== 1 || !passwordHash.verify(password, users[0].password)) {
|
68 | return null
|
69 | }
|
70 | return users[0]
|
71 | })
|
72 | }
|
73 |
|
74 | UsersRepository.prototype.find = function (username) {
|
75 | return this.usersCollection.find({username: username}).then(function (users) {
|
76 | if (users.length !== 1) {
|
77 | return null
|
78 | }
|
79 |
|
80 | return users[0]
|
81 | })
|
82 | }
|
83 |
|
84 | UsersRepository.prototype.changePassword = function (currentUser, shortid, oldPassword, newPassword) {
|
85 | var self = this
|
86 |
|
87 | return this.usersCollection.find({ shortid: shortid }).then(function (users) {
|
88 | var user = users[0]
|
89 | var password = newPassword
|
90 |
|
91 | if (!currentUser.isAdmin && !passwordHash.verify(oldPassword, user.password)) {
|
92 | return Promise.reject(new Error('Invalid password'))
|
93 | }
|
94 |
|
95 | if (!password) {
|
96 | throw new Error('password is required')
|
97 | }
|
98 |
|
99 | if (typeof password !== 'string') {
|
100 | throw new Error('password has an invalid value')
|
101 | }
|
102 |
|
103 | password = passwordHash.generate(password)
|
104 |
|
105 | return self.usersCollection.update({ shortid: shortid }, { $set: { password: password } })
|
106 | })
|
107 | }
|
108 |
|
109 | module.exports = UsersRepository
|