2016-01-25 17:14:42 +01:00
ActiveEntry = { } ;
ActiveEntry . isAbc = function ( ) {
return "abc" ;
} ;
if ( Meteor . isClient ) {
Session . setDefault ( 'Photonic.ActiveEntry' , {
logo : {
url : "https://upload.wikimedia.org/wikipedia/commons/1/1a/Photon-photon_scattering.png" ,
displayed : true
} ,
signIn : {
displayFullName : true ,
destination : "/"
} ,
signUp : {
destination : "/"
} ,
themeColors : {
primary : ""
2016-02-04 23:53:01 +01:00
} ,
passwordOptions : {
2016-02-11 14:48:11 +01:00
showPasswordStrengthIndicator : true ,
2016-02-15 02:45:04 +01:00
requireRegexValidation : true ,
2016-02-11 14:48:11 +01:00
//requireStrongPasswords: false
2016-02-15 02:45:04 +01:00
passwordHistoryCount : 6 ,
2016-02-15 19:09:58 +01:00
failedAttemptsLimit : 5 ,
2016-02-15 22:40:53 +01:00
passwordExpirationDays : 90 ,
inactivityPeriodDays : 180
2016-01-25 17:14:42 +01:00
}
2016-02-14 23:03:00 +01:00
2016-01-25 17:14:42 +01:00
} ) ;
}
2016-02-11 14:48:11 +01:00
// requireRegexValidation toggles regex
// reqiureStrongPasswords toggles zxcvbn
2016-01-25 17:14:42 +01:00
if ( Meteor . isClient ) {
ActiveEntry . errorMessages = new ReactiveDict ( 'errorMessages' ) ;
ActiveEntry . errorMessages . set ( 'signInError' , false ) ;
2016-02-02 16:25:02 +01:00
// Success messages
ActiveEntry . successMessages = new ReactiveDict ( 'successMessages' ) ;
2016-01-25 17:14:42 +01:00
2016-02-04 23:53:01 +01:00
// Change password warning message according to whether zxcvbn is turned on
Session . set ( 'passwordWarning' , 'Password must have at least 8 characters. It must contain at least 1 uppercase, 1 lowercase, 1 number and 1 special character.' ) ;
2016-01-25 17:14:42 +01:00
}
ActiveEntry . configure = function ( configObject ) {
if ( Meteor . isClient ) {
2016-02-15 19:09:58 +01:00
// Set passwordOptions if they are not defined
if ( ! configObject . passwordOptions ) {
configObject . passwordOptions = {
showPasswordStrengthIndicator : true ,
requireRegexValidation : false ,
//requireStrongPasswords: false
passwordHistoryCount : 6 ,
failedAttemptsLimit : 5 ,
2016-02-15 22:40:53 +01:00
passwordExpirationDays : 90 ,
inactivityPeriodDays : 180
2016-02-15 19:09:58 +01:00
}
}
2016-01-25 17:14:42 +01:00
Session . set ( 'Photonic.ActiveEntry' , configObject ) ;
}
} ;
ActiveEntry . verifyPassword = function ( password ) {
if ( password . length === 0 ) {
ActiveEntry . errorMessages . set ( 'password' , 'Password is required' ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'password' , null ) ;
2016-02-04 23:53:01 +01:00
} else if ( ! checkPasswordStrength ( password ) ) {
ActiveEntry . errorMessages . set ( 'password' , Session . get ( 'passwordWarning' ) ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'password' , null ) ;
} else {
ActiveEntry . errorMessages . set ( 'password' , null ) ;
ActiveEntry . successMessages . set ( 'password' , 'Password present' ) ;
2016-01-25 17:14:42 +01:00
}
} ;
2016-02-03 20:41:51 +01:00
2016-01-25 17:14:42 +01:00
ActiveEntry . verifyConfirmPassword = function ( password , confirmPassword ) {
2016-02-11 14:48:11 +01:00
// we have two different logic checks happening in this function
// would be reasonable to separate them out into separate functions
if ( confirmPassword === "" ) {
2016-01-25 17:14:42 +01:00
ActiveEntry . errorMessages . set ( 'confirm' , 'Password is required' ) ;
2016-02-11 14:48:11 +01:00
ActiveEntry . successMessages . set ( 'confirm' , null ) ;
} else if ( confirmPassword === password ) {
2016-02-02 16:25:02 +01:00
ActiveEntry . errorMessages . set ( 'confirm' , null ) ;
ActiveEntry . successMessages . set ( 'confirm' , 'Passwords match' ) ;
2016-02-11 14:48:11 +01:00
} else {
2016-02-02 21:31:01 +01:00
ActiveEntry . errorMessages . set ( 'confirm' , 'Passwords do not match' ) ;
ActiveEntry . successMessages . set ( 'confirm' , null ) ;
2016-01-25 17:14:42 +01:00
}
} ;
2016-02-03 20:41:51 +01:00
2016-01-25 17:14:42 +01:00
ActiveEntry . verifyEmail = function ( email ) {
if ( email . length === 0 ) {
ActiveEntry . errorMessages . set ( 'email' , 'Email is required' ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'email' , null ) ;
2016-01-25 17:14:42 +01:00
} else if ( email . indexOf ( "@" ) === - 1 ) {
ActiveEntry . errorMessages . set ( 'email' , 'Email is poorly formatted' ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'email' , null ) ;
2016-01-25 17:14:42 +01:00
} else if ( email . indexOf ( "@" ) >= 0 ) {
2016-02-02 16:25:02 +01:00
ActiveEntry . errorMessages . set ( 'email' , null ) ;
ActiveEntry . successMessages . set ( 'email' , 'Email present' ) ;
2016-01-25 17:14:42 +01:00
}
} ;
2016-02-03 20:41:51 +01:00
2016-01-25 17:14:42 +01:00
ActiveEntry . verifyFullName = function ( fullName ) {
if ( fullName . length === 0 ) {
ActiveEntry . errorMessages . set ( 'fullName' , 'Name is required' ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'fullName' , null ) ;
2016-01-25 17:14:42 +01:00
} else if ( fullName . indexOf ( " " ) === - 1 ) {
ActiveEntry . errorMessages . set ( 'fullName' , 'Name is probably not complete' ) ;
2016-02-02 16:25:02 +01:00
ActiveEntry . successMessages . set ( 'fullName' , null ) ;
2016-01-25 17:14:42 +01:00
} else if ( fullName . indexOf ( " " ) >= 0 ) {
2016-02-02 16:25:02 +01:00
//ActiveEntry.errorMessages.set('fullName', 'Name present');
ActiveEntry . errorMessages . set ( 'fullName' , null ) ;
ActiveEntry . successMessages . set ( 'fullName' , 'Name present' ) ;
2016-01-25 17:14:42 +01:00
}
} ;
ActiveEntry . signIn = function ( emailValue , passwordValue ) {
2016-02-15 19:09:58 +01:00
2016-01-25 17:14:42 +01:00
ActiveEntry . verifyPassword ( passwordValue ) ;
ActiveEntry . verifyEmail ( emailValue ) ;
2016-02-15 19:09:58 +01:00
2016-02-14 23:03:00 +01:00
var ActiveEntryConfig = Session . get ( 'Photonic.ActiveEntry' ) ;
var failedAttemptsLimit = ActiveEntryConfig && ActiveEntryConfig . passwordOptions && ActiveEntryConfig . passwordOptions . failedAttemptsLimit || 5 ;
2016-02-15 19:09:58 +01:00
var passwordExpirationDays = ActiveEntryConfig && ActiveEntryConfig . passwordOptions && ActiveEntryConfig . passwordOptions . passwordExpirationDays || 90 ;
2016-02-15 22:40:53 +01:00
var inactivityPeriodDays = ActiveEntryConfig && ActiveEntryConfig . passwordOptions && ActiveEntryConfig . passwordOptions . inactivityPeriodDays || 180 ;
2016-01-25 17:14:42 +01:00
2016-02-15 22:40:53 +01:00
Meteor . call ( "isAccountInactive" , [ emailValue , inactivityPeriodDays ] , function ( error , isAccountInactive ) {
2016-01-25 17:14:42 +01:00
if ( error ) {
2016-02-15 19:09:58 +01:00
console . warn ( error ) ;
2016-01-25 17:14:42 +01:00
} else {
2016-02-15 22:40:53 +01:00
if ( isAccountInactive ) {
// Lock account
Meteor . call ( "lockAccount" , emailValue ) ;
ActiveEntry . errorMessages . set ( 'signInError' , "Your account has been locked due to inactivity." ) ;
2016-02-15 19:09:58 +01:00
return ;
2016-02-15 22:40:53 +01:00
} else {
// Check account is locked
Meteor . call ( "isAccountLocked" , function ( error , isAccountLocked ) {
if ( error ) {
console . warn ( error ) ;
} else {
2016-02-15 19:09:58 +01:00
2016-02-15 22:40:53 +01:00
if ( isAccountLocked ) {
ActiveEntry . errorMessages . set ( 'signInError' , "Your account has been locked." ) ;
return ;
}
2016-02-15 19:09:58 +01:00
2016-02-15 22:40:53 +01:00
Meteor . call ( "getFailedAttemptsCount" , emailValue , function ( error , failedAttemptsCount ) {
if ( error ) {
console . warn ( error . message ) ;
2016-02-14 23:03:00 +01:00
} else {
2016-02-15 22:40:53 +01:00
if ( failedAttemptsCount != failedAttemptsLimit ) {
Meteor . loginWithPassword ( { email : emailValue } , passwordValue , function ( loginError , result ) {
if ( loginError ) {
// Login failed
Meteor . call ( "updateFailedAttempts" , [ emailValue , failedAttemptsLimit ] , function ( error , failedAttemptCount ) {
if ( error ) {
console . warn ( error ) ;
} else {
if ( failedAttemptCount == failedAttemptsLimit ) {
ActiveEntry . errorMessages . set ( 'signInError' , "Too many failed login attempts. Your account has been locked." ) ;
} else if ( failedAttemptCount < failedAttemptsLimit ) {
ActiveEntry . errorMessages . set ( 'signInError' , loginError . message + "<br />" + ( failedAttemptsLimit - failedAttemptCount ) + " attempts remaining." ) ;
} else {
ActiveEntry . errorMessages . set ( 'signInError' , loginError . message ) ;
}
}
} ) ;
2016-02-15 19:09:58 +01:00
} else {
2016-02-15 22:40:53 +01:00
// Reset failed attempts
Meteor . call ( "resetFailedAttempts" , emailValue ) ;
// Check password expiration
// if password expired, route to changePassword page
Meteor . call ( "isPasswordExpired" , passwordExpirationDays , function ( error , isPasswordExpired ) {
if ( error ) {
console . warn ( error ) ;
} else {
// Update last login time
Meteor . call ( "updateLastLoginDate" ) ;
if ( isPasswordExpired ) {
ActiveEntry . errorMessages . set ( 'changePasswordError' , 'Your password expired. Please change your password.' ) ;
Router . go ( '/changePassword' ) ;
} else {
Router . go ( ActiveEntryConfig . signIn . destination ) ;
}
}
} ) ;
2016-02-14 23:03:00 +01:00
2016-02-15 22:40:53 +01:00
}
} ) ;
} else {
ActiveEntry . errorMessages . set ( 'signInError' , "Your account has been locked." ) ;
}
2016-02-14 23:03:00 +01:00
}
2016-02-15 22:40:53 +01:00
2016-02-14 23:03:00 +01:00
} ) ;
2016-02-15 19:09:58 +01:00
2016-02-15 22:40:53 +01:00
}
2016-02-15 19:09:58 +01:00
2016-02-15 22:40:53 +01:00
} ) ;
}
2016-01-25 17:14:42 +01:00
}
} ) ;
2016-02-14 23:03:00 +01:00
2016-01-25 17:14:42 +01:00
} ;
ActiveEntry . signUp = function ( emailValue , passwordValue , confirmPassword , fullName ) {
ActiveEntry . verifyEmail ( emailValue ) ;
ActiveEntry . verifyPassword ( passwordValue ) ;
ActiveEntry . verifyConfirmPassword ( passwordValue , confirmPassword ) ;
ActiveEntry . verifyFullName ( fullName ) ;
2016-02-02 21:31:01 +01:00
ActiveEntry . errorMessages . set ( 'signInError' , null ) ;
2016-01-25 17:14:42 +01:00
2016-02-02 16:25:02 +01:00
var errorIsFound = false ;
Object . keys ( ActiveEntry . errorMessages . keys ) . forEach ( function ( key ) {
if ( ActiveEntry . errorMessages . get ( key ) !== "null" && ActiveEntry . errorMessages . get ( key ) !== null ) {
errorIsFound = true ;
}
} ) ;
if ( errorIsFound ) {
return ;
}
2016-01-25 17:14:42 +01:00
Accounts . createUser ( {
email : emailValue ,
password : passwordValue ,
profile : {
fullName : fullName
2016-02-14 23:03:00 +01:00
} ,
testCase : {
createdAt : new Date ( )
2016-01-25 17:14:42 +01:00
}
} , function ( error , result ) {
if ( error ) {
ActiveEntry . errorMessages . set ( 'signInError' , error . message ) ;
} else {
2016-02-15 22:40:53 +01:00
// Add password in previousPasswords field
2016-02-14 23:03:00 +01:00
ActiveEntry . insertHashedPassword ( passwordValue ) ;
2016-02-15 19:09:58 +01:00
// Update password set date
ActiveEntry . updatePasswordSetDate ( ) ;
2016-02-15 22:40:53 +01:00
// Update last login time
Meteor . call ( "updateLastLoginDate" ) ;
2016-01-25 17:14:42 +01:00
var ActiveEntryConfig = Session . get ( 'Photonic.ActiveEntry' ) ;
Router . go ( ActiveEntryConfig . signUp . destination ) ;
}
} ) ;
} ;
2016-02-14 23:03:00 +01:00
2016-03-16 15:28:07 +01:00
ActiveEntry . forgotPassword = function ( emailAddress ) {
ActiveEntry . verifyEmail ( emailAddress ) ;
ActiveEntry . errorMessages . set ( "forgotPassword" , null ) ;
ActiveEntry . successMessages . set ( "forgotPassword" , null ) ;
if ( ActiveEntry . errorMessages . get ( "email" ) ) {
return ;
}
Accounts . forgotPassword ( { email : emailAddress } , function ( error ) {
if ( error ) {
console . warn ( error . message ) ;
ActiveEntry . errorMessages . set ( "forgotPassword" , error . message ) ;
return ;
}
// Show email sent notification
ActiveEntry . successMessages . set ( "forgotPassword" , "Your password reset email is sent to <strong>" + emailAddress + "</strong>" ) ;
} ) ;
} ;
ActiveEntry . resetPassword = function ( passwordValue , confirmPassword ) {
ActiveEntry . verifyPassword ( passwordValue ) ;
ActiveEntry . verifyConfirmPassword ( passwordValue , confirmPassword ) ;
ActiveEntry . errorMessages . set ( "resetPassword" , null ) ;
// Check error messages
if ( ActiveEntry . errorMessages . get ( "password" ) || ActiveEntry . errorMessages . get ( "confirm" ) ) {
return ;
}
Accounts . resetPassword ( Session . get ( '_resetPasswordToken' ) , passwordValue , function ( error ) {
if ( error ) {
ActiveEntry . errorMessages . set ( "resetPassword" , error . message ) ;
return ;
}
Session . set ( '_resetPasswordToken' , null ) ;
var ActiveEntryConfig = Session . get ( 'Photonic.ActiveEntry' ) ;
Router . go ( ActiveEntryConfig . signIn . destination ) ;
} ) ;
} ;
2016-02-14 23:03:00 +01:00
// Insert hashed password in previousPasswords fields
ActiveEntry . insertHashedPassword = function ( passwordValue ) {
var ActiveEntryConfig = Session . get ( 'Photonic.ActiveEntry' ) ;
var passwordHistoryCount = ActiveEntryConfig && ActiveEntryConfig . passwordOptions && ActiveEntryConfig . passwordOptions . passwordHistoryCount || 6 ;
Meteor . call ( "insertHashedPassword" , [ new String ( passwordValue ) . hashCode ( ) , passwordHistoryCount ] ) ;
} ;
2016-02-15 19:09:58 +01:00
ActiveEntry . updatePasswordSetDate = function ( ) {
Meteor . call ( "updatePasswordSetDate" ) ;
2016-02-14 23:03:00 +01:00
} ;
2016-01-25 17:14:42 +01:00
ActiveEntry . signOut = function ( ) {
Meteor . logout ( ) ;
} ;
ActiveEntry . reset = function ( ) {
2016-02-02 21:31:01 +01:00
ActiveEntry . errorMessages . set ( 'signInError' , false ) ;
2016-01-25 17:14:42 +01:00
ActiveEntry . errorMessages . set ( 'fullName' , false ) ;
ActiveEntry . errorMessages . set ( 'email' , false ) ;
ActiveEntry . errorMessages . set ( 'confirm' , false ) ;
ActiveEntry . errorMessages . set ( 'password' , false ) ;
} ;
2016-02-03 20:41:51 +01:00
2016-01-25 17:14:42 +01:00
ActiveEntry . logoIsDisplayed = function ( ) {
var ActiveEntryConfig = Session . get ( 'Photonic.ActiveEntry' ) ;
return ActiveEntryConfig . logo . displayed ;
2016-02-03 20:41:51 +01:00
} ;