Java Web 项目学习(一) Spring 入门

Spring 全家桶

https://spring.io/

  • Spring Framework
  • Spring Boot
  • Spring Cloud  (微服务)
  • Spring Cloud Data Flow    (数据集成)

 

 

Spring Framework

  • Spring Core
    • IoC 面向对象、AOP  面向切面编程-----(用来管理对象bean的一种思想)
  • Spring Data Access 
    • Transactions、Spring MyBatis
  • Web Servlet 
    • Spring MVC
  • Integration
    • Email、Scheduling、AMQP、Security

 

Spring  IoC

  • Inversion of Control   控制反转,一种面向对象的编程的设计思想   (减少对象之间的耦合度)eg  : 自己管理对象  a.set(b)  建立对象a,b之间的关系 。耦合度高
  • Dependency Injection   依赖注入,IoC的实现方式
  • IoC Container     IoC容器,实现依赖注入的关键,本质是一个工厂

 

 

在CommunityApplication.java 中SpringApplication.run(CommunityApplication.class, args);  会自动创建容器。
package com.myproject.community;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class CommunityApplication {

    public static void main(String[] args) {
        //自动创建Spring容器,扫描配置类和其子类的包会被扫描到。
        //需要写注解才能被扫描   4个
        // @Service        业务
        // @Component    通用的
        // @Repository    数据库访问
        // @Controller    处理请求
        SpringApplication.run(CommunityApplication.class, args);
    }

}

 如果其他类需要获得容器,只需要implement ApplicationContextAware 接口并且重写set方法。

假设有一个AlphaDao 接口,AlphaDaoHibernateImpl (类内注解 @Repository("alphaHibernate") 起别名)和  AlphaDaoMyBatisImpl (默认优先级较高,类内注解 @Primary 实现)都是其具体实现。

默认调用时,会调用优先级高的,但也指定调用 applicationContext.getBean("alphaHibernate",AlphaDao.class); 

AlphaDao 

package com.myproject.community.dao;

public interface AlphaDao {
    String select();
}
View Code

AlphaDaoHibernateImpl 

package com.myproject.community.dao;

import org.springframework.stereotype.Repository;

@Repository("alphaHibernate")  //访问数据库使用 Repository  ,获取bean并自动装配
public class AlphaDaoHibernateImpl  implements  AlphaDao{

    @Override
    public String select() {
        return "Hibernate";
    }
}
View Code

AlphaDaoMyBatisImpl 

package com.myproject.community.dao;

import org.springframework.context.annotation.Primary;
import org.springframework.stereotype.Repository;

@Repository
@Primary  //拥有更高优先级,优先装配

public class AlphaDaoMyBatisImpl implements  AlphaDao{
    @Override
    public String select() {
        return "MyBatis";
    }
}
View Code

AlphaService

 

@Service
//@Scope("prototype")               //默认是单例@Scope("singleton"),初始化一个对象
public class AlphaService {

    @Autowired
    private AlphaDao alphaDao;

    public AlphaService(){
        System.out.println("实例化/构造AlphaService");
    }

    @PostConstruct //让容器在合适的时候调用这个方法,这个方法会在构造器之后调用
    public void init(){
        System.out.println("初始化AlphaService");
    }

    @PreDestroy     //在销毁对象之前调用
    public void destory(){
        System.out.println("销毁 AlphaService");
    }

    public String find(){
       return alphaDao.select();
    }
}
View Code

 

 

 

 

测试代码    分主动获取和依赖注入。

package com.myproject.community;

import com.myproject.community.dao.AlphaDao;
import com.myproject.community.service.AlphaService;
import org.junit.jupiter.api.Test;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;
import org.springframework.test.context.ContextConfiguration;

import java.text.SimpleDateFormat;
import java.util.Date;


@SpringBootTest

@ContextConfiguration (classes = CommunityApplication.class)    //保证测试类的配置类和正式环境是一样的
    //Ioc 是Spring 容器,容器是自动被创建的,如何得到这个容器呢?
        // 想要获得容器的类   实现ApplicationContextAware接口,并且实现set方法 ,
        // ApplicationContext、继承于HierarchicalBeanFactory继承于BeanFactory---Spring容器的顶层接口,
        // 子接口比父接口扩展了更多的方法

class CommunityApplicationTests implements ApplicationContextAware {
    private  ApplicationContext    applicationContext;

