on user login and in heavy load mode, only force refresh feeds that are up for refresh

This commit is contained in:
Athou
2023-06-16 12:35:40 +02:00
parent b16978d8fe
commit fcfeaa462e
4 changed files with 26 additions and 31 deletions

View File

@@ -8,8 +8,6 @@ import javax.persistence.Table;
import javax.persistence.Temporal;
import javax.persistence.TemporalType;
import org.apache.commons.lang3.time.DateUtils;
import lombok.Getter;
import lombok.Setter;
@@ -49,17 +47,4 @@ public class User extends AbstractModel {
@Temporal(TemporalType.TIMESTAMP)
private Date recoverPasswordTokenDate;
@Column(name = "last_full_refresh")
@Temporal(TemporalType.TIMESTAMP)
private Date lastFullRefresh;
public boolean shouldRefreshFeedsAt(Date when) {
return lastFullRefresh == null || lastFullRefreshMoreThan30MinutesBefore(when);
}
private boolean lastFullRefreshMoreThan30MinutesBefore(Date when) {
return lastFullRefresh.before(DateUtils.addMinutes(when, -30));
}
}

View File

@@ -1,5 +1,6 @@
package com.commafeed.backend.service;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@@ -107,6 +108,17 @@ public class FeedSubscriptionService {
}
}
public void refreshAllUpForRefresh(User user) {
List<FeedSubscription> subs = feedSubscriptionDAO.findAll(user);
for (FeedSubscription sub : subs) {
Date disabledUntil = sub.getFeed().getDisabledUntil();
if (disabledUntil == null || disabledUntil.before(new Date())) {
Feed feed = sub.getFeed();
feedRefreshEngine.refreshImmediately(feed);
}
}
}
public Map<Long, UnreadCount> getUnreadCount(User user) {
return feedSubscriptionDAO.findAll(user).stream().collect(Collectors.toMap(FeedSubscription::getId, s -> getUnreadCount(user, s)));
}

View File

@@ -25,25 +25,20 @@ public class PostLoginActivities {
private final CommaFeedConfiguration config;
public void executeFor(User user) {
Date lastLogin = user.getLastLogin();
// only update lastLogin every once in a while in order to avoid invalidating the cache every time someone logs in
Date now = new Date();
boolean saveUser = false;
// only update lastLogin field every hour in order to not
// invalidate the cache every time someone logs in
if (lastLogin == null || lastLogin.before(DateUtils.addHours(now, -1))) {
Date lastLogin = user.getLastLogin();
if (lastLogin == null || lastLogin.before(DateUtils.addMinutes(now, -30))) {
user.setLastLogin(now);
saveUser = true;
}
if (Boolean.TRUE.equals(config.getApplicationSettings().getHeavyLoad()) && user.shouldRefreshFeedsAt(now)) {
feedSubscriptionService.refreshAll(user);
user.setLastFullRefresh(now);
saveUser = true;
}
boolean heavyLoad = Boolean.TRUE.equals(config.getApplicationSettings().getHeavyLoad());
if (heavyLoad) {
// the amount of feeds in the database that are up for refresh might be very large since we're in heavy load mode
// the feed refresh engine might not be able to catch up quickly enough
// put feeds from online users that are up for refresh at the top of the queue
feedSubscriptionService.refreshAllUpForRefresh(user);
}
if (saveUser) {
// Post login activites are susceptible to run for any webservice call.
// We update the user in a new transaction to update the user immediately.
// If we didn't and the webservice call takes time, subsequent webservice calls would have to wait for the first call to
@@ -51,5 +46,4 @@ public class PostLoginActivities {
unitOfWork.run(() -> userDAO.saveOrUpdate(user));
}
}
}

View File

@@ -18,4 +18,8 @@
<addNotNullConstraint tableName="FEEDSUBSCRIPTIONS" columnName="position" columnDataType="int" />
</changeSet>
<changeSet id="drop-unused-last-full-refresh" author="athou">
<dropColumn tableName="USERS" columnName="last_full_refresh" />
</changeSet>
</databaseChangeLog>