public void User_can_set_password()
 {
     var u = new User();
     u.SetPassword("asdf");
     Assert.That(u.PasswordHash.Length, Is.GreaterThan(0));
     Assert.That(u.PasswordSalt.Length, Is.GreaterThan(0));
 }
        public void User_sets_unique_password_hash_even_for_same_password()
        {
            var u1 = new User();
            var u2 = new User();

            u1.SetPassword("asdf");
            u2.SetPassword("asdf");

            Assert.That(User.CompareHash(u1.PasswordHash, u2.PasswordHash), Is.False);
        }
 public User CreateUser()
 {
     var u = new User
     {
         Login = Login,
         Email = Email,
         FirstName = FirstName,
         LastName = LastName,
         State = UserState.Registered,
         StateChanged = DateTime.UtcNow,
         DateRegistered = DateTime.UtcNow,
         Document = new Document { Id = Document.For<User>(Login.ToSlug()) }
     };
     u.State = Activate ? UserState.Active : UserState.Registered;
     u.SetPassword(Password);
     if (!Activate)
     {
         u.SetActivationCode();
     }
     return u;
 }
        public void Apply(User u, IAccountingService accounting)
        {
            if (!String.IsNullOrEmpty(Password))
            {
                u.SetPassword(Password);
            }
            u.Manager = Manager;
            u.Group = Group;
            u.ManagedGroups = ManagedGroups;
            u.State = State;
            u.DateBirth = DateBirth;
            u.DateHired = DateHired;
            u.Title = Title;
            u.EmployeeId = EmployeeId;
            u.Email = Email;
            u.FirstName = FirstName;
            u.LastName = LastName;
            u.HomeAddress = HomeAddress;
            u.WorkAddress = WorkAddress;
            u.HomePhone = HomePhone;
            u.WorkPhone = WorkPhone;
            u.MobilePhone = MobilePhone;
            u.Custom = Custom;
            u.Permissions = Permissions;

            accounting.SetUserBudget(u, null == Budget ? null : Budget.ToBudget());
        }   
        public void Apply(ProfileElements e, User u)
        {
            if (e.Email)
            {
                u.Email = Email;
            }
            if (e.Name)
            {
                u.FirstName = FirstName;
                u.LastName = LastName; 
            }
            if (e.DateOfBirth) 
            {
                u.DateBirth = DateBirth;
            }
            if (e.DateOfHire)
            {
                u.DateHired = DateHired;
            }
            if (e.HomeAddress)
            {
                u.HomeAddress = HomeAddress;
            }
            if (e.WorkAddress)
            { 
                u.WorkAddress = WorkAddress;
            }
            if (e.HomePhone)
            {
                u.HomePhone = HomePhone;
            }
            if (e.WorkPhone)
            {
                u.WorkPhone = WorkPhone;
            }
            if (e.MobilePhone)
            {
                u.MobilePhone = MobilePhone;
            }
            if (e.CustomFields)
            { 
                u.Custom = Custom;
            }
            if (e.Password &&
                !String.IsNullOrEmpty(Password) &&
                !String.IsNullOrEmpty(PasswordConfirmation) &&
                Password == PasswordConfirmation)
            {
                u.SetPassword(Password);
            }

            u.LastUpdatedProfile = DateTime.UtcNow;
        }
        public virtual ActionResult Randomizer(RandomizerModel model)
        {
            // keep all the users in a local structure
            var r = new Random();
            var all = new Dictionary<string, User>();
            var execs = new List<User>();
            var managers = new List<User>();
            var groups = Groups.All().WithDocuments().ToList();

            // load up all the quizes and awards that we could do
            var quizzes = Quizzes.All().WithDocuments();
			// var awards = Awards.All().WithDocuments();

            // load up a random slice of about 10% of all products
            var products =
                Catalog.GetCategories(Application.DefaultCatalog)
                       .Products
                       .Where(x => r.NextDouble() < 0.10)
                       .ToArray();
            var averageprice = (int)products.Average(x => x.Price);

            var start = (model.From ?? DateTime.Now.AddYears(-1));
            var end = (model.To ?? DateTime.Now);
            var days = (int)(end-start).TotalDays;

            var dobstart = new DateTime(1955, 1, 1);
            const int dobdays = 365*35;

            for (var n=all.Count; n<model.Users; n++)
            {
                // create basic user properties
                var first = Firstnames[(int)(Math.Pow(r.NextDouble(), r.NextDouble()) * Firstnames.Length)];
                var last = Lastnames[(int)(Math.Pow(r.NextDouble(), r.NextDouble()) * Lastnames.Length)];
                var login = (first[0] + last).ToSlug();
                var u = new User {
                  Document = new Document { Id = Document.For<User>(login) },
                  Login = login,
                  FirstName = first,
                  LastName = last,
                  Email = String.Format("{0}.{1}@{2}", first.ToSlug(), last.ToSlug(), model.EmailDomain),
                  State = UserState.Active,
                  DateBirth = dobstart.AddDays(r.Next(1, dobdays)),
                  DateHired = end.AddDays(-1 * r.Next(1, 3000)),
                  DateActivated = start.AddDays(r.Next(0, days)),
                };
                u.SetPassword("asdf");

                // place into group/management hierarchy.. execs in charge of a group, with
                // several managers in each group with employers reporting to them.
                if (groups.Count > 2)
                {
                    if (execs.Count < groups.Count)
                    {
                        // there's 1 exec for each group
                        var g = groups[execs.Count];
                        u.Group = g.Document.Id;
                        u.ManagedGroups = new[] { u.Group };
                        u.Title = "VP of " + g.Name;
                        execs.Add(u);

                        // execs get a large budget
                        Accounting.GetBudgetLedger(u, true,
                            new Budget {
                                RefreshLimit = 3000,
                                RefreshInterval = BudgetRefreshInterval.Monthly,
                            });
                    }
                    else if (managers.Count < 3 * groups.Count)
                    {
                        // there are a few managers in each group        
                        u.Group = groups[r.Next(0, groups.Count - 1)].Document.Id;
                        u.Manager = execs.Where(x => x.Group == u.Group).First().Document.Id;
                        u.Title = "Supervisor";
                        managers.Add(u);

                        // managers get a modest budget
                        Accounting.GetBudgetLedger(u, true,
                            new Budget {
                                RefreshLimit = r.NextDouble() < 0.50 ? 1500 : 2000,
                                RefreshInterval = BudgetRefreshInterval.Monthly,
                            });                    
                    }
                    else
                    {
                        // assign the user to a random manager (and place in his group)
                        var m = managers[r.Next(0, managers.Count-1)];
                        u.Manager = m.Document.Id;
                        u.Group = m.Group;
                    }
                }
                
                try
                {
                    Users.Save(u);
                    all.Add(u.Document.Id, u);
                }
                catch
                {
                }
            }

            // refresh budgets every day
            for (var n=0; n<days; n++)
            {
                Accounting.RefreshBudgets(start.AddDays(days));
            }

            foreach (var u in all.Values)
            {
                // some users just don't do anything
                var active = r.NextDouble() < 0.95;
                if (active)
                {
                    // avg number of days between logins
                    var frequency = r.Next(7, 60);     
                    var d = start;
                    while (true)
                    {
                        // users are fairly predictable, within about 25% tolerance on either side
                        d = d.AddDays(r.Next(
                            (int)(frequency - (frequency * 0.25)),
                            (int)(frequency + (frequency * 0.25))
                        ));
                        if (d > end) break;

                        // lets meet the bobs
                        if (r.NextDouble() < 0.05)
                        {
                            u.State = UserState.Terminated;
                            u.DateTerminated = d;
                            u.StateChanged = d; 
                            break;
                        }

                        // usually they log in because they got some points
                        var ledger = Accounting.GetPointsLedger(u);
                        if (r.NextDouble() < 0.60)
                        {
                            Accounting.CreateTransaction(
                                Application.GeneralControlAccount,
                                ledger.Account.Document.Id,
                                r.Next(averageprice/10, averageprice/2),
                                "Congrulations on your sale!",
                                "Sales",
                                d.AddHours(-1 * r.Next(2, 72)),
                                null);
                        }

                        // sometimes we forget our password
                        if (r.NextDouble() < 0.05)
                        {
                            u.IncrementLogins(false, Request, d);

                            // and we try again
                            if (r.NextDouble() < 0.75)
                            {
                                d = d.AddMinutes(1);
                                u.IncrementLogins(false, Request, d);
                            }
                           
                            // and again
                            if (r.NextDouble() < 0.75)
                            {
                                d = d.AddMinutes(1);
                                u.IncrementLogins(false, Request, d);
                            }

                            // and again, and /again/
                            // the time for honoring yourself will soon be over

                            // but then we usually reset it and get logged in
                            if (r.NextDouble() < 0.80)
                            {
                                d = d.AddMinutes(5);
                            }
                            else
                            {
                                break;
                            }
                        }
                        
                        // login!
                        u.IncrementLogins(true, Request, d);

                        // if this is their first login, make sure they accept the terms of service
                        if (!u.DateAcceptedTermsOfService.HasValue)
                        {
                            u.DateAcceptedTermsOfService = d;
                        }

                        // try taking a quiz!
                        if (r.NextDouble() < 0.20)
                        {
                            foreach (var q in quizzes)
                            {
                                if (q.CanUserTakeQuiz(u, d, QuizResults.GetResults(q, u)).Available)
                                {
                                    // most quizzes are easy
                                    var qr = q.Score(
                                        u, 
                                        q.Questions.Select(x => {
                                            var correct = (r.NextDouble() < 0.95);
                                            return x.Answers.IndexOf(x.Answers.First(y => y.Correct == correct));
                                        }).ToArray()
                                    );
                                    qr.Taken = d.AddMinutes(5);
                                    if (qr.Passed && qr.PointsEarned.HasValue && qr.PointsEarned > 0)
                                    {
                                        var tx = Accounting.CreateProgramAward(q, null, u, qr.PointsEarned.Value, q.Content.Title);
                                        qr.Transaction = tx.Document.Id;
                                    }
                                    QuizResults.Save(qr);
                                    break;
                                }
                            }
                        }

                        // send an award
                        if (r.NextDouble() < 0.10)
                        {
                        }

                        // if we have at least enough points to buy something 'average', try to place an order
                        if (ledger.Balance > averageprice)
                        {
                            var cart = new List<CatalogProduct>();
                            while (true)
                            {
                                var p = products[r.Next(0, products.Length-1)];
                                if (cart.Sum(x => x.Price) + p.Price < ledger.Balance)
                                {
                                    cart.Add(p);
                                }
                                else
                                {
                                    break;
                                }
                            }
                            if (cart.Count > 0)
                            {
                                var o = new Order
                                {   
                                    User = u.Document.Id,
                                    State = OrderStateMachine.Create(),
                                    ShippingName = u.DisplayName,
                                    ShippingAddress = new Address { Address1 = "123 Main St.", City = "Minneapolis", State = "MN", PostalCode = "55456" },
                                    ShippingPhone = new Phone { Number = "(952)555-7834" },
                                    Items = cart.Select(x => new OrderItem
                                    {
                                        ProductId = x.Id,
                                        ProductName = x.Name,
                                        OptionName = x.Options[0].Name,
                                        OptionSku =  x.Options[1].Sku,
                                        Description = x.Description,
                                        UnitPrice = x.Price,
                                        Quantity = 1,
                                        Stock = x.Stock,
                                        State = OrderItemStateMachine.Create(),
                                    }).ToArray(),
                                };
                                o.State[0].Changed = d.AddMinutes(15);
                                var tx = Accounting.CreateOrderPayment(u, o);
                                o.Transaction = tx.Document.Id;
                                Orders.Save(o);
                            }
                        }

                        // distribute budget
                        var budgetLedger = Accounting.GetBudgetLedger(u);
                        if (null != budgetLedger &&
                            null != budgetLedger.Account &&
                            null != budgetLedger.Account.Budget &&
                            r.NextDouble() < 0.50)
                        {
                            var budgetBalance = budgetLedger.Balance;
                            if (budgetBalance > budgetLedger.Account.Budget.RefreshLimit.Value * 0.15)
                            {
                                // pick a random user that reports to us
                                var reports = all.Values.Where(x => x.Manager == u.Document.Id).ToList();
                                if (reports.Count > 0)
                                {
                                    var awardee = reports[r.Next(0, reports.Count-1)];
                                    Accounting.CreateBudgetTransfer(
                                        u,
                                        awardee,
                                        r.Next((int)(budgetBalance * 0.10), (int)(budgetBalance * 0.85)),
                                        "Budget Award");
                                }
                            }
                        }

                    }
                }
                Users.Save(u);
            }
            
            Notifier.Notify(Severity.Success, "Randomized!", "Random activity succesfully created. You may want to compact the database.", null);
            return this.RedirectToAction<UserController>(c => c.Index());
        }
 public void User_password_is_case_sensitive()
 {
     var u = new User();
     u.SetPassword("asdf");
     Assert.That(u.CheckPassword("asdF"), Is.False);
 }
 public void User_can_check_password()
 {
     var u = new User();
     u.SetPassword("asdf");
     Assert.That(u.CheckPassword("asdf"), Is.True);
 }