Пример #1
0
        //[Authenticate(Forms, "/login/")] // Basic, Digest, Oauth, Api
        public override ViewBase Post(ControllerContext context)
        {
            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }
            else if (!UserService.TryAuthorizeUser(user, UserRole.Admin))
            {
                return new StatusCodeView(HttpStatusCode.Forbidden);
            }

            var config = new Config();
            var updates = config.PopulateWithData(context.Form);

            using (var db = DataService.Connect())
            using (var tx = db.OpenTransaction())
            {
                db.Insert(config);

                ConfigService.InitializeWithConfig(config);
                FileService.PregenerateApp();

                tx.Commit();
            }

            return new JsonView(new AppViewModel());
        }
Пример #2
0
        private ViewBase SendToken(ControllerContext context, ResendAction action, string nameOrEmail)
        {
            // If the name or email could not be found, pretend everything is okay.
            User user;
            if (!QueryService.TryGetUser(nameOrEmail, out user))
            {
                return null;
            }

            // Generate a verification token.
            user.VerifyToken = UserService.GenerateVerifyToken();

            using (var db = DataService.Connect())
            using (var tx = db.OpenTransaction())
            {
                db.UpdateOnly(user, u => u.VerifyToken, u => u.Guid == user.Guid);
                if (ResendAction.Activate == action)
                {
                    MailService.SendVerifyUser(user.Email, user.VerifyToken);
                }
                else
                {
                    MailService.SendPasswordReset(user.Email, user.VerifyToken);
                }

                tx.Commit();
            }

            return new StatusCodeView(HttpStatusCode.Created);
        }
Пример #3
0
        public override ViewBase Get(ControllerContext context)
        {
            string username;
            if (!this.TryGetUserNameFromContext(context, out username))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            User me;
            if (!UserService.TryAuthenticateUser(context.User, out me))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }

            if (username.Equals("0"))
            {
                username = "******";
            }

            User user;
            if (!QueryService.TryGetUserByName(me.Guid, username, out user))
            {
                return new StatusCodeView(HttpStatusCode.NotFound);
            }

            return new JsonView(new UserViewModel(user));
        }
Пример #4
0
        public override ViewBase Post(ControllerContext context)
        {
            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }
            else if (!UserService.TryAuthorizeUser(user, UserRole.Admin))
            {
                return new StatusCodeView(HttpStatusCode.Forbidden);
            }

            using (var db = DataService.Connect(true))
            {
                FileService.PregenerateApp();

                var issuesIds = db.SqlList<long>("SELECT Id FROM Issue");
                foreach (var issueId in issuesIds)
                {
                    IssueViewModel vm;
                    if (QueryService.TryGetIssueWithCommentsUsingDb(issueId, db, out vm))
                    {
                        vm.Location = context.ApplicationPath + vm.Id + "/";
                        var breadcrumbs = new BreadcrumbsViewModel(new Breadcrumb("Issues", context.ApplicationPath), new Breadcrumb("#" + vm.Id + " - " + vm.Title, vm.Location));

                        FileService.WriteIssue(vm, breadcrumbs);
                    }
                }
            }

            return null;
        }
Пример #5
0
        public override ViewBase Post(ControllerContext context)
        {
            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }
            else if (!UserService.TryAuthorizeUser(user, UserRole.User))
            {
                return new StatusCodeView(HttpStatusCode.Forbidden);
            }

            Issue issue = new Issue();

            PopulateResults results = issue.PopulateWithData(context.UnvalidatedForm, user.Guid, true);
            if (results.Errors.Count > 0)
            {
                return new JsonView(results.Errors, HttpStatusCode.BadRequest);
            }

            issue.Status = IssueStatus.Untriaged;
            issue.CreatedAt = issue.UpdatedAt;
            issue.CreatedByUserId = user.Id;

            IssueViewModel vm = SaveIssue(context, issue);
            if (vm == null)
            {
                return new StatusCodeView(HttpStatusCode.InternalServerError);
            }

            return new JsonView(vm, HttpStatusCode.Created);
        }
Пример #6
0
        public override ViewBase Delete(ControllerContext context)
        {
            long issueId;
            if (!this.TryGetIssueIdFromContext(context, out issueId))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }

            Issue issue;
            using (var db = DataService.Connect(true))
            {
                issue = db.GetByIdOrDefault<Issue>(issueId);
                if (issue == null)
                {
                    return new StatusCodeView(HttpStatusCode.NotFound);
                }
            }

            if (user.Id != issue.CreatedByUserId &&
                !user.IsInRole(UserRole.Contributor))
            {
                return new StatusCodeView(HttpStatusCode.Forbidden);
            }

            this.DeleteIssue(issue.Id);
            return null;
        }
