06、SpringBoot —— Service层

SpringBoot —— Service层

  • 概念

    • 在实际开发中,Service层主要负责业务模块的逻辑应用设计。首先设计接口,再设计接口的实现类
    • Service层用于封装项目中一些通用的业务逻辑,有利于业务逻辑的独立性和重复利用性
  • Service层与@Service注解

    • 写在前面
      • 详细讲解Service层之前,我们先来简单说一下后端通用的一个服务架构“MVC”模型
      • M指的是Model,意为“模型”,指的是数据库在服务架构内的映射,用于访问和操作数据库中的数据。在Java中,我们一般使用Dao层表示
      • V指的是View,意为“视图”,在之前前后端不分离的情况下,页面由模板引擎构建好(实际上就是去自动化的插入代码),再返回给前端渲染。前后端分离流行以后,后端基本上只负责数据的处理,以及将处理后的数据返回即可。在Java中,我们一般用Service层表示
      • C指的是Controller,意为“控制器”,负责转发请求到Service层
      • 综上所述,后端返回数据的一般步骤:
        • Dao层访问数据库,拿到对应的数据或执行相关的操作
        • Service层拿到Dao层的结果进行处理
        • Controller层返回数据
    • @Service注解
      • Service层的实现类须使用@Service注解予以标注,被@Service标注的类称为服务类
      • @Service注解属于Component组件,可以被扫描器扫描到
  • Service层的实现过程

    • 大多数的SpringBoot项目采用接口模式实现Service层

    • 步骤

      • 定义一个Service层的接口,在这个接口中定义用于传递和处理数据的方法
      • 定义一个Service层的接口的实现类,使用@Service注解标注
        • 这个实现类的作用有两个:
          • 实现Service层的接口中的业务方法
          • 执行Dao层中用于访问、处理数据的操作
      • 在服务类的对象被自动地创建并注册成Bean之后,其他Component组件即可直接注入这个Bean
    • 示例

      ProductService接口:

      public interface ProductService {
          String getName();
      }

      ProductServiceImpl实现类:

      @Service
      public class ProductServiceImpl implements ProductService{
      
          @Override
          public String getName() {
              return "kaiven";
          }
      }

      TestController控制器:

      @RestController
      public class TestController {
          @Autowired
          ProductServiceImpl productService;
          @RequestMapping("/test")
          public String test() {
              return productService.getName();
          }
      }
  • 同时存在多个实现类的情况

    • 概念

      • 实际的开发过程中,一个Service层的接口可能会针对多种业务场景而存在多个实现类
    • 按照实现类的服务名称映射服务类对象

      • 概念

        • 被@Service标注的实现类被称作服务类,这个实现类的对象被称作服务类的对象。服务类的对象会被自动创建,并注册为Bean,而Bean的名称就是类名的首字母小写版
        • 其他Component组件即可通过指定的Bean的名称的方式注入与服务类对象对应的Bean
      • 示例

        server.TranslateService:

        public interface TranslateService {
            String translate(String word);
        }

        server.impl.English2ChineseImpl:

        @Service
        public class English2ChineseImpl implements TranslateService {
            @Override
            public String translate(String word) {
                if("hello".equalsIgnoreCase(word)) return "你好";
                return "抱歉,我还没有学习过这个!";
            }
        }

        server.impl.French2ChineseImpl:

        @Service
        public class French2ChineseImpl implements TranslateService {
        
            @Override
            public String translate(String word) {
                if("Allô?".equalsIgnoreCase(word)) return "你好";
                return "我还没有学过这个嘞!";
            }
        }

        controller.TranslateController:

        @RestController
        public class TranslateController {
            @Autowired
            TranslateService english2ChineseImpl; // 英译汉
        
            @Autowired
            TranslateService french2ChineseImpl; // 法译汉
        
            @RequestMapping("/english")
            public String english(String word) {
                return english2ChineseImpl.translate(word);
            }
        
            @RequestMapping("/french")
            public String french(String word) {
                return french2ChineseImpl.translate(word);
            }
        }
    • 按照@Service的value属性映射服务类的对象

      • 概念

        • @Service注解中,只包含一个value属性,value属性是@Service注解的默认属性
        • 为value属性赋值后,就相当于在创建与服务类的对象对应的Bean时确定了Bean的名称
      • 示例

        service.TranscriptsService:

        public interface TranscriptsService {
            void sort(List<Double> score);
        }

        service.impl.ASCTranscriptsServiceImpl:

        @Service("asc")
        public class ASCTranscriptsServiceImpl implements TranscriptsService {
        
            @Override
            public void sort(List<Double> score) {
                Collections.sort(score);
            }
        }

        service.impl.DESCTranscriptsServiceImpl:

        @Service("desc")
        public class DESCTranscriptsServiceImpl implements TranscriptsService {
        
            @Override
            public void sort(List<Double> score) {
                score.sort(new Comparator<Double>() {
                    @Override
                    public int compare(Double o1, Double o2) {
                        return o2.compareTo(o1);
                    }
                });
            }
        }

        controller.TranscriptsController:

        @RestController
        public class TranscriptsController {
            @Autowired
            TranscriptsService asc;
        
            @Autowired
            TranscriptsService desc;
        
            @RequestMapping("/asc")
            public String asc(Double a, Double b, Double c) {
                List<Double> list = new ArrayList<Double>(List.of(a,b,c));
                asc.sort(list);
                StringBuilder sb = new StringBuilder();
                list.forEach(e -> sb.append(e.toString()).append("\n"));
                return sb.toString();
            }
        
            @RequestMapping("/desc")
            public String desc(Double a, Double b, Double c) {
                List<Double> list = new ArrayList<>(List.of(a,b,c));
                desc.sort(list);
                StringBuilder sb = new StringBuilder();
                list.forEach(e -> sb.append(e.toString()).append("\n"));
                return sb.toString();
            }
        }
  • 不采用接口模式的服务类

    • 概念

      • 实际开发中,一些功非常简单的服务可以不采用接口模式,直接创建服务类病使用@Service注解标注即可
    • 示例

      service.VerifyService:

      @Service
      public class VerifyService {
          public boolean chineseName(String name) {
              String match = "^[\\u4E00-\\u9FA5]{2,4}$";
              return name != null && name.matches(match);
          }
      }

      controller.VerifyController:

      @RestController
      public class VerifyController {
          @Autowired
          VerifyService verifyService;
      
          @RequestMapping("/verify/name")
          public String verifyName(String name){
              return verifyService.chineseName(name) ? "是中文名" : "不是中文名";
          }
      }
  • @Service和@Repository的联系与区别

    • 联系
      • 两个注解都被@Component注解标注,都可以被扫描器扫描到
    • 区别
      • 其实区别不大,主要是为了方便开发人员从字面上就能够判断出某个服务是业务服务,还是数据库服务
      • @Service标注Service层,@Repository标注Dao层
  • 14
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,关于在 Spring Boot 中插入一条数据,我们可以按照以下步骤进行操作: 1. 首先,我们需要在 pom.xml 中引入 Spring Boot 的相关依赖,包括 Spring Boot Starter 和 Spring Boot Starter Data JPA,如下所示: ```xml <dependencies> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-data-jpa</artifactId> </dependency> </dependencies> ``` 2. 在 application.properties 或 application.yml 配置文件中,配置数据库连接信息,例如: ```properties spring.datasource.url=jdbc:mysql://localhost:3306/test spring.datasource.username=root spring.datasource.password=123456 spring.datasource.driver-class-name=com.mysql.jdbc.Driver ``` 3. 创建一个实体类,用于映射数据库中的表结构,例如: ```java @Entity @Table(name = "user") public class User { @Id @GeneratedValue(strategy = GenerationType.IDENTITY) private Long id; private String name; private Integer age; // 省略 getter 和 setter 方法 } ``` 4. 创建一个 Repository 接口,用于操作数据库,例如: ```java @Repository public interface UserRepository extends JpaRepository<User, Long> { } ``` 5. 在业务逻辑中调用 UserRepository 的 save() 方法即可插入一条数据,例如: ```java @Service public class UserService { @Autowired private UserRepository userRepository; public void addUser() { User user = new User(); user.setName("张三"); user.setAge(20); userRepository.save(user); } } ``` 以上就是在 Spring Boot 中插入一条数据的详细步骤。需要注意的是,在实际开发中,我们需要根据具体的业务需求进行适当的调整,例如增加数据校验、事务管理等。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值