예제 #1
0
        /// <summary>
        /// 创建 <see cref="ArticlePage"/>
        /// </summary>
        /// <param name="authorIdCode">作者识别码</param>
        /// <param name="sidForAuthor">文章在作者名下的序号</param>
        /// <param name="currentUserId">当前登录用户 ID</param>
        /// <param name="isOperator">当前登录用户是否为运维职员</param>
        /// <param name="dbContext"><see cref="KeylolDbContext"/></param>
        /// <param name="cachedData"><see cref="CachedDataProvider"/></param>
        /// <param name="userManager"><see cref="KeylolUserManager"/></param>
        /// <returns><see cref="ArticlePage"/></returns>
        public static async Task <ArticlePage> CreateAsync(string authorIdCode, int sidForAuthor, string currentUserId,
                                                           bool isOperator, KeylolDbContext dbContext, CachedDataProvider cachedData, KeylolUserManager userManager)
        {
            var articlePage = new ArticlePage();

            var article = await dbContext.Articles
                          .Include(a => a.Author)
                          .Include(a => a.TargetPoint)
                          .Where(a => a.Author.IdCode == authorIdCode && a.SidForAuthor == sidForAuthor)
                          .SingleOrDefaultAsync();

            if (article == null)
            {
                return(articlePage);
            }

            articlePage.Archived = article.Archived != ArchivedState.None;
            if (articlePage.Archived.Value && currentUserId != article.AuthorId && !isOperator)
            {
                return(articlePage);
            }

            articlePage.PointBasicInfo =
                await PointBasicInfo.CreateAsync(currentUserId, article.TargetPoint, dbContext, cachedData);

            articlePage.AuthorBasicInfo = new UserBasicInfo
            {
                Id                  = article.Author.Id,
                IdCode              = article.Author.IdCode,
                AvatarImage         = article.Author.AvatarImage,
                UserName            = article.Author.UserName,
                FriendCount         = await cachedData.Subscriptions.GetFriendCountAsync(article.AuthorId),
                SubscribedUserCount = await cachedData.Subscriptions
                                      .GetSubscribedUserCountAsync(article.AuthorId),
                SubscriberCount = await cachedData.Subscriptions
                                  .GetSubscriberCountAsync(article.AuthorId, SubscriptionTargetType.User),
                IsFriend = string.IsNullOrWhiteSpace(currentUserId)
                    ? (bool?)null
                    : await cachedData.Users.IsFriendAsync(currentUserId, article.AuthorId),
                Subscribed = string.IsNullOrWhiteSpace(currentUserId)
                    ? (bool?)null
                    : await cachedData.Subscriptions.IsSubscribedAsync(currentUserId, article.AuthorId,
                                                                       SubscriptionTargetType.User),
                SteamId = await userManager.GetSteamIdAsync(article.AuthorId)
            };
            if (!string.IsNullOrWhiteSpace(articlePage.AuthorBasicInfo.SteamId))
            {
                articlePage.AuthorBasicInfo.SteamProfileName = article.Author.SteamProfileName;
            }
            articlePage.AuthorPlayedTime = article.TargetPoint.SteamAppId == null
                ? null
                : (await dbContext.UserSteamGameRecords
                   .Where(r => r.UserId == article.AuthorId && r.SteamAppId == article.TargetPoint.SteamAppId)
                   .SingleOrDefaultAsync())?.TotalPlayedTime;
            articlePage.Id       = article.Id;
            articlePage.Title    = article.Title;
            articlePage.Subtitle = article.Subtitle;
            var attachedPointIds = Helpers.SafeDeserialize <List <string> >(article.AttachedPoints) ?? new List <string>();

            articlePage.AttachedPoints = (from id in attachedPointIds
                                          join point in await(from point in dbContext.Points
                                                              where attachedPointIds.Contains(point.Id)
                                                              select new
            {
                point.Type,
                point.Id,
                point.IdCode,
                point.AvatarImage,
                point.ChineseName,
                point.EnglishName
            }).ToListAsync() on id equals point.Id
                                          select new PointBasicInfo
            {
                Type = point.Type,
                Id = point.Id,
                IdCode = point.IdCode,
                AvatarImage = point.AvatarImage,
                ChineseName = point.ChineseName,
                EnglishName = point.EnglishName
            }).ToList();
            articlePage.PublishTime             = article.PublishTime;
            articlePage.Rejected                = article.Rejected;
            articlePage.Spotlighted             = article.Spotlighted;
            articlePage.Warned                  = article.Warned;
            articlePage.Content                 = article.Content;
            articlePage.ReproductionRequirement =
                Helpers.SafeDeserialize <ReproductionRequirement>(article.ReproductionRequirement);
            articlePage.LikeCount = await cachedData.Likes.GetTargetLikeCountAsync(article.Id, LikeTargetType.Article);

            articlePage.Liked = string.IsNullOrWhiteSpace(currentUserId)
                ? (bool?)null
                : await cachedData.Likes.IsLikedAsync(currentUserId, article.Id, LikeTargetType.Article);

            articlePage.Rating              = article.Rating;
            articlePage.CoverImage          = article.CoverImage;
            articlePage.Pros                = Helpers.SafeDeserialize <List <string> >(article.Pros);
            articlePage.Cons                = Helpers.SafeDeserialize <List <string> >(article.Cons);
            articlePage.RecommendedArticles =
                await RecommendedArticleList.CreateAsync(article.Id, article.AuthorId, article.TargetPointId, dbContext);

            var comments = await ArticleCommentList.CreateAsync(article, 1, currentUserId, isOperator, true, dbContext,
                                                                cachedData);

            articlePage.CommentCount      = comments.Item2;
            articlePage.LatestCommentTime = comments.Item3;
            articlePage.CommentPageCount  = comments.Item4;
            articlePage.Comments          = comments.Item1;
            return(articlePage);
        }