Пример #7
0
        public IssueViewModel SaveIssue(ControllerContext context, Issue issue)
        {
            IssueViewModel vm = null;
            using (var db = DataService.Connect())
            using (var tx = db.BeginTransaction())
            {
                db.Insert(issue);
                issue.Id = db.GetLastInsertId();

                var issueSearch = new FullTextSearchIssue()
                {
                    DocId = issue.Id,
                    Text = issue.Text,
                    Title = issue.Title,
                };
                db.InsertParam(issueSearch);

                if (QueryService.TryGetIssueWithCommentsUsingDb(issue.Id, db, out vm))
                {
                    vm.Location = context.ApplicationPath + vm.Id + "/";
                    var breadcrumbs = new BreadcrumbsViewModel(new Breadcrumb("Issues", context.ApplicationPath), new Breadcrumb("#" + vm.Id + " - " + vm.Title, vm.Location));

                    FileService.WriteIssue(vm, breadcrumbs);
                    tx.Commit();
                }
            }

            return vm;
        }
Пример #8
0
        public override ViewBase Get(ControllerContext context)
        {
            Query q = QueryService.ParseQuery(context.QueryString);

            User user;
            if (q.Filters != null &&
                q.Filters.Any(f => f.Column.Equals("user", StringComparison.OrdinalIgnoreCase)) &&
                !UserService.TryAuthenticateUser(context.User, out user))
            {
                FormsAuthentication.RedirectToLoginPage(QueryService.RecreateQueryString(q));
                return null;
            }

            var issuesPaged = QueryService.QueryIssues(context.User, q);
            var pagePrefix = context.ControllerPath + QueryService.RecreateQueryString(q) + "&page=";

            RootViewModel vm = new RootViewModel()
            {
                Breadcrumbs = new BreadcrumbsViewModel(new Breadcrumb("Issues", context.ControllerPath)),
                Issues = issuesPaged.Issues,
                Page = new PaginationViewModel(q.Page, q.Count, issuesPaged.Total, pagePrefix),
            };

            string path = q.Template ?? "search.mustache";
            return new TemplateView(path, vm);
        }
Пример #9
0
        public override ViewBase Get(ControllerContext context)
        {
            long issueId;
            if (!Int64.TryParse(context.RouteData.Values["issue"] as string, out issueId))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.Unauthorized);
            }

            IssueViewModel issue;
            if (!QueryService.TryGetIssueWithComments(issueId, out issue))
            {
                return new StatusCodeView(HttpStatusCode.NotFound);
            }

            if (!user.Email.Equals(issue.AssignedToUserEmail) &&
                !user.Email.Equals(issue.CreatedByUserEmail) &&
                !user.IsInRole(UserRole.Contributor))
            {
                return new RedirectView("~/accessdenied/");
            }

            return new TemplateView("bugform.mustache", new { app = new AppViewModel(), issue = issue });
        }
Пример #10
0
 public override ViewBase Get(ControllerContext context)
 {
     string query = context.QueryString["q"] ?? String.Empty;
     using (var db = DataService.Connect(true))
     {
         var usernames = db.Select<User>(ev => ev.Select(u => u.UserName).Where(u => u.UserName.Contains(query))).Select(u => u.UserName);
         return new JsonView(usernames);
     }
 }
Пример #11
0
        public override ViewBase Get(ControllerContext context)
        {
            string token = context.RouteData.Values["token"] as string;
            if (String.IsNullOrEmpty(token))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            return VerifyToken(context, token);
        }
Пример #12
0
        public override ViewBase Get(ControllerContext context)
        {
            User me;
            if (!UserService.TryAuthenticateUser(context.User, out me))
            {
                return new StatusCodeView(HttpStatusCode.Unauthorized);
            }

            return new TemplateView("userform.mustache", new { app = new AppViewModel(), user = new UserViewModel(me), });
        }
Пример #13
0
        public override ViewBase Get(ControllerContext context)
        {
            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.Unauthorized);
            }

            if (!user.IsInRole(UserRole.Admin))
            {
                return new RedirectView("~/accessdenied/");
            }

            return new TemplateView("admin.mustache", new { app = new AppViewModel(), breadcrumbs = ConfigService.ExternalBreadcrumbs, mail = ConfigService.Mail });
        }
