diff --git a/pom.xml b/pom.xml
index 922207e..08e9451 100644
--- a/pom.xml
+++ b/pom.xml
@@ -10,7 +10,7 @@
UTF-8
11
- 1.0.0
+ 1.0.1
diff --git a/src/main/java/de/bstly/board/businesslogic/BookmarksManager.java b/src/main/java/de/bstly/board/businesslogic/BookmarksManager.java
index 6503769..1d37a39 100644
--- a/src/main/java/de/bstly/board/businesslogic/BookmarksManager.java
+++ b/src/main/java/de/bstly/board/businesslogic/BookmarksManager.java
@@ -99,4 +99,17 @@ public class BookmarksManager {
}
}
+ /**
+ * Removes the entry.
+ *
+ * @param entryId the entry id
+ */
+ public void removeEntry(Long entryId) {
+ for (Bookmarks bookmarks : bookmarksRepository
+ .findAll(qBookmarks.entries.contains(entryId))) {
+ bookmarks.getEntries().remove(entryId);
+ bookmarksRepository.save(bookmarks);
+ }
+ }
+
}
diff --git a/src/main/java/de/bstly/board/businesslogic/CommentManager.java b/src/main/java/de/bstly/board/businesslogic/CommentManager.java
index b8db280..dea020f 100644
--- a/src/main/java/de/bstly/board/businesslogic/CommentManager.java
+++ b/src/main/java/de/bstly/board/businesslogic/CommentManager.java
@@ -283,6 +283,7 @@ public class CommentManager {
}
voteManager.deleteByTarget(comment.getId(), Types.comment);
+ flagManager.deleteByTarget(comment.getId(), Types.comment);
commentRepository.delete(comment);
}
diff --git a/src/main/java/de/bstly/board/businesslogic/EntryManager.java b/src/main/java/de/bstly/board/businesslogic/EntryManager.java
index d25d7f7..4568d9d 100644
--- a/src/main/java/de/bstly/board/businesslogic/EntryManager.java
+++ b/src/main/java/de/bstly/board/businesslogic/EntryManager.java
@@ -3,9 +3,13 @@
*/
package de.bstly.board.businesslogic;
+import java.math.BigInteger;
import java.time.Instant;
import java.util.List;
+import javax.persistence.EntityManager;
+import javax.persistence.Query;
+
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageImpl;
@@ -21,11 +25,10 @@ import com.querydsl.jpa.impl.JPAQueryFactory;
import de.bstly.board.model.Bookmarks;
import de.bstly.board.model.Entry;
-import de.bstly.board.model.EntryStatus;
+import de.bstly.board.model.FlaggedStatus;
import de.bstly.board.model.QEntry;
import de.bstly.board.model.QFlag;
import de.bstly.board.model.QVote;
-import de.bstly.board.model.RankedEntry;
import de.bstly.board.model.Types;
import de.bstly.board.model.VoteType;
import de.bstly.board.repository.EntryRepository;
@@ -53,61 +56,195 @@ public class EntryManager {
private FlagManager flagManager;
@Autowired
private JPAQueryFactory jpaQueryFactory;
+ @Autowired
+ private EntityManager em;
private QEntry qEntry = QEntry.entry;
private QVote qVote = QVote.vote;
private QFlag qFlag = QFlag.flag;
+ static final String UPVOTES_QUERY = "SELECT upvote.target,COUNT(upvote.id) AS count FROM votes as upvote WHERE upvote.type = 0 AND upvote.target_type = 1 GROUP BY upvote.target";
+
+ static final String DOWNVOTES_QUERY = "SELECT downvote.target,COUNT(downvote.id) AS count FROM votes as downvote WHERE downvote.type = 1 AND downvote.target_type = 1 GROUP BY downvote.target";
+
+ static final String COMMENTS_QUERY = "SELECT comment.target,MAX(comment.created) as last,COUNT(comment.id) AS count FROM comments as comment WHERE comment.flagged_status = :flag GROUP BY comment.target";
+
+ static final String RANK_CALCULATION_QUERY = "SELECT entry.*, (IFNULL(upvote.count,0) - IFNULL(downvote.count,0)) as points, (IFNULL(upvote.count,0) - IFNULL(downvote.count,0)) / IF(:gravity > 0, POW(TIMESTAMPDIFF(HOUR, entry.created, :before)+2,:gravity), 1) AS ranking FROM entries AS entry LEFT JOIN ("
+ + UPVOTES_QUERY
+ + ") AS upvote ON upvote.target = entry.id LEFT JOIN ("
+ + DOWNVOTES_QUERY
+ + ") AS downvote ON downvote.target = entry.id WHERE %s ORDER BY ranking DESC, entry.created DESC";
+
+ static final String DATE_QUERY = "SELECT entry.*FROM entries AS entry WHERE %s ORDER BY entry.created DESC";
+
+ static final String COMMENT_CALCULATION_QUERY = "SELECT entry.*, IFNULL(comment.count,0) as comments, IFNULL(comment.count,0) / IF(:gravity > 0, POW(TIMESTAMPDIFF(HOUR, comment.last, :before)+2,:gravity), 1) AS ranking FROM entries AS entry LEFT JOIN ("
+ + COMMENTS_QUERY
+ + ") AS comment ON comment.target = entry.id WHERE %s ORDER BY ranking DESC, entry.created DESC";
+
+ static final String LAST_COMMENT_QUERY = "SELECT entry.* FROM entries AS entry LEFT JOIN ("
+ + COMMENTS_QUERY
+ + ") AS comment ON comment.target = entry.id WHERE %s ORDER BY comment.last DESC, entry.created DESC";
+
+ static final String COUNT_QUERY = "SELECT count(entry.id) FROM entries as entry WHERE %s";
+
/**
* Fetch by ranking.
*
- * @param date the date
- * @param gravity the gravity
- * @param page the page
- * @param size the size
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @param gravity the gravity
+ * @param page the page
+ * @param size the size
* @return the page
*/
- public Page fetchByRanking(Instant date, double gravity, int page, int size) {
- return entryRepository.findAllByRanking(date, gravity, PageRequest.of(page, size));
- }
-
- /**
- * Fetch by comments.
- *
- * @param date the date
- * @param gravity the gravity
- * @param page the page
- * @param size the size
- * @return the page
- */
- public Page fetchByComments(Instant date, double gravity, int page, int size) {
- return entryRepository.findAllByComments(date, gravity, PageRequest.of(page, size));
- }
-
- /**
- * Fetch by last comment.
- *
- * @param date the date
- * @param page the page
- * @param size the size
- * @return the page
- */
- public Page fetchByLastComment(Instant date, int page, int size) {
- return entryRepository.findAllByLastComment(date, PageRequest.of(page, size));
+ public Page fetchByRanking(String username, Instant date, FlaggedStatus flaggedStatus,
+ double gravity, int page, int size) {
+ Query query = createEntryQuery(RANK_CALCULATION_QUERY, username, date, flaggedStatus);
+ query.setParameter("gravity", gravity);
+ query.setFirstResult((page) * size);
+ query.setMaxResults(size);
+ @SuppressWarnings("unchecked")
+ List list = query.getResultList();
+ Query queryTotal = createCountQuery(COUNT_QUERY, username, date, flaggedStatus);
+ long countResult = ((BigInteger) queryTotal.getSingleResult()).longValue();
+ return new PageImpl(list, PageRequest.of(page, size), countResult);
}
/**
* Fetch by date.
*
- * @param date the date
- * @param page the page
- * @param size the size
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @param page the page
+ * @param size the size
* @return the page
*/
- public Page fetchByDate(Instant date, int page, int size) {
- return entryRepository.findAll(
- qEntry.created.before(date).and(qEntry.entryStatus.eq(EntryStatus.NORMAL)),
- PageRequest.of(page, size, Sort.by(Order.desc("created"))));
+ public Page fetchByDate(String username, Instant date, FlaggedStatus flaggedStatus,
+ int page, int size) {
+ Query query = createEntryQuery(DATE_QUERY, username, date, flaggedStatus);
+ query.setFirstResult((page) * size);
+ query.setMaxResults(size);
+ @SuppressWarnings("unchecked")
+ List list = query.getResultList();
+ Query queryTotal = createCountQuery(COUNT_QUERY, username, date, flaggedStatus);
+ long countResult = ((BigInteger) queryTotal.getSingleResult()).longValue();
+ return new PageImpl(list, PageRequest.of(page, size), countResult);
+ }
+
+ /**
+ * Fetch by comments.
+ *
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @param gravity the gravity
+ * @param page the page
+ * @param size the size
+ * @return the page
+ */
+ public Page fetchByComments(String username, Instant date, FlaggedStatus flaggedStatus,
+ double gravity, int page, int size) {
+ Query query = createEntryQuery(COMMENT_CALCULATION_QUERY, username, date, flaggedStatus);
+ query.setParameter("gravity", gravity);
+ query.setFirstResult((page) * size);
+ query.setMaxResults(size);
+ @SuppressWarnings("unchecked")
+ List list = query.getResultList();
+ Query queryTotal = createCountQuery(COUNT_QUERY, username, date, flaggedStatus);
+ long countResult = ((BigInteger) queryTotal.getSingleResult()).longValue();
+ return new PageImpl(list, PageRequest.of(page, size), countResult);
+ }
+
+ /**
+ * Fetch by last comment.
+ *
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @param page the page
+ * @param size the size
+ * @return the page
+ */
+ public Page fetchByLastComment(String username, Instant date,
+ FlaggedStatus flaggedStatus, int page, int size) {
+ Query query = createEntryQuery(LAST_COMMENT_QUERY, username, date, flaggedStatus);
+ query.setFirstResult((page) * size);
+ query.setMaxResults(size);
+ @SuppressWarnings("unchecked")
+ List list = query.getResultList();
+ Query queryTotal = createCountQuery(COUNT_QUERY, username, date, flaggedStatus);
+ long countResult = ((BigInteger) queryTotal.getSingleResult()).longValue();
+ return new PageImpl(list, PageRequest.of(page, size), countResult);
+ }
+
+ /**
+ * Creates the entry query.
+ *
+ * @param rawQuery the raw query
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @return the query
+ */
+ protected Query createEntryQuery(String rawQuery, String username, Instant date,
+ FlaggedStatus flaggedStatus) {
+ String filterString = "";
+
+ boolean author = false;
+ if (date != null) {
+ filterString = "entry.created < :before";
+ } else {
+ date = Instant.now();
+ author = true;
+ filterString = "(entry.created < :before OR entry.author = :author)";
+ }
+
+ filterString += " AND entry.flagged_status = :flag";
+
+ Query query = em.createNativeQuery(String.format(rawQuery, filterString), Entry.class);
+ query.setParameter("before", date);
+ if (author) {
+ query.setParameter("author", username);
+ }
+ query.setParameter("flag", flaggedStatus.toString());
+
+ return query;
+ }
+
+ /**
+ * Creates the count query.
+ *
+ * @param rawQuery the raw query
+ * @param username the username
+ * @param date the date
+ * @param flaggedStatus the flagged status
+ * @return the query
+ */
+ protected Query createCountQuery(String rawQuery, String username, Instant date,
+ FlaggedStatus flaggedStatus) {
+ String filterString = "";
+
+ boolean author = false;
+ if (date != null) {
+ filterString = "entry.created < :before";
+ } else {
+ date = Instant.now();
+ author = true;
+ filterString = "(entry.created < :before OR entry.author = :author)";
+ }
+
+ filterString += " AND entry.flagged_status = :flag";
+
+ Query query = em.createNativeQuery(String.format(rawQuery, filterString));
+ query.setParameter("before", date);
+ if (author) {
+ query.setParameter("author", username);
+ }
+ query.setParameter("flag", flaggedStatus.toString());
+
+ return query;
}
/**
@@ -115,7 +252,7 @@ public class EntryManager {
*
* @param page the page
* @param size the size
- * @param asc the asc
+ * @param asc the asc
* @return the page
*/
public Page fetchFlagged(int page, int size, boolean asc) {
@@ -134,10 +271,10 @@ public class EntryManager {
* Fetch by user.
*
* @param username the username
- * @param date the date
- * @param page the page
- * @param size the size
- * @param asc the asc
+ * @param date the date
+ * @param page the page
+ * @param size the size
+ * @param asc the asc
* @return the page
*/
public Page fetchByUser(String username, Instant date, int page, int size, boolean asc) {
@@ -151,8 +288,8 @@ public class EntryManager {
* Fetch by bookmarks.
*
* @param username the username
- * @param page the page
- * @param size the size
+ * @param page the page
+ * @param size the size
* @return the page
*/
public Page fetchByBookmarks(String username, int page, int size) {
@@ -170,9 +307,9 @@ public class EntryManager {
* Apply metadata.
*
* @param username the username
- * @param karma the karma
- * @param entry the entry
- * @param ignore the ignore
+ * @param karma the karma
+ * @param entry the entry
+ * @param ignore the ignore
*/
public void applyMetadata(String username, long karma, Entry entry, List ignore) {
@@ -246,9 +383,9 @@ public class EntryManager {
* Apply metadata.
*
* @param username the username
- * @param karma the karma
- * @param entries the entries
- * @param ignore the ignore
+ * @param karma the karma
+ * @param entries the entries
+ * @param ignore the ignore
*/
public void applyMetadata(String username, long karma, List entries,
List ignore) {
@@ -295,6 +432,8 @@ public class EntryManager {
public void delete(Entry entry) {
commentManager.deleteByTarget(entry.getId());
voteManager.deleteByTarget(entry.getId(), Types.entry);
+ bookmarksManager.removeEntry(entry.getId());
+ flagManager.deleteByTarget(entry.getId(), Types.entry);
entryRepository.delete(entry);
}
@@ -315,7 +454,7 @@ public class EntryManager {
/**
* Gets the user points.
*
- * @param entryId the entry id
+ * @param entryId the entry id
* @param username the username
* @return the user points
*/
diff --git a/src/main/java/de/bstly/board/businesslogic/SettingsManager.java b/src/main/java/de/bstly/board/businesslogic/SettingsManager.java
index 0c7f838..67d0c0d 100644
--- a/src/main/java/de/bstly/board/businesslogic/SettingsManager.java
+++ b/src/main/java/de/bstly/board/businesslogic/SettingsManager.java
@@ -16,6 +16,8 @@ public class SettingsManager {
private double GRAVITY;
@Value("${bstly.board.size:30}")
private int SIZE;
+ @Value("${bstly.board.entry.changePeriod:1}")
+ private long ENTRY_CHANGE_PERIDO;
@Value("${bstly.board.comment.changePeriod:1}")
private long COMMENT_CHANGE_PERIDO;
@Value("${bstly.board.unvoteThresh:10}")
@@ -41,6 +43,15 @@ public class SettingsManager {
return SIZE;
}
+ /**
+ * Gets the entry delay.
+ *
+ * @return the entry delay
+ */
+ public long getEntryDelay() {
+ return ENTRY_CHANGE_PERIDO;
+ }
+
/**
* Gets the comment delay.
*
diff --git a/src/main/java/de/bstly/board/businesslogic/UserManager.java b/src/main/java/de/bstly/board/businesslogic/UserManager.java
index 4099cdc..2dc7be0 100644
--- a/src/main/java/de/bstly/board/businesslogic/UserManager.java
+++ b/src/main/java/de/bstly/board/businesslogic/UserManager.java
@@ -107,6 +107,24 @@ public class UserManager implements UserDetailsService, SmartInitializingSinglet
/*
* @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
*/
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
+ /*
+ * @see org.springframework.security.core.userdetails.UserDetailsService#loadUserByUsername(java.lang.String)
+ */
/*
* @see org.springframework.security.core.userdetails.UserDetailsService#
* loadUserByUsername(java.lang.String)
@@ -188,6 +206,24 @@ public class UserManager implements UserDetailsService, SmartInitializingSinglet
/*
* @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
*/
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
+ /*
+ * @see org.springframework.beans.factory.SmartInitializingSingleton#afterSingletonsInstantiated()
+ */
/*
* @see org.springframework.beans.factory.SmartInitializingSingleton#
* afterSingletonsInstantiated()
diff --git a/src/main/java/de/bstly/board/controller/BaseController.java b/src/main/java/de/bstly/board/controller/BaseController.java
index 6e6c34a..8e8d4e9 100644
--- a/src/main/java/de/bstly/board/controller/BaseController.java
+++ b/src/main/java/de/bstly/board/controller/BaseController.java
@@ -18,7 +18,7 @@ import de.bstly.board.security.LocalUserDetails;
public class BaseController {
@Autowired
- private UserManager localUserManager;
+ private UserManager userManager;
@Autowired
private SettingsManager settingsManager;
@@ -62,7 +62,7 @@ public class BaseController {
protected int getPageSize() {
String username = getCurrentUsername();
if (username != null) {
- LocalUser localUser = localUserManager.getByUsername(username);
+ LocalUser localUser = userManager.getByUsername(username);
if (localUser.getSettings() != null
&& localUser.getSettings().containsKey("pageSize")) {
try {
@@ -83,7 +83,7 @@ public class BaseController {
protected double getGravity() {
String username = getCurrentUsername();
if (username != null) {
- LocalUser localUser = localUserManager.getByUsername(username);
+ LocalUser localUser = userManager.getByUsername(username);
if (localUser.getSettings() != null && localUser.getSettings().containsKey("gravity")) {
try {
double gravity = Double.parseDouble(localUser.getSettings().get("gravity"));
@@ -103,6 +103,36 @@ public class BaseController {
return settingsManager.getGravity();
}
+ /**
+ * Gets the entry delay.
+ *
+ * @return the entry delay
+ */
+ protected long getEntryDelay() {
+ String username = getCurrentUsername();
+ if (username != null) {
+ LocalUser localUser = userManager.getByUsername(username);
+ if (localUser.getSettings() != null
+ && localUser.getSettings().containsKey("entryDelay")) {
+ try {
+ long entryDelay = Long.parseLong(localUser.getSettings().get("entryDelay"));
+
+ if (entryDelay < 0) {
+ return 0;
+ }
+
+ if (entryDelay > 15) {
+ return 15;
+ }
+
+ return entryDelay;
+ } catch (Exception e) {
+ }
+ }
+ }
+ return settingsManager.getEntryDelay();
+ }
+
/**
* Gets the comment delay.
*
@@ -111,7 +141,7 @@ public class BaseController {
protected long getCommentDelay() {
String username = getCurrentUsername();
if (username != null) {
- LocalUser localUser = localUserManager.getByUsername(username);
+ LocalUser localUser = userManager.getByUsername(username);
if (localUser.getSettings() != null
&& localUser.getSettings().containsKey("commentDelay")) {
try {
diff --git a/src/main/java/de/bstly/board/controller/EntryController.java b/src/main/java/de/bstly/board/controller/EntryController.java
index fc31081..04eb0fc 100644
--- a/src/main/java/de/bstly/board/controller/EntryController.java
+++ b/src/main/java/de/bstly/board/controller/EntryController.java
@@ -8,17 +8,17 @@ import java.io.InputStream;
import java.net.URL;
import java.net.URLDecoder;
import java.time.Instant;
+import java.time.temporal.ChronoUnit;
import java.util.List;
import java.util.Optional;
import java.util.Scanner;
-import java.util.stream.Collectors;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
-import org.springframework.data.domain.PageImpl;
import org.springframework.http.HttpStatus;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.web.bind.annotation.GetMapping;
+import org.springframework.web.bind.annotation.PatchMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
@@ -38,7 +38,6 @@ import de.bstly.board.controller.validation.EntryValidator;
import de.bstly.board.model.Entry;
import de.bstly.board.model.EntryStatus;
import de.bstly.board.model.FlaggedStatus;
-import de.bstly.board.model.RankedEntry;
import de.bstly.board.model.Types;
import de.bstly.board.model.Vote;
import de.bstly.board.model.VoteType;
@@ -91,21 +90,15 @@ public class EntryController extends BaseController {
gravityParameter = Optional.of(2.0);
}
- Page entries = entryManager.fetchByRanking(dateParameter.orElse(Instant.now()),
+ Page entries = entryManager.fetchByRanking(getCurrentUsername(),
+ dateParameter.orElse(null), FlaggedStatus.NORMAL,
gravityParameter.orElse(getGravity()), pageParameter.orElse(0),
sizeParameter.orElse(settingsManager.getPageSize()));
- Page transformed = new PageImpl(
- entries.getContent().stream().map(rankedEntry -> {
- Entry entry = Entry.fromRankedEntry(rankedEntry);
- entry.getMetadata().put("points", rankedEntry.getPoints());
- return entry;
- }).collect(Collectors.toList()), entries.getPageable(), entries.getTotalElements());
-
List ignore = ignoreParameter.orElse(Lists.newArrayList());
entryManager.applyMetadata(getCurrentUsername(), userManager.getKarma(getCurrentUsername()),
- transformed.getContent(), ignore);
- return transformed;
+ entries.getContent(), ignore);
+ return entries;
}
/**
@@ -132,8 +125,9 @@ public class EntryController extends BaseController {
dateParameter = Optional.of(Instant.now());
}
- Page entries = entryManager.fetchByDate(dateParameter.orElse(Instant.now()),
- pageParameter.orElse(0), sizeParameter.orElse(settingsManager.getPageSize()));
+ Page entries = entryManager.fetchByDate(getCurrentUsername(),
+ dateParameter.orElse(null), FlaggedStatus.NORMAL, pageParameter.orElse(0),
+ sizeParameter.orElse(settingsManager.getPageSize()));
List ignore = ignoreParameter.orElse(Lists.newArrayList());
entryManager.applyMetadata(getCurrentUsername(), userManager.getKarma(getCurrentUsername()),
entries.getContent(), ignore);
@@ -166,19 +160,15 @@ public class EntryController extends BaseController {
dateParameter = Optional.of(Instant.now());
}
- Page entries = entryManager.fetchByComments(
- dateParameter.orElse(Instant.now()), gravityParameter.orElse(getGravity()),
- pageParameter.orElse(0), sizeParameter.orElse(settingsManager.getPageSize()));
-
- Page transformed = new PageImpl(
- entries.getContent().stream().map(rankedEntry -> Entry.fromRankedEntry(rankedEntry))
- .collect(Collectors.toList()),
- entries.getPageable(), entries.getTotalElements());
+ Page entries = entryManager.fetchByComments(getCurrentUsername(),
+ dateParameter.orElse(null), FlaggedStatus.NORMAL,
+ gravityParameter.orElse(getGravity()), pageParameter.orElse(0),
+ sizeParameter.orElse(settingsManager.getPageSize()));
List ignore = ignoreParameter.orElse(Lists.newArrayList());
entryManager.applyMetadata(getCurrentUsername(), userManager.getKarma(getCurrentUsername()),
- transformed.getContent(), ignore);
- return transformed;
+ entries.getContent(), ignore);
+ return entries;
}
/**
@@ -205,8 +195,9 @@ public class EntryController extends BaseController {
dateParameter = Optional.of(Instant.now());
}
- Page entries = entryManager.fetchByLastComment(dateParameter.orElse(Instant.now()),
- pageParameter.orElse(0), sizeParameter.orElse(settingsManager.getPageSize()));
+ Page entries = entryManager.fetchByLastComment(getCurrentUsername(),
+ dateParameter.orElse(null), FlaggedStatus.NORMAL, pageParameter.orElse(0),
+ sizeParameter.orElse(settingsManager.getPageSize()));
List ignore = ignoreParameter.orElse(Lists.newArrayList());
entryManager.applyMetadata(getCurrentUsername(), userManager.getKarma(getCurrentUsername()),
@@ -294,7 +285,7 @@ public class EntryController extends BaseController {
HttpStatus.UNPROCESSABLE_ENTITY);
}
- entry.setCreated(Instant.now());
+ entry.setCreated(Instant.now().plus(getEntryDelay(), ChronoUnit.MINUTES));
entry.setAuthor(getCurrentUsername());
entry.setEntryStatus(EntryStatus.NORMAL);
entry.setFlaggedStatus(FlaggedStatus.NORMAL);
@@ -316,6 +307,57 @@ public class EntryController extends BaseController {
return entry;
}
+ /**
+ * Update entry.
+ *
+ * @param entry the entry
+ * @param ignoreParameter the ignore parameter
+ * @return the entry
+ */
+ @PreAuthorize("isAuthenticated()")
+ @PatchMapping
+ public Entry updateEntry(@RequestBody Entry entry,
+ @RequestParam("ignore") Optional> ignoreParameter) {
+ Entry orgEnry = entryManager.get(entry.getId());
+ if (orgEnry == null || !orgEnry.getAuthor().equals(getCurrentUsername()) || orgEnry
+ .getCreated().plus(getEntryDelay(), ChronoUnit.MINUTES).isBefore(Instant.now())) {
+ throw new EntityResponseStatusException(HttpStatus.FORBIDDEN);
+ }
+
+ RequestBodyErrors bindingResult = new RequestBodyErrors(entry);
+ entryValidator.validate(entry, bindingResult);
+
+ if (bindingResult.hasErrors()) {
+ throw new EntityResponseStatusException(bindingResult.getAllErrors(),
+ HttpStatus.UNPROCESSABLE_ENTITY);
+ }
+
+ orgEnry.setUrl(entry.getUrl());
+ orgEnry.setTitle(entry.getTitle().trim());
+ orgEnry.setText(entry.getText().trim());
+ orgEnry = entryManager.save(orgEnry);
+
+ List ignore = ignoreParameter.orElse(Lists.newArrayList());
+ entryManager.applyMetadata(getCurrentUsername(), userManager.getKarma(getCurrentUsername()),
+ entry, ignore);
+ return entry;
+ }
+
+ /**
+ * Detele entry.
+ *
+ * @param id the id
+ */
+ public void deteleEntry(@PathVariable("id") Long id) {
+ Entry orgEntry = entryManager.get(id);
+ if (orgEntry == null || !orgEntry.getAuthor().equals(getCurrentUsername()) || orgEntry
+ .getCreated().plus(getEntryDelay(), ChronoUnit.MINUTES).isBefore(Instant.now())) {
+ throw new EntityResponseStatusException(HttpStatus.FORBIDDEN);
+ }
+
+ entryManager.delete(orgEntry);
+ }
+
/**
* Gets the title.
*
diff --git a/src/main/java/de/bstly/board/controller/SettingsController.java b/src/main/java/de/bstly/board/controller/SettingsController.java
index 4a580e5..ec31c8b 100644
--- a/src/main/java/de/bstly/board/controller/SettingsController.java
+++ b/src/main/java/de/bstly/board/controller/SettingsController.java
@@ -34,9 +34,11 @@ public class SettingsController extends BaseController {
Map settings = Maps.newHashMap();
settings.put("gravity", getGravity());
settings.put("pageSize", getPageSize());
+ settings.put("entryDelay", getEntryDelay());
settings.put("commentDelay", getCommentDelay());
settings.put("defaultGravity", settingsManager.getGravity());
settings.put("defaultPageSize", settingsManager.getPageSize());
+ settings.put("defaultEntryDelay", settingsManager.getEntryDelay());
settings.put("defaultCommentDelay", settingsManager.getCommentDelay());
return settings;
}
diff --git a/src/main/java/de/bstly/board/model/Entry.java b/src/main/java/de/bstly/board/model/Entry.java
index fba9ec6..9a7b39f 100644
--- a/src/main/java/de/bstly/board/model/Entry.java
+++ b/src/main/java/de/bstly/board/model/Entry.java
@@ -57,6 +57,8 @@ public class Entry {
@Transient
private Double ranking;
@Transient
+ private Long points;
+ @Transient
private Map metadata;
/**
@@ -239,6 +241,24 @@ public class Entry {
this.ranking = ranking;
}
+ /**
+ * Gets the points.
+ *
+ * @return the points
+ */
+ public Long getPoints() {
+ return points;
+ }
+
+ /**
+ * Sets the points.
+ *
+ * @param points the new points
+ */
+ public void setPoints(Long points) {
+ this.points = points;
+ }
+
/**
* Gets the metadata.
*
@@ -260,23 +280,4 @@ public class Entry {
this.metadata = metadata;
}
- /**
- * From ranked entry.
- *
- * @param rankedEntry the ranked entry
- * @return the entry
- */
- public static Entry fromRankedEntry(RankedEntry rankedEntry) {
- Entry entry = new Entry();
- entry.setId(rankedEntry.getId());
- entry.setAuthor(rankedEntry.getAuthor());
- entry.setCreated(rankedEntry.getCreated());
- entry.setEntryType(rankedEntry.getEntry_Type());
- entry.setUrl(rankedEntry.getUrl());
- entry.setTitle(rankedEntry.getTitle());
- entry.setText(rankedEntry.getText());
- entry.setRanking(rankedEntry.getRanking());
- return entry;
- }
-
}
diff --git a/src/main/java/de/bstly/board/model/RankedEntry.java b/src/main/java/de/bstly/board/model/RankedEntry.java
deleted file mode 100644
index 581f973..0000000
--- a/src/main/java/de/bstly/board/model/RankedEntry.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/**
- *
- */
-package de.bstly.board.model;
-
-import java.time.Instant;
-
-
-/**
- * The Interface RankedEntry.
- */
-public interface RankedEntry {
-
- /**
- * Gets the id.
- *
- * @return the id
- */
- Long getId();
-
- /**
- * Gets the author.
- *
- * @return the author
- */
- String getAuthor();
-
- /**
- * Gets the created.
- *
- * @return the created
- */
- Instant getCreated();
-
- /**
- * Gets the entry type.
- *
- * @return the entry type
- */
- EntryType getEntry_Type();
-
- /**
- * Gets the url.
- *
- * @return the url
- */
- String getUrl();
-
- /**
- * Gets the title.
- *
- * @return the title
- */
- String getTitle();
-
- /**
- * Gets the text.
- *
- * @return the text
- */
- String getText();
-
- /**
- * Gets the ranking.
- *
- * @return the ranking
- */
- Double getRanking();
-
- /**
- * Gets the points.
- *
- * @return the points
- */
- Long getPoints();
-}
diff --git a/src/main/java/de/bstly/board/repository/EntryRepository.java b/src/main/java/de/bstly/board/repository/EntryRepository.java
index bc9c3d3..805fd28 100644
--- a/src/main/java/de/bstly/board/repository/EntryRepository.java
+++ b/src/main/java/de/bstly/board/repository/EntryRepository.java
@@ -3,18 +3,11 @@
*/
package de.bstly.board.repository;
-import java.time.Instant;
-
-import org.springframework.data.domain.Page;
-import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;
-import org.springframework.data.jpa.repository.Query;
import org.springframework.data.querydsl.QuerydslPredicateExecutor;
-import org.springframework.data.repository.query.Param;
import org.springframework.stereotype.Repository;
import de.bstly.board.model.Entry;
-import de.bstly.board.model.RankedEntry;
/**
* The Interface EntryRepository.
@@ -23,60 +16,4 @@ import de.bstly.board.model.RankedEntry;
public interface EntryRepository
extends JpaRepository, QuerydslPredicateExecutor {
- static final String UPVOTES_QUERY = "SELECT upvote.target,COUNT(upvote.id) AS count FROM votes as upvote WHERE upvote.type = 0 AND upvote.target_type = 1 GROUP BY upvote.target";
-
- static final String DOWNVOTES_QUERY = "SELECT downvote.target,COUNT(downvote.id) AS count FROM votes as downvote WHERE downvote.type = 1 AND downvote.target_type = 1 GROUP BY downvote.target";
-
- static final String COMMENTS_QUERY = "SELECT comment.target,MAX(comment.created) as last,COUNT(comment.id) AS count FROM comments as comment WHERE comment.flagged_status = 'NORMAL' GROUP BY comment.target";
-
- static final String RANK_CALCULATION_QUERY = "SELECT entry.*, (IFNULL(upvote.count,0) - IFNULL(downvote.count,0)) as points, (IFNULL(upvote.count,0) - IFNULL(downvote.count,0)) / IF(:gravity > 0, POW(TIMESTAMPDIFF(HOUR, entry.created, :before)+2,:gravity), 1) AS ranking FROM entries AS entry LEFT JOIN ("
- + UPVOTES_QUERY
- + ") AS upvote ON upvote.target = entry.id LEFT JOIN ("
- + DOWNVOTES_QUERY
- + ") AS downvote ON downvote.target = entry.id WHERE entry.created < :before AND entry.flagged_status = 'NORMAL' ORDER BY ranking DESC, entry.created DESC";
-
- static final String COMMENT_CALCULATION_QUERY = "SELECT entry.*, IFNULL(comment.count,0) as comments, IFNULL(comment.count,0) / IF(:gravity > 0, POW(TIMESTAMPDIFF(HOUR, comment.last, :before)+2,:gravity), 1) AS ranking FROM entries AS entry LEFT JOIN ("
- + COMMENTS_QUERY
- + ") AS comment ON comment.target = entry.id WHERE entry.created < :before AND entry.flagged_status = 'NORMAL' ORDER BY ranking DESC, entry.created DESC";
-
- static final String LAST_COMMENT_QUERY = "SELECT entry.* FROM entries AS entry LEFT JOIN ("
- + COMMENTS_QUERY
- + ") AS comment ON comment.target = entry.id WHERE entry.created < :before AND entry.flagged_status = 'NORMAL' ORDER BY comment.last DESC, entry.created DESC";
-
- static final String COUNT_QUERY = "SELECT count(*) FROM entries as entry WHERE entry.created < :before AND entry.flagged_status = 'NORMAL'";
-
- /**
- * Find all by ranking.
- *
- * @param before the before
- * @param gravity the gravity
- * @param pageable the pageable
- * @return the page
- */
- @Query(value = RANK_CALCULATION_QUERY, countQuery = COUNT_QUERY, nativeQuery = true)
- Page findAllByRanking(@Param("before") Instant before,
- @Param("gravity") double gravity, Pageable pageable);
-
- /**
- * Find all by comments.
- *
- * @param before the before
- * @param gravity the gravity
- * @param pageable the pageable
- * @return the page
- */
- @Query(value = COMMENT_CALCULATION_QUERY, countQuery = COUNT_QUERY, nativeQuery = true)
- Page findAllByComments(@Param("before") Instant before,
- @Param("gravity") double gravity, Pageable pageable);
-
- /**
- * Find all by last comment.
- *
- * @param before the before
- * @param pageable the pageable
- * @return the page
- */
- @Query(value = LAST_COMMENT_QUERY, countQuery = COUNT_QUERY, nativeQuery = true)
- Page findAllByLastComment(@Param("before") Instant before, Pageable pageable);
-
}
diff --git a/src/main/java/de/bstly/board/security/SecurityConfig.java b/src/main/java/de/bstly/board/security/SecurityConfig.java
index cd9edd4..fb31934 100755
--- a/src/main/java/de/bstly/board/security/SecurityConfig.java
+++ b/src/main/java/de/bstly/board/security/SecurityConfig.java
@@ -50,6 +50,9 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Value("${loginTargetUrl:/}")
private String loginTargetUrl;
+ /*
+ * @see org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter#configure(org.springframework.security.config.annotation.web.builders.HttpSecurity)
+ */
/*
* @see org.springframework.security.config.annotation.web.configuration.
* WebSecurityConfigurerAdapter#configure(org.springframework.security.config.
@@ -126,6 +129,11 @@ public class SecurityConfig extends WebSecurityConfigurerAdapter {
return rememberMeServices;
}
+ /**
+ * Cors configuration source.
+ *
+ * @return the cors configuration source
+ */
@Bean
public CorsConfigurationSource corsConfigurationSource() {
CorsConfiguration configuration = new CorsConfiguration();