微服务的实现
实体类:#
在shop_service_common中创建 com.yyj.entity.Product实体类,并配置

package com.yyj.entity; import lombok.Data; import javax.persistence.Entity; import javax.persistence.Id; import javax.persistence.Table; import java.math.BigDecimal; @Entity @Table(name="tb_product") @Data public class Product { @Id private Long id; private String productName; private Integer status; private BigDecimal price; private String productDesc; private String caption; private Integer inventory; }
这里使用了lombok简化实体类的开发,Lombok能以简单的注解形式来简化java代码,提高开发人员的开发效率
dao层接口:#
在shop_service_product中创建 com.yyj.product.dao.ProductDao 接口
package com.yyj.product.dao; import com.yyj.entity.Product; import org.springframework.data.jpa.repository.JpaRepository; import org.springframework.data.jpa.repository.JpaSpecificationExecutor; public interface ProductDao extends JpaRepository<Product,Long>, JpaSpecificationExecutor<Product> { }
service层:#
在shop_service_product中创建 com.yyj.product.service.ProductService

package com.yyj.product.service;
import com.yyj.entity.Product;
import java.util.List;
public interface ProductService {
//根据id查询
Product findById(Long id);
//查询全部
List findAll();
//保存
void save(Product product);
//更新
void update(Product product);
//删除
void delete(Long id);
}
在shop_service_product中创建 com.yyj.product.service.impl.ProductServiceImpl 实现类

package com.yyj.product.service.impl;
import com.yyj.entity.Product;
import com.yyj.product.dao.ProductDao;
import com.yyj.product.service.ProductService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import java.util.List;
@Service
public class ProductServiceImpl implements ProductService {
@Autowired
private ProductDao productDao;
@Override
public Product findById(Long id) {
return productDao.findById(id).get();
}
@Override
public List findAll() {
return productDao.findAll();
}
@Override
public void save(Product product) {
productDao.save(product);
}
@Override
public void update(Product product) {
productDao.save(product);
}
@Override
public void delete(Long id) {
productDao.deleteById(id);
}
}
controller层:#
在shop_service_product中创建 com.yyj.product.controller.ProductController

package com.yyj.product.controller;
import com.yyj.entity.Product;
import com.yyj.product.service.ProductService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import java.util.List;
@RestController
@RequestMapping("/product")
public class ProductController {
@Autowired
private ProductService productService;
@GetMapping
public List findAll() {
return productService.findAll();
}
@GetMapping("/{id}")
public Product findById(@PathVariable Long id) {
return productService.findById(id);
}
@PostMapping
public String save(@RequestBody Product product) {
productService.save(product);
return "保存成功";
}
@PutMapping("/{id}")
public String update(@RequestBody Product product) {
productService.update(product);
return "修改成功";
}
@DeleteMapping("/{id}")
public String delete(Long id) {
productService.delete(id);
return "删除成功";
}
}
controller中使用的@GetMapping是一个组合注解,相当与@RequestMapping(method="get")。
类似的注解还有@PostMapping,@PutMapping,@DeleteMapping
配置启动类#
在shop_service_product中创建 com.yyj.product.ProductApplication 启动类
package com.yyj.product;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.domain.EntityScan;
@SpringBootApplication(scanBasePackages = {"com.yyj.product"})
@EntityScan("com.yyj.entity")
public class ProductApplication {
public static void main(String[] args) {
SpringApplication.run(ProductApplication.class,args);
}
}
配置application.yml文件#

server: port: 9002 spring: application: name: shop-service-product datasource: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://localhost:3306/shop?useUnicode=true&characterEncoding=utf8&serverTimezone=UTC username: root password: 123 jpa: database: MySQL show-sql: true open-in-view: true
用户和订单微服务与上述微服务类似,根据商品微服务进行编写#
服务调用#
前文已经编写了三个基础的微服务,在用户下单时需要调用商品微服务获取商品数据。那应该怎么做呢?显然,商品微服务提供了供人调用的HTTP接口。所以可以再下定单的时候使用http请求的相关工具类完成,如常见的HttpClient,OkHttp,当然也可以使用Spring提供的RestTemplate
RestTemplate介绍#
Spring框架提供的RestTemplate类可用于在应用中调用rest服务,它简化了与http服务的通信方式,统一了RESTful的标准,封装了http链接, 我们只需要传入url及返回值类型即可。相较于之前常用的HttpClient,RestTemplate是一种更优雅的调用RESTful服务的方式。
在Spring应用程序中访问第三方REST服务与使用Spring RestTemplate类有关。RestTemplate类的设计原则与许多其他Spring 模板类(例如JdbcTemplate、JmsTemplate)相同,为执行复杂任务提供了一种具有默认行为的简化方法。
RestTemplate默认依赖JDK提供http连接的能力(HttpURLConnection),如果有需要的话也可以通过setRequestFactory方法替换为例如 Apache HttpComponents、Netty或OkHttp等其它HTTP library。考虑到RestTemplate类是为调用REST服务而设计的,因此它的主要方法与REST的基础紧密相连就不足为奇了,后者是HTTP协议的方法:HEAD、GET、POST、PUT、DELETE和OPTIONS。例如,RestTemplate类具有headForHeaders()、getForObject()、postForObject()、put()和delete()等方法。
RestTemplate方法介绍#
通过RestTemplate调用微服务#
(1) 在 shop_service_order工程中ProductApplication启动类 中配置RestTemplate
//配置RestTemplate交给spring管理 @Bean public RestTemplate getRestTemplate() { return new RestTemplate(); }
(2) 编写下订单方法
@PostMapping("/{id}") public String order(Integer num) { //通过restTemplate调用商品微服务 Product object = restTemplate.getForObject("http://127.0.0.1:9002/product/1", Product.class); System.out.println(object); return "操作成功"; }
硬编码存在的问题#
至此已经可以通过RestTemplate调用商品微服务的RESTFul API接口。但是我们把提供者的网络地址(ip,端口)等硬编码到了代码中,这种做法存在许多问题:
应用场景有局限
无法动态调整
那么应该怎么解决呢,就需要通过注册中心动态的对服务注册和服务发现
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列(二):开始使用ML.NET
· 记一次.NET内存居高不下排查解决与启示
· 探究高空视频全景AR技术的实现原理
· 理解Rust引用及其生命周期标识(上)
· 浏览器原生「磁吸」效果!Anchor Positioning 锚点定位神器解析
· DeepSeek 开源周回顾「GitHub 热点速览」
· 物流快递公司核心技术能力-地址解析分单基础技术分享
· .NET 10首个预览版发布:重大改进与新特性概览!
· AI与.NET技术实操系列(二):开始使用ML.NET
· .NET10 - 预览版1新功能体验(一)