Java Spring with JPA:对来自不同请求的JPA实体的并发访问进行排队

Java Spring with JPA:对来自不同请求的JPA实体的并发访问进行排队,java,spring-mvc,jpa,concurrency,spring-data-jpa,Java,Spring Mvc,Jpa,Concurrency,Spring Data Jpa,我有一个SpringWeb应用程序,可以并发访问特定的资源。此资源包含一个特定数量的对象列表,这些对象可能由请求获取。如果列表为空,则不应再返回任何SomeClass对象 资源如下所示: public class Resource { private List<SomeClass> someList; public List<SomeClass> fetch() { List<SomeClass> fetched = new

我有一个SpringWeb应用程序,可以并发访问特定的资源。此资源包含一个特定数量的对象列表,这些对象可能由请求获取。如果列表为空,则不应再返回任何SomeClass对象

资源如下所示:

public class Resource {

    private List<SomeClass> someList;

    public List<SomeClass> fetch() {
        List<SomeClass> fetched = new ArrayList<SomeClass>();
        int max = someList.size();          
        if(max<=0) {
            return fetched;
        }

        int added = 0;
        while(added<max) {
            int randomIndex = Math.random(max-1);
            SomeClass someClass = someList.get(randomIndex);
            if(!fetched.contains(someClass)) {
                fetched.add(someClass);
                ++added;
            }
        }
        someList.remove(fetched);

        return fetched;
    }

}
此资源加载到服务层,然后访问并保存回数据库:

@Service    
public class ResourceService {

    @Autowired
    private ResourceRepository repo;

    public List<SomeClass> fetch(long id) {
        Resource resource = repo.findOne(id);
        List<SomeClass> fetched = resource.fetch();
        repo.save(resource);
        return fetched;
    }

}
我尝试在ResourceServicefetch方法上使用@Transactional来避免两个并发请求可能从列表中获取SomeClass对象的问题,尽管第一个请求已经清空了列表,但我不确定这是否是正确的方法。。。我必须在Resourcefetch方法上使用@Synchronized,还是在服务层中引入显式锁


我需要确保只有一个请求正在访问获取SomeClass对象列表的资源,而不会引发异常。相反,后续请求应该排队,并在当前请求完成获取SomeClass对象列表后尝试访问资源。

我的最终解决方案是在@Service中引入一个,并将所有传入请求添加到该服务中。一个单独的线程是队列中的一个元素,只要添加一个线程并对其进行处理


我认为这是最干净的解决方案,因为添加一个将阻止请求处理

我认为简单地同步Java synchronize会有所帮助,因为默认情况下,所有SpringBean都是单例的,JVM中只有一个Bean实例。我还需要ResourceServicefetch mehotd上的@Transactional吗?如果两个请求从数据库加载资源,第一个请求获取其列表,然后第二个请求尝试获取其列表,尽管数据库中的资源尚未更新,因此两个请求都使用相同的对象!?对不起,我没有仔细阅读您的问题:资源是JPA实体吗?在这种情况下,您可以使用。我是否正确理解ResourceService==浏览器的客户端?是的,资源是一个JPA实体。。问题是,我不能使用乐观锁定,因为据我所知,这会引发异常,但我需要客户端排队以访问资源,因此第二个请求在第一个请求完成后访问资源。。是的,我的resourceservice的客户端可能是一个浏览器应用程序,或者一些原生android应用程序。我不认为这真的很重要。当浏览器请求一个资源并且从不更新它时,会发生什么,也就是说从不释放锁?你有关于如何做的更多信息吗,任何链接?或者github项目有什么例子吗?