Пример #14
0
        public override ViewBase Get(ControllerContext context)
        {
            Query q = QueryService.ParseQuery(context.QueryString);
            QueriedIssuesViewModel issues = QueryService.QueryIssues(context.User, q);
            issues.Issues.ForEach(i => i.Location = context.ApplicationPath + i.Id + "/"); // TODO: come up with a better way of handling this.
            var pagePrefix = context.ControllerPath + QueryService.RecreateQueryString(q) + "&page=";

            IssuesApiViewModel vm = new IssuesApiViewModel()
            {
                Issues = issues.Issues,
                Page = new PaginationViewModel(q.Page, q.Count, issues.Total, pagePrefix),
            };

            return new JsonView(vm);
        }
Пример #15
0
        public override ViewBase Post(ControllerContext context)
        {
            string fullname = context.Form["fullname"];
            string email = context.Form["email"];
            string password = context.Form["password"];
            string verifyPassword = context.Form["verifypassword"];
            string username = context.Form["username"];

            var errors = VerifyData(email, password, verifyPassword, username);
            if (errors.Length > 0)
            {
                return new JsonView(errors, HttpStatusCode.BadRequest);
            }

            // Default username to email.
            if (String.IsNullOrEmpty(username))
            {
                username = email;
            }

            User user = UserService.Create(email, password, username);
            user.FullName = String.IsNullOrEmpty(fullname) ? null : fullname;
            user.VerifyToken = UserService.GenerateVerifyToken();

            using (var db = DataService.Connect())
            using (var tx = db.OpenTransaction())
            {
                db.Insert(user);
                user.Id = db.GetLastInsertId();

                // First user magically becomes an admin.
                if (user.Id == 1)
                {
                    user.Role = UserRole.Admin;
                    user.VerifyToken = null;
                    db.Update(user);
                }
                else
                {
                    MailService.SendVerifyUser(user.Email, user.VerifyToken);
                }

                tx.Commit();
            }

            return new JsonView(new UserViewModel(user), HttpStatusCode.Created);
        }
Пример #16
0
        public override ViewBase Post(ControllerContext context)
        {
            string token = context.RouteData.Values["token"] as string;
            if (String.IsNullOrEmpty(token))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            string password = context.Form["password"] ?? String.Empty;
            string confirm = context.Form["verifypassword"];
            if (String.IsNullOrEmpty(password) && password.Equals(confirm))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            return VerifyToken(context, token, password);
        }
Пример #17
0
        public override ViewBase Get(ControllerContext context)
        {
            long issueId;
            if (!this.TryGetIssueIdFromContext(context, out issueId))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            IssueViewModel issue;
            if (!QueryService.TryGetIssueWithComments(issueId, out issue))
            {
                return new StatusCodeView(HttpStatusCode.NotFound);
            }

            issue.Location = context.ApplicationPath + issue.Id + "/";
            return new JsonView(issue);
        }
Пример #18
0
        public override ViewBase Post(ControllerContext context)
        {
            ResendAction action;
            string actionData = context.RouteData.Values["action"] as string;
            if (!Enum.TryParse<ResendAction>(actionData, true, out action))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            string email = context.Form["email"];
            if (String.IsNullOrEmpty(email))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            return SendToken(context, action, email);
        }
Пример #19
0
        public override ViewBase Put(ControllerContext context)
        {
            string username;
            if (!this.TryGetUserNameFromContext(context, out username))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }
            else if (username.Equals("0"))
            {
                username = "******";
            }

            User me;
            if (!UserService.TryAuthenticateUser(context.User, out me))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }

            User user;
            if (!QueryService.TryGetUserByName(context.User, username, out user))
            {
                return new StatusCodeView(HttpStatusCode.NotFound);
            }

            var results = user.PopulateWithData(context.Form, me);
            if (results.Errors.Count == 0)
            {
                using (var db = DataService.Connect())
                using (var tx = db.BeginTransaction())
                {
                    db.UpdateOnly(user, v => v.Update(results.Updates.Keys.ToArray()).Where(u => u.Id == user.Id));

                    if (results.Updates.Any(u => u.Key.Equals("VerifyToken")))
                    {
                        MailService.SendVerifyUser(user.Email, user.VerifyToken);
                    }

                    tx.Commit();
                }
            }

            return new JsonView(new { user = new UserViewModel(user), errors = results.Errors },
                                results.Errors.Count == 0 ? HttpStatusCode.OK : HttpStatusCode.BadRequest);
        }
