Java 如何将类的单个实例用于所有请求RestController

Java 如何将类的单个实例用于所有请求RestController,java,spring,spring-boot,Java,Spring,Spring Boot,我有一个名为PriorityJobScheduler的类,在restcontrol中,我只想为所有请求创建一次它的对象,我在@PostConstruct方法中实例化这个类,但对于每个新请求,我都会得到一个新对象 我想知道如何只实例化这个类一次,并将其对象用于所有请求 public class PriorityJobScheduler { Logger log = LoggerFactory.getLogger(PriorityJobScheduler.class); private Exe

我有一个名为PriorityJobScheduler的类,在restcontrol中,我只想为所有请求创建一次它的对象,我在@PostConstruct方法中实例化这个类,但对于每个新请求,我都会得到一个新对象

我想知道如何只实例化这个类一次,并将其对象用于所有请求

public class PriorityJobScheduler {
 Logger log = LoggerFactory.getLogger(PriorityJobScheduler.class);

 private ExecutorService priorityJobPoolExecutor;
 private ExecutorService priorityJobScheduler = 
                Executors.newSingleThreadExecutor();
 private PriorityBlockingQueue<DowloadProccess> priorityQueue;

 public PriorityJobScheduler(Integer poolSize, Integer queueSize) {
    Comparator<DowloadProccess> priorityComparator = Comparator.comparingInt(DowloadProccess::getJobPriority).reversed();
    
    priorityJobPoolExecutor = Executors.newFixedThreadPool(poolSize);
    priorityQueue = new PriorityBlockingQueue<DowloadProccess>(queueSize, priorityComparator);
    priorityJobScheduler.execute(() -> {
        while (true) {
            try {
                log.debug(priorityQueue.take().toString());
                priorityJobPoolExecutor.execute(priorityQueue.take());
            } catch (InterruptedException e) {
                break;
            }
        }
    });
}


   public void scheduleJob(DowloadProccess job) {   
       priorityQueue.add(job);   
       log.debug("Jobs in queu :: " +  priorityQueue.size());   
   }   
公共类优先级作业调度器{
Logger log=LoggerFactory.getLogger(PriorityJobScheduler.class);
私人遗嘱执行人服务优先权JobPoolExecutor;
专用ExecutorService priorityJobScheduler=
Executors.newSingleThreadExecutor();
private PriorityBlockingQueue priorityQueue;
public PriorityJobScheduler(整数池大小、整数队列大小){
Comparator priorityComparator=Comparator.comparingInt(DowLoadProcess::getJobPriority).reversed();
priorityJobPoolExecutor=Executors.newFixedThreadPool(池大小);
priorityQueue=新的PriorityBlockingQueue(queueSize,priorityComparator);
priorityJobScheduler.execute(()->{
while(true){
试一试{
log.debug(priorityQueue.take().toString());
priorityjobboolexecutor.execute(priorityQueue.take());
}捕捉(中断异常e){
打破
}
}
});
}
public void scheduleJob(dowLoadProcess作业){
priorityQueue.add(作业);
debug(“queu中的作业::”+priorityQueue.size());
}   
}

我的控制器

@RestController
   public class ZcrController {
    private static int POOL_SIZE = 1;
    private static int QUEUE_SIZE = 100;
    PriorityJobScheduler pjs;
    
    
    @PostConstruct
    public void init() {
         pjs = new PriorityJobScheduler(POOL_SIZE, QUEUE_SIZE);
    }
    
    @GetMapping("/zcr/run")
    public List<Map<String,Object>>  exicuteCRTask(@RequestParam(required = false) String agentId,@RequestParam(required = false) String callCenterId,
            @RequestParam(required = false) String clientId,@RequestParam(required = false) String skillId,
            @RequestParam(required = false) String interval,@RequestParam("callRecordingId") String callRecordingId,@RequestParam(required = false) String type, @RequestParam(required = false) String customReport,@RequestParam(required = false) boolean ivrAcd,
            @RequestParam(required = false) String endDate, @RequestParam(required = false) String startDate,
            @RequestParam(required = false) String startTime, @RequestParam(required = false) String endTime) {
        ITxn txn = new TxnToken();
        List<Map<String,Object>> listCDRDetail = dao.getIvrRecords(txn, params,dbParam,type);
        log.debug("CDR bean size::" +listCDRDetail.size());
      
        // Here I am passing of instance of that class.
        // And on each new request i am getting a new instance pjs.
        taskExecutor.runZcrJob(pjs, dbParam, listCDRDetail, type, txn);
        return listCDRDetail;
        
    }   
@RestController
公共类ZRCC控制器{
私有静态int池_SIZE=1;
私有静态int队列_SIZE=100;
优先作业调度程序pjs;
@施工后
公共void init(){
pjs=新的优先级作业调度程序(池大小、队列大小);
}
@GetMapping(“/zcr/run”)
public List exicutecrask(@RequestParam(required=false)String agentId,@RequestParam(required=false)String callCenterId,
@RequestParam(required=false)字符串clientId、@RequestParam(required=false)字符串skillId、,
@RequestParam(required=false)字符串间隔、@RequestParam(“callRecordingId”)字符串callRecordingId、@RequestParam(required=false)字符串类型、@RequestParam(required=false)字符串自定义报告、@RequestParam(required=false)布尔ivrAcd、,
@RequestParam(required=false)字符串endDate、@RequestParam(required=false)字符串startDate、,
@RequestParam(required=false)字符串开始时间,@RequestParam(required=false)字符串结束时间){
ITxn txn=新的TxnToken();
List listCDRDetail=dao.getIvrRecords(txn,params,dbParam,type);
debug(“cdrbeansize::”+listCDRDetail.size());
//在这里,我将传递该类的实例。
//在每一个新的请求中,我都会得到一个新的pjs实例。
runZcrJob(pjs,dbParam,listCDRDetail,type,txn);
返回列表详细信息;
}   

您可以在Spring容器中创建bean

@Configuration
class JobSchedulerConfig {
    private static int POOL_SIZE = 1;
    private static int QUEUE_SIZE = 100;

    @Bean
    public PriorityJobScheduler createJobScheduler() {
         return new PriorityJobScheduler(POOL_SIZE, QUEUE_SIZE);
    }
}
然后将这个bean注入Rest控制器

@RestController
public class ZcrController {

   private final PriorityJobScheduler priorityJobScheduler;

   @Autowired // kept it for readability
   public ZcrController(PriorityJobScheduler priorityJobScheduler) {
      this.priorityJobScheduler = priorityJobScheduler;
   }

   ...
}

通过让spring注入正确配置的
PriorityJobScheduler
而不是自己使用
new
。@luk2302感谢您的回复。您能分享一个代码示例吗?如何使用构造函数参数创建PriorityJobScheduler对象一次,并将其用于所有请求?public void scheduleJob(DowLoadProcess job){priorityQueue.add(job);log.debug(“queu中的作业::”+priorityQueue.size());}通过调用上述方法,我在priorityQueue中添加了一个新作业,因此在每个请求中添加新作业时,priorityQueue的每个请求大小都会增加一个。但问题是在新请求中,我只使用一个条目获得新priorityQuery。注意:最好将
池大小
队列大小
tants,可配置属性,如
@Value(${scheduler.pool size}”)private String poolSize;
(队列大小相同)我刚刚尝试了这个,我仍然在每个requestpublic void scheduleJob(DowloadProccess job){priorityQueue.add(job);log.debug(“queu中的作业:“+priorityQueue.size());}通过调用上述方法,我在priorityQueue中添加了一个新作业,因此在每个请求中添加新作业时,priorityQueue的每个请求的大小都会增加一个。但问题是在新请求中,我只会得到一个条目的新priorityQuery。@RahulRai只要向priorityQueue添加一个对象,
while(true){
将删除它。仅为了调试,请尝试将
take()
替换为
poll()
,您将看到实际大小。使用poll()方法具有相同的结果我更改了此特定任务的方法(问题)