mirror of
https://github.com/Athou/commafeed.git
synced 2026-03-21 21:37:29 +00:00
Merge pull request #171 from Athou/jklm
Use jkeylockmanager for entry update locking
This commit is contained in:
15
pom.xml
15
pom.xml
@@ -31,6 +31,16 @@
|
|||||||
<enabled>true</enabled>
|
<enabled>true</enabled>
|
||||||
</snapshots>
|
</snapshots>
|
||||||
</repository>
|
</repository>
|
||||||
|
<repository>
|
||||||
|
<id>jklm.releases</id>
|
||||||
|
<url>http://mvn.jkeylockmanager.de</url>
|
||||||
|
<releases>
|
||||||
|
<enabled>true</enabled>
|
||||||
|
</releases>
|
||||||
|
<snapshots>
|
||||||
|
<enabled>false</enabled>
|
||||||
|
</snapshots>
|
||||||
|
</repository>
|
||||||
</repositories>
|
</repositories>
|
||||||
|
|
||||||
<build>
|
<build>
|
||||||
@@ -234,6 +244,11 @@
|
|||||||
<artifactId>joda-time</artifactId>
|
<artifactId>joda-time</artifactId>
|
||||||
<version>2.2</version>
|
<version>2.2</version>
|
||||||
</dependency>
|
</dependency>
|
||||||
|
<dependency>
|
||||||
|
<groupId>de.jkeylockmanager</groupId>
|
||||||
|
<artifactId>jkeylockmanager</artifactId>
|
||||||
|
<version>1.0.0</version>
|
||||||
|
</dependency>
|
||||||
|
|
||||||
<dependency>
|
<dependency>
|
||||||
<groupId>net.java.dev.rome</groupId>
|
<groupId>net.java.dev.rome</groupId>
|
||||||
|
|||||||
@@ -1,69 +0,0 @@
|
|||||||
package com.commafeed.backend;
|
|
||||||
|
|
||||||
import java.lang.ref.WeakReference;
|
|
||||||
import java.util.WeakHashMap;
|
|
||||||
|
|
||||||
// A map that creates and stores lock objects for arbitrary keys values.
|
|
||||||
// Lock objects which are no longer referenced are automatically released during garbage collection.
|
|
||||||
// Author: Christian d'Heureuse, www.source-code.biz
|
|
||||||
// Based on IdMutexProvider by McDowell, http://illegalargumentexception.blogspot.ch/2008/04/java-synchronizing-on-transient-id.html
|
|
||||||
// See also http://stackoverflow.com/questions/5639870/simple-java-name-based-locks
|
|
||||||
public class LockMap<KEY> {
|
|
||||||
|
|
||||||
private WeakHashMap<KeyWrapper<KEY>, WeakReference<KeyWrapper<KEY>>> map;
|
|
||||||
|
|
||||||
public LockMap() {
|
|
||||||
map = new WeakHashMap<KeyWrapper<KEY>, WeakReference<KeyWrapper<KEY>>>();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns a lock object for the specified key.
|
|
||||||
public synchronized Object get(KEY key) {
|
|
||||||
if (key == null) {
|
|
||||||
throw new NullPointerException();
|
|
||||||
}
|
|
||||||
KeyWrapper<KEY> newKeyWrapper = new KeyWrapper<KEY>(key);
|
|
||||||
WeakReference<KeyWrapper<KEY>> ref = map.get(newKeyWrapper);
|
|
||||||
KeyWrapper<KEY> oldKeyWrapper = (ref == null) ? null : ref.get();
|
|
||||||
if (oldKeyWrapper != null) {
|
|
||||||
return oldKeyWrapper;
|
|
||||||
}
|
|
||||||
map.put(newKeyWrapper,
|
|
||||||
new WeakReference<KeyWrapper<KEY>>(newKeyWrapper));
|
|
||||||
return newKeyWrapper;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Returns the number of used entries in the map.
|
|
||||||
public synchronized int size() {
|
|
||||||
return map.size();
|
|
||||||
}
|
|
||||||
|
|
||||||
// KeyWrapper wraps a key value and is used in three ways:
|
|
||||||
// - as the key for the internal WeakHashMap
|
|
||||||
// - as the value for the internal WeakHashMap, additionally wrapped in a
|
|
||||||
// WeakReference
|
|
||||||
// - as the lock object associated to the key
|
|
||||||
private static class KeyWrapper<KEY> {
|
|
||||||
private KEY key;
|
|
||||||
private int hashCode;
|
|
||||||
|
|
||||||
public KeyWrapper(KEY key) {
|
|
||||||
this.key = key;
|
|
||||||
hashCode = key.hashCode();
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean equals(Object obj) {
|
|
||||||
if (obj == this) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (obj instanceof KeyWrapper) {
|
|
||||||
return ((KeyWrapper<?>) obj).key.equals(key);
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int hashCode() {
|
|
||||||
return hashCode;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
} // end class LockMap
|
|
||||||
@@ -14,7 +14,6 @@ import javax.inject.Singleton;
|
|||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
import com.commafeed.backend.LockMap;
|
|
||||||
import com.commafeed.backend.dao.FeedDAO;
|
import com.commafeed.backend.dao.FeedDAO;
|
||||||
import com.commafeed.backend.dao.FeedSubscriptionDAO;
|
import com.commafeed.backend.dao.FeedSubscriptionDAO;
|
||||||
import com.commafeed.backend.model.ApplicationSettings;
|
import com.commafeed.backend.model.ApplicationSettings;
|
||||||
@@ -26,13 +25,17 @@ import com.commafeed.backend.pubsubhubbub.SubscriptionHandler;
|
|||||||
import com.commafeed.backend.services.ApplicationSettingsService;
|
import com.commafeed.backend.services.ApplicationSettingsService;
|
||||||
import com.commafeed.backend.services.FeedUpdateService;
|
import com.commafeed.backend.services.FeedUpdateService;
|
||||||
|
|
||||||
|
import de.jkeylockmanager.manager.KeyLockManager;
|
||||||
|
import de.jkeylockmanager.manager.KeyLockManagers;
|
||||||
|
import de.jkeylockmanager.manager.LockCallback;
|
||||||
|
|
||||||
@Singleton
|
@Singleton
|
||||||
public class FeedRefreshUpdater {
|
public class FeedRefreshUpdater {
|
||||||
|
|
||||||
protected static Logger log = LoggerFactory
|
protected static Logger log = LoggerFactory
|
||||||
.getLogger(FeedRefreshUpdater.class);
|
.getLogger(FeedRefreshUpdater.class);
|
||||||
|
|
||||||
private static LockMap<String> lockMap = new LockMap<String>();
|
private static final KeyLockManager lockManager = KeyLockManagers.newLock();
|
||||||
|
|
||||||
@Inject
|
@Inject
|
||||||
FeedUpdateService feedUpdateService;
|
FeedUpdateService feedUpdateService;
|
||||||
@@ -107,11 +110,14 @@ public class FeedRefreshUpdater {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private void updateEntry(Feed feed, FeedEntry entry,
|
private void updateEntry(final Feed feed, final FeedEntry entry,
|
||||||
List<FeedSubscription> subscriptions) {
|
final List<FeedSubscription> subscriptions) {
|
||||||
synchronized (lockMap.get(entry.getGuid())) {
|
lockManager.executeLocked(entry.getGuid(), new LockCallback() {
|
||||||
feedUpdateService.updateEntry(feed, entry, subscriptions);
|
@Override
|
||||||
}
|
public void doInLock() throws Exception {
|
||||||
|
feedUpdateService.updateEntry(feed, entry, subscriptions);
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
private void handlePubSub(final Feed feed) {
|
private void handlePubSub(final Feed feed) {
|
||||||
|
|||||||
@@ -46,8 +46,9 @@ public class UserService {
|
|||||||
PasswordEncryptionService encryptionService;
|
PasswordEncryptionService encryptionService;
|
||||||
|
|
||||||
public User login(String name, String password) {
|
public User login(String name, String password) {
|
||||||
Preconditions.checkNotNull(name);
|
if (name == null || password == null) {
|
||||||
Preconditions.checkNotNull(password);
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
User user = userDAO.findByName(name);
|
User user = userDAO.findByName(name);
|
||||||
if (user != null && !user.isDisabled()) {
|
if (user != null && !user.isDisabled()) {
|
||||||
|
|||||||
Reference in New Issue
Block a user