feed and tag
This commit is contained in:
@@ -56,13 +56,21 @@ public class ArticlesApi {
|
||||
}});
|
||||
}
|
||||
|
||||
@GetMapping(path = "feed")
|
||||
public ResponseEntity getFeed(@RequestParam(value = "offset", defaultValue = "0") int offset,
|
||||
@RequestParam(value = "limit", defaultValue = "20") int limit,
|
||||
@AuthenticationPrincipal User user) {
|
||||
return ResponseEntity.ok(articleQueryService.findUserFeed(user, new Page(offset, limit)));
|
||||
}
|
||||
|
||||
@GetMapping
|
||||
public ResponseEntity getArticles(@RequestParam(value = "offset", defaultValue = "0") int offset,
|
||||
@RequestParam(value = "limit", defaultValue = "20") int limit,
|
||||
@RequestParam(value = "tag", required = false) String tag,
|
||||
@RequestParam(value = "favorited", required = false) String favoritedBy,
|
||||
@RequestParam(value = "author", required = false) String author) {
|
||||
return ResponseEntity.ok(articleQueryService.findRecentArticles(tag, author, favoritedBy, new Page(offset, limit)));
|
||||
@RequestParam(value = "author", required = false) String author,
|
||||
@AuthenticationPrincipal User user) {
|
||||
return ResponseEntity.ok(articleQueryService.findRecentArticles(tag, author, favoritedBy, new Page(offset, limit), user));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
28
src/main/java/io/spring/api/TagsApi.java
Normal file
28
src/main/java/io/spring/api/TagsApi.java
Normal file
@@ -0,0 +1,28 @@
|
||||
package io.spring.api;
|
||||
|
||||
import io.spring.application.tag.TagsQueryService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
@RestController
|
||||
@RequestMapping(path = "tags")
|
||||
public class TagsApi {
|
||||
private TagsQueryService tagsQueryService;
|
||||
|
||||
@Autowired
|
||||
public TagsApi(TagsQueryService tagsQueryService) {
|
||||
this.tagsQueryService = tagsQueryService;
|
||||
}
|
||||
|
||||
@GetMapping
|
||||
public ResponseEntity getTags() {
|
||||
return ResponseEntity.ok(new HashMap<String, Object>() {{
|
||||
put("tags", tagsQueryService.allTags());
|
||||
}});
|
||||
}
|
||||
}
|
||||
@@ -25,6 +25,7 @@ public class WebSecurityConfig extends WebSecurityConfigurerAdapter {
|
||||
.and()
|
||||
.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.STATELESS).and()
|
||||
.authorizeRequests()
|
||||
.antMatchers(HttpMethod.GET, "/articles/feed").authenticated()
|
||||
.antMatchers(HttpMethod.POST, "/users", "/users/login").permitAll()
|
||||
.antMatchers(HttpMethod.GET, "/articles/**", "/profiles/**").permitAll()
|
||||
.anyRequest().authenticated();
|
||||
|
||||
@@ -1,13 +1,21 @@
|
||||
package io.spring.application.article;
|
||||
|
||||
import io.spring.core.user.User;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.apache.ibatis.annotations.Param;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
@Mapper
|
||||
@Component
|
||||
public interface ArticleFavoritesQueryService {
|
||||
boolean isUserFavorite(@Param("userId") String userId, @Param("articleId") String articleId);
|
||||
|
||||
int articleFavoriteCount(@Param("articleId") String articleId);
|
||||
|
||||
List<ArticleFavoriteCount> articlesFavoriteCount(@Param("ids") List<String> ids);
|
||||
|
||||
Set<String> userFavorites(@Param("ids") List<String> ids, @Param("currentUser") User currentUser);
|
||||
}
|
||||
|
||||
@@ -3,12 +3,19 @@ package io.spring.application.article;
|
||||
import io.spring.application.Page;
|
||||
import io.spring.application.profile.UserRelationshipQueryService;
|
||||
import io.spring.core.user.User;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import java.util.Set;
|
||||
|
||||
import static java.util.stream.Collectors.toList;
|
||||
|
||||
@Service
|
||||
public class ArticleQueryService {
|
||||
@@ -49,6 +56,56 @@ public class ArticleQueryService {
|
||||
}
|
||||
}
|
||||
|
||||
public ArticleDataList findRecentArticles(String tag, String author, String favoritedBy, Page page, User currentUser) {
|
||||
List<String> articleIds = articleReadService.queryArticles(tag, author, favoritedBy, page);
|
||||
int articleCount = articleReadService.countArticle(tag, author, favoritedBy);
|
||||
if (articleIds.size() == 0) {
|
||||
return new ArticleDataList(new ArrayList<>(), articleCount);
|
||||
} else {
|
||||
List<ArticleData> articles = articleReadService.findArticles(articleIds);
|
||||
fillExtraInfo(articles, currentUser);
|
||||
return new ArticleDataList(articles, articleCount);
|
||||
}
|
||||
}
|
||||
|
||||
private void fillExtraInfo(List<ArticleData> articles, User currentUser) {
|
||||
setFavoriteCount(articles);
|
||||
if (currentUser != null) {
|
||||
setIsFavorite(articles, currentUser);
|
||||
setIsFollowingAuthor(articles, currentUser);
|
||||
}
|
||||
}
|
||||
|
||||
private void setIsFollowingAuthor(List<ArticleData> articles, User currentUser) {
|
||||
Set<String> followingAuthors = userRelationshipQueryService.followingAuthors(
|
||||
currentUser.getId(),
|
||||
articles.stream().map(articleData1 -> articleData1.getProfileData().getId()).collect(toList()));
|
||||
articles.forEach(articleData -> {
|
||||
if (followingAuthors.contains(articleData.getProfileData().getId())) {
|
||||
articleData.getProfileData().setFollowing(true);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void setFavoriteCount(List<ArticleData> articles) {
|
||||
List<ArticleFavoriteCount> favoritesCounts = articleFavoritesQueryService.articlesFavoriteCount(articles.stream().map(ArticleData::getId).collect(toList()));
|
||||
Map<String, Integer> countMap = new HashMap<>();
|
||||
favoritesCounts.forEach(item -> {
|
||||
countMap.put(item.getId(), item.getCount());
|
||||
});
|
||||
articles.forEach(articleData -> articleData.setFavoritesCount(countMap.get(articleData.getId())));
|
||||
}
|
||||
|
||||
private void setIsFavorite(List<ArticleData> articles, User currentUser) {
|
||||
Set<String> favoritedArticles = articleFavoritesQueryService.userFavorites(articles.stream().map(articleData -> articleData.getId()).collect(toList()), currentUser);
|
||||
|
||||
articles.forEach(articleData -> {
|
||||
if (favoritedArticles.contains(articleData.getId())) {
|
||||
articleData.setFavorited(true);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void fillExtraInfo(String id, User user, ArticleData articleData) {
|
||||
articleData.setFavorited(articleFavoritesQueryService.isUserFavorite(user.getId(), id));
|
||||
articleData.setFavoritesCount(articleFavoritesQueryService.articleFavoriteCount(id));
|
||||
@@ -58,11 +115,22 @@ public class ArticleQueryService {
|
||||
articleData.getProfileData().getId()));
|
||||
}
|
||||
|
||||
public ArticleDataList findRecentArticles(String tag, String author, String favoritedBy, Page page) {
|
||||
List<String> articleIds = articleReadService.queryArticles(tag, author, favoritedBy, page);
|
||||
int articleCount = articleReadService.countArticle(tag, author, favoritedBy);
|
||||
return new ArticleDataList(
|
||||
articleIds.size() == 0 ? new ArrayList<>() : articleReadService.findArticles(articleIds),
|
||||
articleCount);
|
||||
public ArticleDataList findUserFeed(User user, Page page) {
|
||||
List<String> followdUsers = userRelationshipQueryService.followedUsers(user.getId());
|
||||
if (followdUsers.size() == 0) {
|
||||
return new ArticleDataList(new ArrayList<>(), 0);
|
||||
} else {
|
||||
List<ArticleData> articles = articleReadService.findArticlesOfAuthors(followdUsers, page);
|
||||
fillExtraInfo(articles, user);
|
||||
int count = articleReadService.countFeedSize(followdUsers);
|
||||
return new ArticleDataList(articles, count);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Data
|
||||
@NoArgsConstructor
|
||||
class ArticleFavoriteCount {
|
||||
private String id;
|
||||
private int count;
|
||||
}
|
||||
@@ -19,4 +19,8 @@ public interface ArticleReadService {
|
||||
int countArticle(@Param("tag") String tag, @Param("author") String author, @Param("favoritedBy") String favoritedBy);
|
||||
|
||||
List<ArticleData> findArticles(@Param("articleIds") List<String> articleIds);
|
||||
|
||||
List<ArticleData> findArticlesOfAuthors(@Param("authors") List<String> authors, @Param("page") Page page);
|
||||
|
||||
int countFeedSize(@Param("authors") List<String> authors);
|
||||
}
|
||||
|
||||
@@ -1,11 +1,19 @@
|
||||
package io.spring.application.profile;
|
||||
|
||||
import io.spring.application.article.ArticleData;
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.apache.ibatis.annotations.Param;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.Set;
|
||||
|
||||
@Component
|
||||
@Mapper
|
||||
public interface UserRelationshipQueryService {
|
||||
boolean isUserFollowing(@Param("userId") String userId, @Param("anotherUserId") String anotherUserId);
|
||||
|
||||
Set<String> followingAuthors(@Param("userId") String userId, @Param("ids") List<String> ids);
|
||||
|
||||
List<String> followedUsers(@Param("userId") String userId);
|
||||
}
|
||||
|
||||
12
src/main/java/io/spring/application/tag/TagReadService.java
Normal file
12
src/main/java/io/spring/application/tag/TagReadService.java
Normal file
@@ -0,0 +1,12 @@
|
||||
package io.spring.application.tag;
|
||||
|
||||
import org.apache.ibatis.annotations.Mapper;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Component
|
||||
@Mapper
|
||||
public interface TagReadService {
|
||||
List<String> all();
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
package io.spring.application.tag;
|
||||
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@Service
|
||||
public class TagsQueryService {
|
||||
private TagReadService tagReadService;
|
||||
|
||||
public TagsQueryService(TagReadService tagReadService) {
|
||||
this.tagReadService = tagReadService;
|
||||
}
|
||||
|
||||
public List<String> allTags() {
|
||||
return tagReadService.all();
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user