1

我有一个 Spring Boot 应用程序,它有两个 bean -AppStateUsers. AppState取决于bean Users,因为它自动装配它。两个 bean 的骨架代码如下。

@Component
@EnableScheduling
public class Users {
    @Getter // lombok
    private List<String> users;

    @PostConstruct
    public void init(){
        users = new ArrayList<>();
        load(); // I removed this later
    }

    @Scheduled(fixedRate = 3600000)
    public void load(){
        // load list of users from (say) a file and populate ArrayList 'users'
        // this method takes at least 3 mins to finish
    }
}

AppState

@Component
public class AppState {
    @Atowired
    private Users users;

    public List<String> getUsers(){
        return users.getUsers();
    }
}

我注意到load()in中的方法Users被触发了两次——可能一次是在创建 bean之后init(),另一次是在调度期间。所以我删除了对in的调用。这解决了冗余呼叫问题。load()Usersload()init()

但是,现在我发现我的服务在创建 bean 后立即启动AppStateUsers即使Users尚未填充数据。这对我来说是有风险的,因为在此期间,如果被查询,服务将返回 0 个用户。

我需要以下任何方面的帮助。

  • 我是否应该load()返回init()以确保 bean 完成后PostConstruct,它确实具有所有用户信息?如果我走这条路,我怎样才能防止冗余运行load()

  • 如果load()要置身事外init(),我怎么能保证AppState不准备好除非Users已经执行load()?我尝试使用以下代码,AppState但它只是挂起。

代码如下。

@PostConstruct
public void appStateInit(){
    while(users.getUsers().size()==0){
        try{
            Thread.sleep(10000); // sleep 10s
        }catch(whatever){
        }
    }
}
4

1 回答 1

2

我建议flag在课堂上有一个并将其设置为true一旦 init() 完成。您可以跳过load()if flagis not set yet 的执行,例如:

private AtomicBoolean shouldExecute;

@PostConstruct
    public void init(){
        users = new ArrayList<>();
        shouldExecute = true;
    }

@Scheduled(fixedRate = 3600000)
public void load(){
    if(shouldExecute){
       // load list of users from (say) a file and populate ArrayList 'users'
    // this method takes at least 3 mins to finish
    } 
}

此外,另一种解决方案是initialDelay@Scheduled注释中配置(此处的文档),这将通过配置的毫秒数延迟第一次执行,例如:

    @Scheduled(fixedRate = 3600000, initialDelay=180000)
    public void load(){
        // load list of users from (say) a file and populate ArrayList 'users'
        // this method takes at least 3 mins to finish
    }
于 2016-04-13T21:38:47.660 回答