// TestLoginUser validates a user can login and not after changes. func TestLoginUser(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to test user login.") { t.Log("\tWhen using a new user") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID if _, err := auth.LoginUser(tests.Context, db, u1.Email, "_Password124"); err != nil { t.Errorf("\t%s\tShould be able to login the user : %v", tests.Failed, err) } else { t.Logf("\t%s\tShould be able to login the user.", tests.Success) } if err := auth.UpdateUserPassword(tests.Context, db, u1, "password890"); err != nil { t.Fatalf("\t%s\tShould be able to update the user password : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to update the user password.", tests.Success) if _, err := auth.LoginUser(tests.Context, db, u1.Email, "_Password124"); err == nil { t.Errorf("\t%s\tShould Not be able to login the user.", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to login the user.", tests.Success) } } } }
// runCreate is the code that implements the create command. func runCreate(cmd *cobra.Command, args []string) { cmd.Printf("Creating User : Name[%s] Email[%s] Pass[%s]\n", create.name, create.email, create.pass) if create.name == "" && create.email == "" && create.pass == "" { cmd.Help() return } u, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: create.name, Email: create.email, Password: create.pass, }) if err != nil { cmd.Println("Creating User : "******"", db, u); err != nil { cmd.Println("Creating User : "******"", db, u, 24*365*time.Hour) if err != nil { cmd.Println("Creating User : "******"\nToken: %s\n\n", webTok) }
// TestInvalidWebTokens tests create an invalid web token and tests it fails. func TestInvalidWebTokens(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) tokens := []string{ "", "6dcda2da-92c3-11e5-8994-feff819cdc9f", "OGY4OGI3YWQtZjc5Ny00ODI1LWI0MmUtMjIwZTY5ZDQxYjMzOmFKT2U1b0pFZlZ4cWUrR0JONEl0WlhmQTY0K3JsN2VGcmM2MVNQMkV1WVE9", } t.Log("Given the need to validate bad web tokens don't validate.") { for _, token := range tokens { t.Logf("\tWhen using token [%s]", token) { if _, err := auth.ValidateWebToken(tests.Context, db, token); err == nil { t.Errorf("\t%s\tShould Not be able to validate the web token : %v", tests.Failed, err) } else { t.Logf("\t%s\tShould Not be able to validate the web token.", tests.Success) } } } } }
// Mongo handles session management. func Mongo(h app.Handler) app.Handler { // Check if mongodb is configured. dbName, err := cfg.String(cfgMongoDB) if err != nil { return func(c *app.Context) error { log.Dev(c.SessionID, "Mongo", "******> Mongo Not Configured") return h(c) } } // Wrap the handlers inside a session copy/close. return func(c *app.Context) error { mgoDB, err := db.NewMGO("Mongo", dbName) if err != nil { log.Error(c.SessionID, "Mongo", err, "Method[%s] URL[%s] RADDR[%s]", c.Request.Method, c.Request.URL.Path, c.Request.RemoteAddr) return app.ErrDBNotConfigured } log.Dev(c.SessionID, "Mongo", "******> Capture Mongo Session") c.DB = mgoDB defer func() { log.Dev(c.SessionID, "Mongo", "******> Release Mongo Session") mgoDB.CloseMGO("Mongo") }() return h(c) } }
// runStatus is the code that implements the status command. func runStatus(cmd *cobra.Command, args []string) { cmd.Printf("Status User : Pid[%s] Email[%s] Active[%v]\n", status.pid, status.email, status.active) if status.pid == "" && status.email == "" { cmd.Help() return } db := db.NewMGO() defer db.CloseMGO() var publicID string if status.pid != "" { publicID = status.pid } else { u, err := auth.GetUserByEmail("", db, status.email, false) if err != nil { cmd.Println("Status User : "******"", db, publicID, st); err != nil { cmd.Println("Status User : "******"Status User : Updated") }
// TestDisableUser test the disabling of a user. func TestDisableUser(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to update a user.") { t.Log("\tWhen using an existing user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID u2, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by PublicID : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by PublicID.", tests.Success) if err := auth.UpdateUserStatus(tests.Context, db, u2.PublicID, auth.StatusDisabled); err != nil { t.Fatalf("\t%s\tShould be able to disable the user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to disable the user.", tests.Success) if _, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true); err == nil { t.Fatalf("\t%s\tShould Not be able to retrieve the user by PublicID.", tests.Failed) } t.Logf("\t%s\tShould Not be able to retrieve the user by PublicID.", tests.Success) } } }
// TestExpiredWebToken tests create a web token and tests when it expires. func TestExpiredWebToken(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to validate web tokens expire.") { t.Log("\tWhen using a new user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID webTok, err := auth.CreateWebToken(tests.Context, db, u1, 1*time.Millisecond) if err != nil { t.Fatalf("\t%s\tShould be able to create a web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a web token.", tests.Success) if _, err := auth.ValidateWebToken(tests.Context, db, webTok); err == nil { t.Fatalf("\t%s\tShould Not be able to validate the web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould Not be able to validate the web token.", tests.Success) } } }
// TestGetLatest tests the retrieval of the latest session. func TestGetLatest(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) defer func() { if err := removeSessions(db); err != nil { t.Errorf("\t%s\tShould be able to remove all sessions : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove all sessions.", tests.Success) }() t.Log("Given the need to get the latest sessions in the DB.") { t.Logf("\tWhen using PublicID %s", publicID) { if err := removeSessions(db); err != nil { t.Fatalf("\t%s\tShould be able to remove all sessions : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove all sessions.", tests.Success) if _, err := session.Create(tests.Context, db, publicID, 10*time.Second); err != nil { t.Fatalf("\t%s\tShould be able to create a session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a session.", tests.Success) time.Sleep(time.Second) s2, err := session.Create(tests.Context, db, publicID, 10*time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create another session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create another session.", tests.Success) s3, err := session.GetByLatest(tests.Context, db, publicID) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the latest session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the latest session.", tests.Success) if s2.SessionID != s3.SessionID { t.Errorf("\t%s\tShould be able to get back the latest session.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the latest session.", tests.Success) } } } }
// Handle is our mechanism for mounting Handlers for a given HTTP verb and path // pair, this makes for really easy, convenient routing. func (a *App) Handle(verb, path string, handler Handler, mw ...Middleware) { // The function to execute for each request. h := func(w http.ResponseWriter, r *http.Request, p map[string]string) { start := time.Now() var dbConn *db.DB if app.useMongo { dbConn = db.NewMGO() } c := Context{ DB: dbConn, ResponseWriter: w, Request: r, Params: p, SessionID: uuid.New(), } if app.useMongo { defer c.DB.CloseMGO() } log.User(c.SessionID, "Request", "Started : Method[%s] URL[%s] RADDR[%s]", c.Request.Method, c.Request.URL.Path, c.Request.RemoteAddr) // Wrap the handler in all associated middleware. wrap := func(h Handler) Handler { // Wrap up the application-wide first... for i := len(a.mw) - 1; i >= 0; i-- { h = a.mw[i](h) } // Then wrap with our route specific ones. for i := len(mw) - 1; i >= 0; i-- { h = mw[i](h) } return h } // Call the wrapped handler and handle any possible error. if err := wrap(handler)(&c); err != nil { c.Error(err) } log.User(c.SessionID, "Request", "Completed : Status[%d] Duration[%s]", c.Status, time.Since(start)) } // Add this handler for the specified verb and route. a.TreeMux.Handle(verb, path, h) }
// TestCreate tests the creation of sessions. func TestCreate(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db := db.NewMGO() defer db.CloseMGO() defer func() { if err := removeSessions(db); err != nil { t.Errorf("\t%s\tShould be able to remove all sessions : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove all sessions.", tests.Success) }() t.Log("Given the need to create sessions in the DB.") { t.Logf("\tWhen using PublicID %s", publicID) { if err := removeSessions(db); err != nil { t.Fatalf("\t%s\tShould be able to remove all sessions : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove all sessions.", tests.Success) s1, err := session.Create(tests.Context, db, publicID, 10*time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create a session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a session.", tests.Success) s2, err := session.GetBySessionID(tests.Context, db, s1.SessionID) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the session.", tests.Success) if s1.SessionID != s2.SessionID { t.Fatalf("\t%s\tShould be able to get back the same session.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the same session.", tests.Success) } if s1.PublicID != s2.PublicID { t.Fatalf("\t%s\tShould be able to get back the same user.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the same user.", tests.Success) } } } }
// TestCreateUserTwice tests the creation of the same user fails. This test // requires an index on the collection. func TestCreateUserTwice(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db := db.NewMGO() defer db.CloseMGO() var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to make sure the same user can't be created twice.") { t.Log("\tWhen using a test user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID if err := auth.CreateUser(tests.Context, db, u1); err == nil { t.Fatalf("\t%s\tShould Not be able to create a user", tests.Failed) } t.Logf("\t%s\tShould Not be able to create a user.", tests.Success) } } }
// TestGetNotFound tests when a session is not found. func TestGetNotFound(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db := db.NewMGO() defer db.CloseMGO() t.Log("Given the need to test finding a session and it is not found.") { t.Logf("\tWhen using SessionID %s", "NOT EXISTS") { if _, err := session.GetBySessionID(tests.Context, db, "NOT EXISTS"); err == nil { t.Fatalf("\t%s\tShould Not be able to retrieve the session.", tests.Failed) } t.Logf("\t%s\tShould Not be able to retrieve the session.", tests.Success) } } }
// runGet is the code that implements the get command. func runGet(cmd *cobra.Command, args []string) { cmd.Printf("Getting User : Pid[%s] Email[%s]\n", get.pid, get.email) if get.pid == "" && get.email == "" { cmd.Help() return } db, err := db.NewMGO("", mgoSession) if err != nil { cmd.Println("Getting User : "******"") var u *auth.User if get.pid != "" { u, err = auth.GetUserByPublicID("", db, get.pid, false) } else { u, err = auth.GetUserByEmail("", db, get.email, false) } if err != nil { cmd.Println("Getting User : "******"", db, u.PublicID) if err != nil { cmd.Println("Getting User : Unable to retrieve web token : ", err) } data, err := json.MarshalIndent(&u, "", " ") if err != nil { cmd.Println("Getting User : "******"\n%s\n\nToken: %s\n\n", string(data), webTok) return }
// TestUpdateInvalidUserPassword tests we can't update user password. func TestUpdateInvalidUserPassword(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) t.Log("Given the need to validate an invalid update to a user.") { t.Log("\tWhen using an existing user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.UpdateUserPassword(tests.Context, db, u1, "_Pass"); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with bad password.", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with bad password.", tests.Success) } u1.Status = auth.StatusDisabled if err := auth.UpdateUserPassword(tests.Context, db, u1, "_Password789"); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with bad user value.", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with bad user value.", tests.Success) } } } }
func main() { if err := cfg.Init(cfg.EnvProvider{Namespace: cfgNamespace}); err != nil { kit.Println("Unable to initialize configuration") os.Exit(1) } logLevel := func() int { ll, err := cfg.Int(cfgLoggingLevel) if err != nil { return log.NONE } return ll } log.Init(os.Stderr, logLevel) cfg := mongo.Config{ Host: cfg.MustString(cfgMongoHost), AuthDB: cfg.MustString(cfgMongoAuthDB), DB: cfg.MustString(cfgMongoDB), User: cfg.MustString(cfgMongoUser), Password: cfg.MustString(cfgMongoPassword), } if err := db.RegMasterSession("startup", cfg.DB, cfg); err != nil { kit.Println("Unable to initialize MongoDB") os.Exit(1) } db, err := db.NewMGO("", cfg.DB) if err != nil { kit.Println("Unable to get MongoDB session") os.Exit(1) } defer db.CloseMGO("") kit.AddCommand( cmdauth.GetCommands(db), cmddb.GetCommands(db), ) kit.Execute() }
func ensureIndexes() { db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { fmt.Printf("Should be able to get a Mongo session : %v", err) os.Exit(1) } defer db.CloseMGO(tests.Context) index := mgo.Index{ Key: []string{"public_id"}, Unique: true, } col, err := db.CollectionMGO(tests.Context, auth.Collection) if err != nil { fmt.Printf("Should be able to get a Mongo session : %v", err) os.Exit(1) } col.EnsureIndex(index) }
// runCreate is the code that implements the create command. func runCreate(cmd *cobra.Command, args []string) { dbMeta, err := retrieveDatabaseMetadata(create.file) if err != nil { dbCmd.Printf("Error reading collections : %s : ERROR : %v\n", create.file, err) return } db, err := db.NewMGO("", mgoSession) if err != nil { cmd.Println("Creating User : "******"") for _, col := range dbMeta.Cols { cmd.Println("Creating collection", col.Name) if err := createCollection(db, dbMeta, &col, true); err != nil && err != ErrCollectionExists { cmd.Println("ERROR:", err) return } } }
// TestUpdateUser tests we can update user information. func TestUpdateUser(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db := db.NewMGO() defer db.CloseMGO() var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to update a user.") { t.Log("\tWhen using an existing user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID uu := auth.UpdUser{ PublicID: publicID, Status: auth.StatusActive, FullName: "Update Kennedy", Email: "*****@*****.**", } if err := auth.UpdateUser(tests.Context, db, uu); err != nil { t.Fatalf("\t%s\tShould be able to update a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to update a user.", tests.Success) u2, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by PublicID : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by PublicID.", tests.Success) // Remove the objectid to be able to compare the values. u2.ID = "" // Need to remove the nanoseconds to be able to compare the values. u1.DateModified = u1.DateModified.Add(-time.Duration(u1.DateModified.Nanosecond())) u1.DateCreated = u1.DateCreated.Add(-time.Duration(u1.DateCreated.Nanosecond())) u2.DateModified = u2.DateModified.Add(-time.Duration(u2.DateModified.Nanosecond())) u2.DateCreated = u2.DateCreated.Add(-time.Duration(u2.DateCreated.Nanosecond())) // Update the fields that changed u1.Status = u2.Status u1.FullName = u2.FullName u1.Email = u2.Email if !reflect.DeepEqual(*u1, *u2) { t.Logf("\t%+v", *u1) t.Logf("\t%+v", *u2) t.Errorf("\t%s\tShould be able to get back the same user with changes.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the same user with changes.", tests.Success) } } } }
// TestCreateWebToken tests create a web token and a pairing session. func TestCreateWebToken(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to create a web token.") { t.Log("\tWhen using a new user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID webTok, err := auth.CreateWebToken(tests.Context, db, u1, time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create a web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a web token.", tests.Success) sId, _, err := auth.DecodeWebToken(tests.Context, webTok) if err != nil { t.Fatalf("\t%s\tShould be able to decode the web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to decode the web token.", tests.Success) s2, err := session.GetBySessionID(tests.Context, db, sId) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the session : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the session.", tests.Success) u2, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by PublicID : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by PublicID.", tests.Success) if u2.PublicID != s2.PublicID { t.Fatalf("\t%s\tShould have the right session for user.", tests.Failed) t.Log(u2.PublicID) t.Log(s2.PublicID) } t.Logf("\t%s\tShould have the right session for user.", tests.Success) webTok2, err := u2.WebToken(sId) if err != nil { t.Fatalf("\t%s\tShould be able to create a new web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a web new token.", tests.Success) if webTok != webTok2 { t.Log(webTok) t.Log(webTok2) t.Fatalf("\t%s\tShould be able to create the same web token.", tests.Failed) } t.Logf("\t%s\tShould be able to create the same web token.", tests.Success) u3, err := auth.ValidateWebToken(tests.Context, db, webTok2) if err != nil { t.Fatalf("\t%s\tShould be able to validate the new web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to validate the new web token.", tests.Success) if u1.PublicID != u3.PublicID { t.Log(u1.PublicID) t.Log(u3.PublicID) t.Fatalf("\t%s\tShould have the right user for the token.", tests.Failed) } t.Logf("\t%s\tShould have the right user for the token.", tests.Success) webTok3, err := auth.GetUserWebToken(tests.Context, db, u2.PublicID) if err != nil { t.Fatalf("\t%s\tShould be able to get the web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to get the web token.", tests.Success) if webTok3 != webTok2 { t.Log(webTok3) t.Log(webTok2) t.Fatalf("\t%s\tShould match existing tokens.", tests.Failed) } t.Logf("\t%s\tShould match existing tokens.", tests.Success) } } }
// TestInvalidWebTokenUpdateEmail tests a token becomes invalid after an update. func TestInvalidWebTokenUpdateEmail(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db := db.NewMGO() defer db.CloseMGO() var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to validate web tokens don't work after user update.") { t.Log("\tWhen using a new user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID webTok, err := auth.CreateWebToken(tests.Context, db, u1, 5*time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create a web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a web token.", tests.Success) if _, err := auth.ValidateWebToken(tests.Context, db, webTok); err != nil { t.Fatalf("\t%s\tShould be able to validate the web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to validate the web token.", tests.Success) uu := auth.UpdUser{ PublicID: publicID, Status: auth.StatusActive, FullName: "Update Kennedy", Email: "*****@*****.**", } if err := auth.UpdateUser(tests.Context, db, uu); err != nil { t.Fatalf("\t%s\tShould be able to update a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to update a user.", tests.Success) if _, err := auth.ValidateWebToken(tests.Context, db, webTok); err == nil { t.Fatalf("\t%s\tShould Not be able to validate the org web token.", tests.Failed) } t.Logf("\t%s\tShould Not be able to validate the org web token.", tests.Success) } } }
// TestCreateUserValidation tests the creation of a user that is not valid. func TestCreateUserValidation(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err == nil { t.Fatalf("\t%s\tShould Not be able to remove the test user", tests.Failed) } t.Logf("\t%s\tShould Not be able to remove the test user.", tests.Success) }() t.Log("Given the need to make sure only valid users are created in the DB.") { t.Log("\tWhen using a test user.") { u, _ := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) u.Status = 0 if err := auth.CreateUser(tests.Context, db, u); err == nil { t.Errorf("\t%s\tShould Not be able to create a user with invalid Status", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to create a user with invalid Status.", tests.Success) } u, _ = auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) u.FullName = "1234567" if err := auth.CreateUser(tests.Context, db, u); err == nil { t.Errorf("\t%s\tShould Not be able to create a user with invalid FullName", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to create a user with invalid FullName.", tests.Success) } u, _ = auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) u.Email = "bill" if err := auth.CreateUser(tests.Context, db, u); err == nil { t.Errorf("\t%s\tShould Not be able to create a user with invalid Email", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to create a user with invalid Email.", tests.Success) } u, _ = auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) u.Password = "******" if err := auth.CreateUser(tests.Context, db, u); err == nil { t.Errorf("\t%s\tShould Not be able to create a user with invalid Password", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to create a user with invalid Password.", tests.Success) } } } }
// TestUpdateUserValidation tests the update of a user that is not valid. func TestUpdateUserValidation(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err == nil { t.Fatalf("\t%s\tShould Not be able to remove the test user", tests.Failed) } t.Logf("\t%s\tShould Not be able to remove the test user.", tests.Success) }() t.Log("Given the need to make sure only valid users are created in the DB.") { t.Log("\tWhen using a test user.") { uu := auth.UpdUser{ PublicID: "asdasdasd", Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", } if err := auth.UpdateUser(tests.Context, db, uu); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with invalid PublicID", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with invalid PublicID.", tests.Success) } uu = auth.UpdUser{ PublicID: "6dcda2da-92c3-11e5-8994-feff819cdc9f", Status: 0, FullName: "Test Kennedy", Email: "*****@*****.**", } if err := auth.UpdateUser(tests.Context, db, uu); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with invalid Status", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with invalid Status.", tests.Success) } uu = auth.UpdUser{ PublicID: "6dcda2da-92c3-11e5-8994-feff819cdc9f", Status: auth.StatusActive, FullName: "1234567", Email: "*****@*****.**", } if err := auth.UpdateUser(tests.Context, db, uu); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with invalid FullName", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with invalid FullName.", tests.Success) } uu = auth.UpdUser{ PublicID: "6dcda2da-92c3-11e5-8994-feff819cdc9f", Status: auth.StatusActive, FullName: "Test Kennedy", Email: "ardanlabs.com", } if err := auth.UpdateUser(tests.Context, db, uu); err == nil { t.Errorf("\t%s\tShould Not be able to update a user with invalid Email", tests.Failed) } else { t.Logf("\t%s\tShould Not be able to update a user with invalid Email.", tests.Success) } uu = auth.UpdUser{ PublicID: "6dcda2da-92c3-11e5-8994-feff819cdc9f", Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", } } } }
// TestUpdateUserPassword tests we can update user password. func TestUpdateUserPassword(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to update a user.") { t.Log("\tWhen using an existing user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID webTok, err := auth.CreateWebToken(tests.Context, db, u1, 5*time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create a web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a web token.", tests.Success) if err := auth.UpdateUserPassword(tests.Context, db, u1, "_Password567"); err != nil { t.Fatalf("\t%s\tShould be able to update a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to update a user.", tests.Success) if _, err := auth.ValidateWebToken(tests.Context, db, webTok); err == nil { t.Fatalf("\t%s\tShould Not be able to validate the org web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould Not be able to validate the new org token.", tests.Success) u2, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by PublicID : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by PublicID.", tests.Success) webTok2, err := auth.CreateWebToken(tests.Context, db, u2, 5*time.Second) if err != nil { t.Fatalf("\t%s\tShould be able to create a new web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a new web token.", tests.Success) if webTok == webTok2 { t.Fatalf("\t%s\tShould have different web tokens after the update.", tests.Failed) } t.Logf("\t%s\tShould have different web tokens after the update.", tests.Success) u3, err := auth.ValidateWebToken(tests.Context, db, webTok2) if err != nil { t.Fatalf("\t%s\tShould be able to validate the new web token : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to validate the new web token.", tests.Success) if u1.PublicID != u3.PublicID { t.Log(u2.PublicID) t.Log(u3.PublicID) t.Fatalf("\t%s\tShould have the right user for the new token.", tests.Failed) } t.Logf("\t%s\tShould have the right user for the new token.", tests.Success) } } }
// TestCreateUser tests the creation of a user. func TestCreateUser(t *testing.T) { tests.ResetLog() defer tests.DisplayLog() db, err := db.NewMGO(tests.Context, tests.TestSession) if err != nil { t.Fatalf("\t%s\tShould be able to get a Mongo session : %v", tests.Failed, err) } defer db.CloseMGO(tests.Context) var publicID string defer func() { if err := removeUser(db, publicID); err != nil { t.Fatalf("\t%s\tShould be able to remove the test user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to remove the test user.", tests.Success) }() t.Log("Given the need to create users in the DB.") { t.Log("\tWhen using a test user.") { u1, err := auth.NewUser(auth.NUser{ Status: auth.StatusActive, FullName: "Test Kennedy", Email: "*****@*****.**", Password: "******", }) if err != nil { t.Fatalf("\t%s\tShould be able to build a new user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to build a new user.", tests.Success) if err := auth.CreateUser(tests.Context, db, u1); err != nil { t.Fatalf("\t%s\tShould be able to create a user : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to create a user.", tests.Success) // We need to do this so we can clean up after. publicID = u1.PublicID u2, err := auth.GetUserByPublicID(tests.Context, db, u1.PublicID, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by PublicID : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by PublicID.", tests.Success) // Remove the objectid to be able to compare the values. u2.ID = "" // Need to remove the nanoseconds to be able to compare the values. u1.DateModified = u1.DateModified.Add(-time.Duration(u1.DateModified.Nanosecond())) u1.DateCreated = u1.DateCreated.Add(-time.Duration(u1.DateCreated.Nanosecond())) u2.DateModified = u2.DateModified.Add(-time.Duration(u2.DateModified.Nanosecond())) u2.DateCreated = u2.DateCreated.Add(-time.Duration(u2.DateCreated.Nanosecond())) if !reflect.DeepEqual(*u1, *u2) { t.Logf("\t%+v", *u1) t.Logf("\t%+v", *u2) t.Fatalf("\t%s\tShould be able to get back the same user.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the same user.", tests.Success) } u3, err := auth.GetUserByEmail(tests.Context, db, u1.Email, true) if err != nil { t.Fatalf("\t%s\tShould be able to retrieve the user by Email : %v", tests.Failed, err) } t.Logf("\t%s\tShould be able to retrieve the user by Email.", tests.Success) // Remove the objectid to be able to compare the values. u3.ID = "" // Need to remove the nanoseconds to be able to compare the values. u3.DateModified = u3.DateModified.Add(-time.Duration(u3.DateModified.Nanosecond())) u3.DateCreated = u3.DateCreated.Add(-time.Duration(u3.DateCreated.Nanosecond())) if !reflect.DeepEqual(*u1, *u3) { t.Logf("\t%+v", *u1) t.Logf("\t%+v", *u3) t.Fatalf("\t%s\tShould be able to get back the same user.", tests.Failed) } else { t.Logf("\t%s\tShould be able to get back the same user.", tests.Success) } } } }