private PostViewModel GeneratePostViewModel(int forumID, int threadID, EditorType editorType, int? quotePostID = null, int? postID = null)
        {
            var postEditor = GeneratePostEditorViewModel(threadID, EditorType.Create);

            if (editorType == EditorType.Create)
            {
                if (quotePostID.HasValue)
                {
                    Post quotePost = _postServices.GetPost(quotePostID.Value);
                    string quoteText = string.Format("[quote={0}]{1}[/quote]{2}", quotePost.User.Username, quotePost.Text, Environment.NewLine);
                    postEditor.Message = quoteText + postEditor.Message;
                }
            }
            else
            {
                Post post = _postServices.GetPost(postID.Value);
                postEditor.Message = post.Text;
                postEditor.PostID = post.PostID;
            }

            var model = new PostViewModel()
            {
                EditorType = editorType,
                PostEditor = postEditor,
                ThreadID = threadID,
                CanUploadAttachments = _permissionServices.CanCreateAttachment(forumID, _currentUser.UserID),
                Thread = _threadServices.GetThread(threadID)
            };

            if (TempData.ContainsKey("Preview_Text"))
            {
                string text = (string)TempData["Preview_Text"];
                model.PreviewText = _parseServices.ParseBBCodeText(text);
                model.Preview = true;
            }

            return model;
        }
        public ActionResult PostValidate(PostViewModel model)
        {
            EditorType editorType;
            if (model.PostEditor.PostID == 0)
                editorType = EditorType.Create;
            else
                editorType = EditorType.Edit;

            var thread = _threadServices.GetThread(model.ThreadID);
            var forum = thread.Forum;

            if (editorType == EditorType.Create)
            {
                if (!_permissionServices.CanReply(forum.ForumID, _currentUser.UserID))
                {
                    if (thread.IsLocked)
                    {
                        SetNotice("You can't reply to this thread because it is locked");
                        return RedirectToAction("ViewThread", "Board", new { ThreadID = thread.ThreadID });
                    }
                    else
                    {
                        SetNotice("You don't have permission to reply in this forum");
                        return RedirectToAction("ViewForum", "Board", new { ForumID = forum.ForumID });
                    }
                }
            }
            else
            {
                if (!_postServices.CanEditPost(model.PostEditor.PostID, _currentUser.UserID))
                {
                    SetError("You can't edit this post");
                    return RedirectToAction("ViewThread", "Board", new { ThreadID = thread.ThreadID });
                }
            }

            HttpPostedFileBase[] files = null;
            if (_permissionServices.CanCreateAttachment(forum.ForumID, _currentUser.UserID))
            {
                if (model.PostEditor.Files != null)
                {
                    ValidatePostedFiles(model.PostEditor.Files);
                    files = model.PostEditor.Files.Where(item => item != null && item.ContentLength > 0 && !string.IsNullOrWhiteSpace(item.FileName)).ToArray();
                }
            }
            else
                model.PostEditor.Files = null;

            if (IsModelValidAndPersistErrors() && !model.Preview.HasValue)
            {
                if (editorType == EditorType.Create)
                {
                    if (_threadServices.IsSubscribed(thread.ThreadID, _currentUser.UserID) && model.PostEditor.SubscribeToThread)
                        _threadServices.Subscribe(thread.ThreadID, _currentUser.UserID);

                    var post = _postServices.CreatePost(model.ThreadID, _currentUser.UserID, model.PostEditor.Message, model.PostEditor.ShowSignature, files);
                    string postUrl = Url.Action("ViewThread", "Board", new { ThreadID = post.ThreadID, PostID = post.PostID }) + "#" + post.PostID;
                    IEnumerable<Subscription> subscriptions = thread.Subscriptions;
                    _emailServices.NewPostEmail(subscriptions, post, post.Thread, postUrl);

                    SetSuccess("Your reply was posted");
                    return Redirect(Url.Action("ViewThread", "Board", new { ThreadID = model.ThreadID, LastPost = true, NewPost = true }) + "#" + post.PostID);
                }
                else
                {
                    if (model.PostEditor.Delete != null)
                        _fileServices.DeleteAttachments(model.PostEditor.Delete);

                    _postServices.UpdatePost(model.PostEditor.PostID, model.PostEditor.Message, files);
                    SetSuccess("Post edited");
                    return Redirect(Url.Action("ViewThread", "Board", new { ThreadID = thread.ThreadID, LastPost = true, PostID = model.PostEditor.PostID }) + "#" + model.PostEditor.PostID);
                }
            }

            if (model.Preview.HasValue)
            {
                TempData["Preview_Text"] = model.PostEditor.Message;
            }

            if (editorType == EditorType.Create)
                return RedirectToAction("CreatePost", new { ThreadID = model.ThreadID });
            else
                return RedirectToAction("EditPost", new { PostID = model.PostEditor.PostID });
        }