예제 #2
0
        /// <summary>
        /// 创建 <see cref="RecommendedArticleList"/>
        /// </summary>
        /// <param name="currentArticleId">当前文章 ID</param>
        /// <param name="authorId">文章作者 ID</param>
        /// <param name="pointId">据点 ID</param>
        /// <param name="dbContext"><see cref="KeylolDbContext"/></param>
        /// <returns><see cref="RecommendedArticleList"/></returns>
        public static async Task <RecommendedArticleList> CreateAsync(string currentArticleId, string authorId,
                                                                      string pointId, KeylolDbContext dbContext)
        {
            var result = new RecommendedArticleList(3);

            // 作者的其他文章中,认可最多的文章
            var a = await(from article in dbContext.Articles
                          where article.AuthorId == authorId && article.Archived == ArchivedState.None &&
                          article.Rejected == false && article.Id != currentArticleId
                          orderby dbContext.Likes
                          .Count(l => l.TargetId == article.Id && l.TargetType == LikeTargetType.Article) descending
                          select new
            {
                AuthorIdCode = article.Author.IdCode,
                article.SidForAuthor,
                article.CoverImage,
                article.Title,
                article.Subtitle
            }).FirstOrDefaultAsync();

            if (a != null)
            {
                result.Add(new RecommendedArticle
                {
                    AuthorIdCode = a.AuthorIdCode,
                    SidForAuthor = a.SidForAuthor,
                    CoverImage   = a.CoverImage,
                    Title        = a.Title,
                    Subtitle     = a.Subtitle
                });
            }

            // 据点的其他文章中,认可最多的文章
            a = await(from article in dbContext.Articles
                      where article.TargetPointId == pointId && article.Archived == ArchivedState.None &&
                      article.Rejected == false && article.Id != currentArticleId
                      orderby dbContext.Likes
                      .Count(l => l.TargetId == article.Id && l.TargetType == LikeTargetType.Article) descending
                      select new
            {
                AuthorIdCode = article.Author.IdCode,
                article.SidForAuthor,
                article.CoverImage,
                article.Title,
                article.Subtitle
            }).FirstOrDefaultAsync();
            if (a != null)
            {
                result.Add(new RecommendedArticle
                {
                    AuthorIdCode = a.AuthorIdCode,
                    SidForAuthor = a.SidForAuthor,
                    CoverImage   = a.CoverImage,
                    Title        = a.Title,
                    Subtitle     = a.Subtitle
                });
            }

            // 作者最近认可过的文章
            a = await(from like in dbContext.Likes
                      where like.OperatorId == authorId && like.TargetType == LikeTargetType.Article
                      join article in dbContext.Articles on like.TargetId equals article.Id
                      where article.Archived == ArchivedState.None && article.Rejected == false
                      orderby like.Sid descending
                      select new
            {
                AuthorIdCode = article.Author.IdCode,
                article.SidForAuthor,
                article.CoverImage,
                article.Title,
                article.Subtitle
            }).FirstOrDefaultAsync();
            if (a != null)
            {
                result.Add(new RecommendedArticle
                {
                    AuthorIdCode = a.AuthorIdCode,
                    SidForAuthor = a.SidForAuthor,
                    CoverImage   = a.CoverImage,
                    Title        = a.Title,
                    Subtitle     = a.Subtitle
                });
            }

            result = new RecommendedArticleList(result.DistinctBy(aa => new { aa.AuthorIdCode, aa.SidForAuthor }));
            // 广场收稿箱中最近的文章
            if (result.Count < 3)
            {
                var remaining = 3 - result.Count;
                var supplies  = await(from article in dbContext.Articles
                                      where article.Rejected == false && article.Archived == ArchivedState.None &&
                                      article.Id != currentArticleId
                                      orderby article.Sid descending
                                      select new
                {
                    AuthorIdCode = article.Author.IdCode,
                    article.SidForAuthor,
                    article.CoverImage,
                    article.Title,
                    article.Subtitle
                }).Take(() => remaining).ToListAsync();
                result.AddRange(supplies.Select(s => new RecommendedArticle
                {
                    AuthorIdCode = s.AuthorIdCode,
                    SidForAuthor = s.SidForAuthor,
                    CoverImage   = s.CoverImage,
                    Title        = s.Title,
                    Subtitle     = s.Subtitle
                }));
            }

            return(result);
        }