Пример #20
0
        public override ViewBase Get(ControllerContext context)
        {
            User me;
            if (!UserService.TryAuthenticateUser(context.User, out me))
            {
                return new StatusCodeView(HttpStatusCode.Unauthorized);
            }

            User user;
            long id;
            string idString = context.RouteData.Values["id"] as string;
            if (String.IsNullOrEmpty(idString))
            {
                user = me;
            }
            else if (!UserService.TryAuthorizeUser(me, UserRole.User))
            {
                return new StatusCodeView(HttpStatusCode.Unauthorized);
            }
            else if (!Int64.TryParse(idString, out id))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }
            else
            {
                using (var db = DataService.Connect(true))
                {
                    user = db.GetByIdOrDefault<User>(id);
                    if (user == null)
                    {
                        return new StatusCodeView(HttpStatusCode.NotFound);
                    }
                }
            }

            return new TemplateView("user.mustache", new
            {
                app = new AppViewModel(),
                breadcrumbs = ConfigService.ExternalBreadcrumbs,
                user = new UserViewModel(user),
                me = new UserViewModel(me)
            });
        }
Пример #21
0
        public override ViewBase Get(ControllerContext context)
        {
            var query = context.QueryString;
            HttpStatusCode statusCode = HttpStatusCode.NotFound;
            string referrer = context.Referrer != null ? context.Referrer.AbsoluteUri : String.Empty;

            if (query.Count > 0)
            {
                string[] s = query.Get(0).Split(new char[] { ';' });
                statusCode = (HttpStatusCode)Convert.ToInt32(s[0]);
                if (String.IsNullOrEmpty(referrer) && s.Length > 1)
                {
                    referrer = s[1];
                }
            }

            Log.InfoFormat("url: {0}  referrer: {1}", context.Url.AbsoluteUri, referrer);

            return new TemplateView("notfound.mustache", new { ReferralUri = referrer, StatusCode = statusCode }, statusCode);
        }
Пример #22
0
        public ViewBase VerifyToken(ControllerContext context, string token, string password = null)
        {
            if (!token.StartsWith("t"))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            token = token.Substring(1); // remove the expected "t" from the beginning of the token.

            DateTime issued;
            if (!UserService.TryValidateVerificationToken(token, out issued))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            using (var db = DataService.Connect())
            {
                User user = db.FirstOrDefault<User>(u => u.VerifyToken == token);
                if (user == null)
                {
                    return new StatusCodeView(HttpStatusCode.NotFound);
                }

                string passwordHash = user.PasswordHash;
                if (!String.IsNullOrEmpty(password))
                {
                    passwordHash = UserService.CalculatePasswordHash(user.Guid, user.Salt, password);
                }

                // Verification tokens are one shot deals. This one is dead now.
                // Also, ensure the user is verifed now.
                UserRole role = (user.Role == UserRole.Unverfied) ? UserRole.User : user.Role;
                db.UpdateOnly(new User { VerifyToken = null, Role = role, PasswordHash = passwordHash },
                    u => new { u.VerifyToken, u.Role, u.PasswordHash },
                    u => u.Guid == user.Guid);
            }

            return null;
        }
Пример #23
0
 public override ViewBase Get(ControllerContext context)
 {
     context.GetOutput().Write("<html><head><title>Everything</title></head><body><h1>Everything</h1></body></html>");
     return null;
 }
Пример #24
0
        public override ViewBase Put(ControllerContext context)
        {
            long issueId;
            if (!this.TryGetIssueIdFromContext(context, out issueId))
            {
                return new StatusCodeView(HttpStatusCode.BadRequest);
            }

            User user;
            if (!UserService.TryAuthenticateUser(context.User, out user))
            {
                return new StatusCodeView(HttpStatusCode.BadGateway); // TODO: return a better error code that doesn't cause forms authentication to overwrite our response
            }

            Issue issue;
            using (var db = DataService.Connect(true))
            {
                issue = db.GetByIdOrDefault<Issue>(issueId);
                if (issue == null)
                {
                    return new StatusCodeView(HttpStatusCode.NotFound);
                }
            }

            if (!user.IsInRole(UserRole.User))
            {
                return new StatusCodeView(HttpStatusCode.Forbidden);
            }

            bool unassigned = (issue.AssignedToUserId == 0);
            bool owner = (user.Id == issue.AssignedToUserId || user.Id == issue.CreatedByUserId);
            bool contributor =  user.IsInRole(UserRole.Contributor);

            PopulateResults results = issue.PopulateWithData(context.UnvalidatedForm, user.Guid);
            if (results.Errors.Count > 0)
            {
                return new JsonView(results.Errors, HttpStatusCode.BadRequest);
            }

            // Only a few fields can be updated by normal users.
            if (!owner && !contributor)
            {
                // AssignedTo may be changed if the issue isn't assigned to anyone. Status can be
                // changed but if it is changed we'll check it further next. Remove anything else.
                var disallowed = results.Updates.Keys.Where(s => !((unassigned && s == "AssignedToUserId") || s == "Status" || s == "UpdatedAt")).ToList();
                foreach (var remove in disallowed)
                {
                    results.Updates.Remove(remove);
                }

                // If status is being changed, ensure it's being set to untriaged.
                PopulateResults.UpdatedValue statusChange;
                if (results.Updates.TryGetValue("Status", out statusChange) &&
                    (IssueStatus)statusChange.New != IssueStatus.Untriaged)
                {
                    results.Updates.Remove("Status");
                }
            }

            string comment = context.UnvalidatedForm.Get("comment");

            IssueViewModel vm = UpdateIssue(context, issue, user.Id, comment, results.Updates);
            if (vm == null)
            {
                return new StatusCodeView(HttpStatusCode.InternalServerError);
            }

            return new JsonView(vm);
        }
