Spring(三)Spring事件+计划定时任务+条件注解+SpringAware
Application Event 事件
当一个Bean处理完一个任务之后,希望另一个Bean知道并做出相应的处理,这时需要让另外一个Bean监听当前Bean所发送的事件
- 自定义事件,集成ApplicationEvent
- 自定义事件监听器,实现ApplicationListener
- 使用容器发布事件
①、自定义事件
public class DemoEvent extends ApplicationEvent{
private static final long serialVersionUID = 1L;
private String msg;
public DemoEvent(Object source,String msg){
super(source);
this.msg = msg;
}
public String getMsg(){
return msg;
}
public void setMsg(String msg){
this.msg = msg;
}
}
②、事件监听器
实现AppliationListener接口,并指定监听的事件类型DemoEvent
使用onApplicationEvent方法对消息进行接收处理
@Component
public class DemoListener implements ApplicationListener<DemoEvent>{
public void onApplicationEvent(DemoEvent event){
String msg = event.getMsg();
System.out.println("bean-demoListener接收到了bean-demoPublisher发布的消息:"+msg);
}
}
③、事件发布类
@Component
public class DemoPublisher{
@Autowired
ApplicationContext applicationContext;//注入该引用,用来发布事件
public void publish(String msg){//发布
applicationContext.publishEvent(new DemoEvent(this,msg));
}
}
④、配置类
@Configuration
@ComponentScan("com.xxx.event");
public class EventConfig{
}
⑤、运行
public class Main{
public static void main(String[] args){
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(EventConfig.class);
DemoPublisher demoPublisher = context.getBean(DemoPublisher.class);
demoPublisher.publish("hello application event");
context.close();
}
}
计划任务
①、计划任务执行类
@Service
public class ScheduleTaskService{
private static final SimpleDataFormat dateFormat = new SimpleDateFormat("HH:mm:ss");
@Scheduled(fixedRate = 5000) //每隔固定的时间执行
public void reportCurrentTime(){
System.out.println("每隔五秒执行一次"+dateFormat(new Date()))
}
@Scheduled(cron = "0 28 11 ? * *")//按照指定的每天11点28分执行
public void fixTimeExecution(){
System.out.println("在指定时间"+dateFormat.format(new Date())+"执行");
}
}
②、配置类
@Configuration
@ComponentScan("com.xxx.taskscheduler")
@EnableScheduling //开启对计划任务的支持
public class TaskSchedulerConfig{
}
③、运行
public class Main{
public static void main(String[] args){
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(TaskSchedulerConfig.class);
}
}
Java中有两种实现定时任务的方式:
- java.util包中的Timer(具体类,负责定时任务的调度和执行)和TimerTask(定时任务抽象类)
- java并发包中的ScheduledExecutorService
Timer
/**
Timer基本示例
*/
public class BasicTimer{
static class DelayTask extends TimerTask{
@Override
public void run(){
System.out.println("delayed task");
}
}
public static void main(String[] args)throws InterruptedException{
Timer timer = new Timer();
timer.schedule(new DelayTask(),1000);//1秒后运行DelayTask
Thread.sleep(2000);
timer.cancel();//取消所有定时任务
}
}
/**
Timer固定延时
*/
public class TimerFixedDelay{
static class LongRunntingTask extends TimerTask{
@Override
public void run(){
try{
Thread.sleep(5000);
}catch(InterruptedException e){
}
System.out.println("long running finished");
}
}
static class FixedDelayTask extends TimerTask{
@Override
public void run(){
System.out.println(System.currentTimeMillis());
}
}
public static void main(String[] args)throws InterruptedException{
Timer timer = new Timer();
timer.schedule(new LongRunningTask(),10);
timer.schedule(new FixedDelayTask(),100,1000);
}
}
ScheduledExecutorService接口
public class ScheduledFixedDeley{
static class LongRunningTask implements Runnable{
//同上
}
static class FixedDelayTask implements Runnable{
//同上
}
public static void main(String[] args)throws InterruptedException{
ScheduledExecutorService timer = Executors.newScheduledThreadPool(10);
}
}
条件注解@Conditional
根据满足某一个特定条件创建一个特定的Bean
①、判定条件定义
/**
判定Window的条件
*/
public class WindowsCondition implements Condition{
public boolean matches(ConditionContext context,AnnotatedTypeMetadata metadata){
return context.getEnvironment().getProperty("os.name").contains("windows");
}
}
/**
判定Linux的条件
*/
public class LinuxCondition implements Condition{
public boolean matches(ConditionContext context,AnnotatedTypeMetadata metadata){
return context.getEnvironment().getProperty("os.name").contains("Linux");
}
}
②、不同系统下Bean的类
public interface ListService{
public String showListCmd();
}
Windows下需要创建的Bean
public class WindowListService implements ListService{
@Override
public String showListCmd(){
return "dir";
}
}
Linux下需要创建的Bean
public class LinuxListService implements ListService{
@Override
public String showListCmd(){
return "ls";
}
}
③、配置类
@Configuration
public class ConditionConfig{
@Bean
@Conditional(WindowsCondition.class)
public ListService windowsListService(){
return new WindowsListService();
}
@Bean
@Conditional(LinuxCondition.class)
public ListService linuxListService(){
return new LinuxListService();
}
}
④、运行
public class Main{
public static void main(String[] args){
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(ConditionConfig.class);
ListService listService = context.getBean(ListService.class);
System.out.println(context.getEnvironment().getProperty("os.name")+"系统下的命令为:"+listService.showListCmd())
}
}
SpringAware
Spring提供的Aware接口:为了让Bean获得Spring容器服务
①、在com.xxx.aware包下新建一个test.txt,内容任意
②、实现对应的接口,获取Bean名称和资源加载服务
@Service
public class AwareService implements BeanNameAware,ResourceLoaderAware{
private String beanName;
private ResourceLoader loader;
@Override
public void setResourceLoader(ResourceLoader resourceLoader){
this.loader = resourceLoader;
}
@Override
public void setBeanName(String name){
this.beanName = name;
}
public void outputResult(){
System.out.println("Bean的名称为:" + beanName);
Resource resource = loader.getResource("classpath:com/xxx/aware/test.txt");
try{
System.out.println("ResourceLoader加载的文件内容为"+IOUtils.buString(resource.getInputStream()));
}catch(IOException e){
e.printStackTrace();
}
}
}
③、配置类
@Configuration
@ComponentScan("com.xxx.aware")
public class AwareConfig{
}
④、运行
public class Main{
public static void main(String[] args){
AnnotationConfigApplicationContext context = new AnnotationConfigApplicationContext(AwareConfig.class);
AwareServcie awareService = context.getBean(AwareService.class);
awareService.outputResult();//加载的文件内容
context.close();
}
}