    @Override
    public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
        this.applicationContext = applicationContext;
    }


    //—————————————————————————————主动获取的方式————————————————————————————————————————
    @Test
    void testApplicationContext() {
        System.out.println(applicationContext);
        // 使用这个容器管理 bean
        AlphaDao  alphaDao = applicationContext.getBean(AlphaDao.class);
        System.out.println(alphaDao.select());

        //强制获取
        alphaDao = applicationContext.getBean("alphaHibernate",AlphaDao.class);
        System.out.println(alphaDao.select());


    }


    @Test    //测试ApplicationContext  对于对象的初始化和销毁
    void testBeanManage(){
        AlphaService alphaService = applicationContext.getBean(AlphaService.class);
        System.out.println(alphaService);

        alphaService = applicationContext.getBean(AlphaService.class);
        System.out.println(alphaService);
        //被Spring容器管理的bean默认是单例的,只被实例化一次.通常情况下都是单例的。
    }

    @Test    //测试ApplicationContext  对于对象的初始化和销毁
    void testBeanConfig(){
        SimpleDateFormat simpleDateFormat = applicationContext.getBean(SimpleDateFormat.class);
        System.out.println(simpleDateFormat.format(new Date()));
    }
    

    //—————————————————————————————依赖注入———————————————————————————————————————
    //依赖注解可以通过  构造器,set方法注入,但是通常加在属性之前,直接注入给属性
    @Autowired
    @Qualifier("alphaHibernate")
    private AlphaDao alphaDao;
    @Autowired
    private SimpleDateFormat simpleDateFormat;
    @Autowired
    private AlphaService alphaService;
    @Test
    public void testDI(){
        System.out.println(alphaDao);
        System.out.println(simpleDateFormat.format(new Date()));
        System.out.println(alphaService);

    }
    


}
View Code

 依赖注入 @Autowired 

获取指定名称AAA的   @Qualifier("AAA") 

 

 

 

 

主动获取 

被Spring容器管理的bean默认是单例的,只被实例化一次(打印输出的地址相同),多例需要在对应Service中使用 @Scope("prototype")  通常情况下都是单例的。

使用这个容器管理 bean,默认获取优先级高的,也可以强制获取。

 

 

自定义Bean(AlphaConfig )

simpleDateFormat 方法名就是 Bean的名字
@Configuration 注解表示这个是配置类,不是一个普通的类
package com.myproject.community.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.text.SimpleDateFormat;

@Configuration   //注解表示这个是配置类,不是一个普通的类
public class AlphaConfig {

    //因为项目中时间格式基本都一样,所以装配到Bean中可以反复用,即方法返回的对象将会被装配到容器中
    //simpleDateFormat 方法名就是 Bean的名字
    @Bean
    public SimpleDateFormat simpleDateFormat(){
        return  new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    }
}
View Code

 

  

 

 

 

项目结构

 

 开发过程之中,controller处理浏览器的请求,过程中会调用业务组件service处理业务,业务组件会调用dao去访问数据,相互依赖。 他们的依赖关系就可以用依赖注入的方式实现。

AlphaController

package com.myproject.community.controller;


import com.myproject.community.service.AlphaService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.stereotype.Repository;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

@Controller
@RequestMapping("/alpha")   //给这个类取一个名
public class AlphaController {
    @Autowired
    private AlphaService alphaService;  //依赖注入

    @RequestMapping("/hello")   ///给这个方法取一个名
    @ResponseBody    // 如果不加,默认是返回一个网页,加上默认返回字符串
    public String sayHello (){
        return "Hello Spring Boot.";
    }

    @RequestMapping("/data")
    @ResponseBody
    public String getData(){
        return alphaService.find();
    }
}
View Code

AlphaService
package com.myproject.community.service;

import com.myproject.community.dao.AlphaDao;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Scope;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import javax.swing.*;

@Service
//@Scope("prototype")
public class AlphaService {

    @Autowired
    private AlphaDao alphaDao;

    public AlphaService(){
        System.out.println("实例化/构造AlphaService");
    }

    @PostConstruct //让容器在合适的时候调用这个方法,这个方法会在构造器之后调用
    public void init(){
        System.out.println("初始化AlphaService");
    }

    @PreDestroy     //在销毁对象之前调用
    public void destory(){
        System.out.println("销毁 AlphaService");
    }

    public String find(){
       return alphaDao.select();
    }
}
View Code
AlphaDao
package com.myproject.community.dao;

public interface AlphaDao {
    String select();
}
View Code

 

 


 

本期代码版本 

链接:https://pan.baidu.com/s/1XZXMUhpoNvPLRIYVOzaggA
提取码:tqra
复制这段内容后打开百度网盘手机App,操作更方便哦

 
posted @ 2021-03-29 10:09  白清欢  阅读(125)  评论(0编辑  收藏  举报