Пример #25
0
        public IssueViewModel UpdateIssue(ControllerContext context, Issue issue, long userId, string commentText, Dictionary<string, PopulateResults.UpdatedValue> updates)
        {
            IssueViewModel vm = null;

            IssueComment comment = new IssueComment();
            comment.IssueId = issue.Id;
            comment.CommentByUserId = userId;
            comment.CreatedAt = issue.UpdatedAt;
            comment.Text = commentText;
            foreach (var kvp in updates)
            {
                if (kvp.Key.Equals("UpdatedAt", StringComparison.OrdinalIgnoreCase))
                {
                    continue;
                }

                object oldValue = kvp.Value.FriendlyOld ?? kvp.Value.Old ?? String.Empty;
                object newValue = kvp.Value.FriendlyNew ?? kvp.Value.New ?? String.Empty;

                IssueChange change = new IssueChange();
                change.Column = kvp.Value.FriendlyName ?? kvp.Key;
                change.Old = oldValue.ToString();
                change.New = newValue.ToString();
                comment.Changes.Add(change);
            }

            comment.Changes.Sort();

            using (var db = DataService.Connect())
            using (var tx = db.BeginTransaction())
            {
                // If there is some sort of recognizable change.
                if (!String.IsNullOrEmpty(comment.Text) || comment.Changes.Count > 0)
                {
                    db.UpdateOnly(issue, v => v.Update(updates.Keys.ToArray()).Where(i => i.Id == issue.Id));

                    if (updates.ContainsKey("Text") || updates.ContainsKey("Title"))
                    {
                        db.Update<FullTextSearchIssue>(new { Text = issue.Text, Title = issue.Title }, s => s.DocId == issue.Id);
                    }

                    db.Insert(comment);
                    comment.Id = db.GetLastInsertId();
                }

                if (QueryService.TryGetIssueWithCommentsUsingDb(issue.Id, db, out vm))
                {
                    vm.Location = context.ApplicationPath + vm.Id + "/";
                    var breadcrumbs = new BreadcrumbsViewModel(new Breadcrumb("Issues", context.ApplicationPath), new Breadcrumb("#" + vm.Id + " - " + vm.Title, vm.Location));

                    FileService.WriteIssue(vm, breadcrumbs);
                    tx.Commit();

                    // best effort email about changes to issue.
                    try
                    {
                        MailService.SendIssueComment(vm, comment.Id);
                    }
                    catch (Exception e)
                    {
                        LogManager.GetLogger("error").Error(String.Format("  failed to send update about issue #{0}, comment #{1}", issue.Id, comment.Id), e);
                    }
                }
            }

            return vm;
        }
Пример #26
0
 public bool TryGetUserNameFromContext(ControllerContext context, out string username)
 {
     username = context.RouteData.Values["username"] as string;
     return username != null;
 }
Пример #27
0
 public override ViewBase Get(ControllerContext context)
 {
     return new StatusCodeView(HttpStatusCode.NotImplemented);
 }
Пример #28
0
 public override ViewBase Post(ControllerContext context)
 {
     // Forward POST to PUT for those clients that only use POST.
     return this.Put(context);
 }
Пример #29
0
 public bool TryGetIssueIdFromContext(ControllerContext context, out long issueId)
 {
     string value = context.RouteData.Values["issue"] as string;
     return Int64.TryParse(value, out issueId);
 }
Пример #30
0
 public override ViewBase Get(ControllerContext context)
 {
     return new JsonView(new AppViewModel());
 }