SpringCloud


1.認識微服務

隨着互聯網行業的發展,對服務的要求也越來越高,服務架構也從單體架構逐漸演變為現在流行的微服務架構。這些架構之間有怎樣的差別呢?了解微服務架構的優缺點

1.1.單體架構

單體架構:將業務的所有功能集中在一個項目中開發,打成一個包部署。

 

 

單體架構的優缺點如下:

優點:

  • 架構簡單

  • 部署成本低

缺點:

  • 耦合度高(維護困難、升級困難)

1.2.分布式架構

分布式架構:根據業務功能對系統做拆分,每個業務功能模塊作為獨立項目開發,稱為一個服務。

 

 

分布式架構的優缺點:

優點:

  • 降低服務耦合

  • 有利於服務升級和拓展

缺點:

  • 服務調用關系錯綜復雜

分布式架構雖然降低了服務耦合,但是服務拆分時也有很多問題需要思考:

  • 服務拆分的粒度如何界定?

  • 服務之間如何調用?

  • 服務的調用關系如何管理?

人們需要制定一套行之有效的標准來約束分布式架構。

1.3.微服務

微服務的架構特征:

  • 單一職責:微服務拆分粒度更小,每一個服務都對應唯一的業務能力,做到單一職責

  • 自治:團隊獨立、技術獨立、數據獨立,獨立部署和交付

  • 面向服務:服務提供統一標准的接口,與語言和技術無關

  • 隔離性強:服務調用做好隔離、容錯、降級,避免出現級聯問題

 

 

微服務的上述特性其實是在給分布式架構制定一個標准,進一步降低服務之間的耦合度,提供服務的獨立性和靈活性。做到高內聚,低耦合。

因此,可以認為微服務是一種經過良好架構設計的分布式架構方案

但方案該怎么落地?選用什么樣的技術棧?全球的互聯網公司都在積極嘗試自己的微服務落地方案。

其中在Java領域最引人注目的就是SpringCloud提供的方案了。

1.4.SpringCloud

SpringCloud是目前國內使用最廣泛的微服務框架。官網地址:https://spring.io/projects/spring-cloud

SpringCloud集成了各種微服務功能組件,並基於SpringBoot實現了這些組件的自動裝配,從而提供了良好的開箱即用體驗。

其中常見的組件包括:

 

 另外,SpringCloud底層是依賴於SpringBoot的,並且有版本的兼容關系,如下:

 

 

1.5.總結

  • 單體架構:簡單方便,高度耦合,擴展性差,適合小型項目。例如:學生管理系統

  • 分布式架構:松耦合,擴展性好,但架構復雜,難度大。適合大型互聯網項目,例如:京東、淘寶

  • 微服務:一種良好的分布式架構方案

    ①優點:拆分粒度更小、服務更獨立、耦合度更低

    ②缺點:架構非常復雜,運維、監控、部署難度提高

  • SpringCloud是微服務架構的一站式解決方案,集成了各種優秀微服務功能組件

2.服務拆分和遠程調用

任何分布式架構都離不開服務的拆分,微服務也是一樣。

2.1.服務拆分原則

這里我總結了微服務拆分時的幾個原則:

  • 不同微服務,不要重復開發相同業務

  • 微服務數據獨立,不要訪問其它微服務的數據庫

  • 微服務可以將自己的業務暴露為接口,供其它微服務調用

 

 

2.2.服務拆分示例

資料中的微服務cloud-demo為例,其結構如下:

 

 

cloud-demo:父工程,管理依賴

  • order-service:訂單微服務,負責訂單相關業務

  • user-service:用戶微服務,負責用戶相關業務

要求:

  • 訂單微服務和用戶微服務都必須有各自的數據庫,相互獨立

  • 訂單服務和用戶服務都對外暴露Restful的接口

  • 訂單服務如果需要查詢用戶信息,只能調用用戶服務的Restful接口,不能查詢用戶數據庫

 

/*
 Navicat Premium Data Transfer

 Source Server         : local
 Source Server Type    : MySQL
 Source Server Version : 50622
 Source Host           : localhost:3306
 Source Schema         : heima

 Target Server Type    : MySQL
 Target Server Version : 50622
 File Encoding         : 65001

 Date: 01/04/2021 14:57:18
*/

SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;

-- ----------------------------
-- Table structure for tb_order
-- ----------------------------
DROP TABLE IF EXISTS `tb_order`;
CREATE TABLE `tb_order`  (
  `id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '訂單id',
  `user_id` bigint(20) NOT NULL COMMENT '用戶id',
  `name` varchar(100) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '商品名稱',
  `price` bigint(20) NOT NULL COMMENT '商品價格',
  `num` int(10) NULL DEFAULT 0 COMMENT '商品數量',
  PRIMARY KEY (`id`) USING BTREE,
  UNIQUE INDEX `username`(`name`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 109 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Compact;

-- ----------------------------
-- Records of tb_order
-- ----------------------------
INSERT INTO `tb_order` VALUES (101, 1, 'Apple 蘋果 iPhone 12 ', 699900, 1);
INSERT INTO `tb_order` VALUES (102, 2, '雅迪 yadea 新國標電動車', 209900, 1);
INSERT INTO `tb_order` VALUES (103, 3, '駱駝(CAMEL)休閑運動鞋女', 43900, 1);
INSERT INTO `tb_order` VALUES (104, 4, '小米10 雙模5G 驍龍865', 359900, 1);
INSERT INTO `tb_order` VALUES (105, 5, 'OPPO Reno3 Pro 雙模5G 視頻雙防抖', 299900, 1);
INSERT INTO `tb_order` VALUES (106, 6, '美的(Midea) 新能效 冷靜星II ', 544900, 1);
INSERT INTO `tb_order` VALUES (107, 2, '西昊/SIHOO 人體工學電腦椅子', 79900, 1);
INSERT INTO `tb_order` VALUES (108, 3, '梵班(FAMDBANN)休閑男鞋', 31900, 1);

SET FOREIGN_KEY_CHECKS = 1;

 

/*
 Navicat Premium Data Transfer

 Source Server         : local
 Source Server Type    : MySQL
 Source Server Version : 50622
 Source Host           : localhost:3306
 Source Schema         : heima

 Target Server Type    : MySQL
 Target Server Version : 50622
 File Encoding         : 65001

 Date: 01/04/2021 14:57:18
*/

SET NAMES utf8mb4;
SET FOREIGN_KEY_CHECKS = 0;

-- ----------------------------
-- Table structure for tb_user
-- ----------------------------
DROP TABLE IF EXISTS `tb_user`;
CREATE TABLE `tb_user`  (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `username` varchar(100) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '收件人',
  `address` varchar(255) CHARACTER SET utf8 COLLATE utf8_general_ci NULL DEFAULT NULL COMMENT '地址',
  PRIMARY KEY (`id`) USING BTREE,
  UNIQUE INDEX `username`(`username`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 109 CHARACTER SET = utf8 COLLATE = utf8_general_ci ROW_FORMAT = Compact;

-- ----------------------------
-- Records of tb_user
-- ----------------------------
INSERT INTO `tb_user` VALUES (1, '柳岩', '湖南省衡陽市');
INSERT INTO `tb_user` VALUES (2, '文二狗', '陝西省西安市');
INSERT INTO `tb_user` VALUES (3, '華沉魚', '湖北省十堰市');
INSERT INTO `tb_user` VALUES (4, '張必沉', '天津市');
INSERT INTO `tb_user` VALUES (5, '鄭爽爽', '遼寧省沈陽市大東區');
INSERT INTO `tb_user` VALUES (6, '范兵兵', '山東省青島市');

SET FOREIGN_KEY_CHECKS = 1;

 

2.2.1.導入Sql語句

cloud-user表中初始數據如下:

 

 cloud-order表中初始數據如下:

 

 

 cloud-order表中持有cloud-user表中的id字段。

 

2.2.2.使用demo工程

項目結構如下:

 

 

導入后,會在IDEA右下角出現彈窗:

 

 點擊彈窗,然后按下圖選擇:

 

 會出現這樣的菜單:

 

 配置下項目使用的JDK:

 

 

 

2.3.實現遠程調用案例

在order-service服務中,有一個根據id查詢訂單的接口:

 

 根據id查詢訂單,返回值是Order對象,如圖:

 其中的user為null

 

在user-service中有一個根據id查詢用戶的接口:

 

 查詢的結果如圖

2.3.1.案例需求:

修改order-service中的根據id查詢訂單業務,要求在查詢訂單的同時,根據訂單中包含的userId查詢出用戶信息,一起返回。

 

 因此,我們需要在order-service中 向user-service發起一個http的請求,調用http://localhost:8081/user/{userId}這個接口。

大概的步驟是這樣的:

  • 注冊一個RestTemplate的實例到Spring容器

  • 修改order-service服務中的OrderService類中的queryOrderById方法,根據Order對象中的userId查詢User

  • 將查詢的User填充到Order對象,一起返回

2.3.2.注冊RestTemplate

首先,我們在order-service服務中的OrderApplication啟動類中,注冊RestTemplate實例:

package cn.itcast.order;

import org.mybatis.spring.annotation.MapperScan;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.annotation.Bean;
import org.springframework.web.client.RestTemplate;

@MapperScan("cn.itcast.order.mapper")
@SpringBootApplication
public class OrderApplication {

    public static void main(String[] args) {
        SpringApplication.run(OrderApplication.class, args);
    }

    @Bean
    public RestTemplate restTemplate() {
        return new RestTemplate();
    }
}

2.3.3.實現遠程調用

修改order-service服務中的cn.itcast.order.service包下的OrderService類中的queryOrderById方法:

 這里我們的url路徑是寫死的,這樣當user配置文件被修改時,我們就需要修改Order中的代碼,很不方便。這是我們就要了解注冊中心的內容了。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM