微服务场景实战:基于SpringCloud Alibaba从零搭建鉴权中心服务(1)

本文涉及的产品
服务治理 MSE Sentinel/OpenSergo,Agent数量 不受限
云原生网关 MSE Higress,422元/月
注册配置 MSE Nacos/ZooKeeper,118元/月
简介: 微服务场景实战:基于SpringCloud Alibaba从零搭建鉴权中心服务(1)

鉴权中心服务

认识JWT

json web token 是一个开放的标准 ,它定义了一个种紧凑的,自包含的方式,用于作为json对象在各方之间安全的传输信息


服务器鉴权完成之后 会生成 json 对象 发送给客户端,之后客户端和服务端传输数据都需要带上这个对象,服务器完全通过这个json对象认定客户端身份,为了防止篡改数据,服务端在生成的时候都会加上签名(加密的意思),服务器不保存session数据也就是无状态,更适合实现扩展

那些环境可以考虑使用jwt呢? 用户授权 ,信息交换

JWT组成部分

Header :头部信息

Header 由两部分组成(Token类型,加密算法的名称),并且使用的是base64的编码

2.png

Payload: 我们想要传递的数据


Payload KV形式的诗数据 ,这里就是我们想要传递的信息(授权的话就是Token信息)


Signature :签名


Signature 为了得到签名 首先我们得有编码过的Header 编码过的payload 和一个密钥。签名用的算法就是header中指定的那个,之后就会对他们签名


我们需要一个签名公式


HMACSHA245(base64UrlEncode(header)+"."+base64UrlEncode(payload),secret)


产生一个签名,返回一个字符串,返回给客户端,之后客户端每次访问都要带上这个字符串,进行鉴权


JWT使用 . 号来连接 HHH.PPPP.SSSS


授权,鉴权设计

这里我们先不考虑 gateway 网关,后续会搭建,我们的重点放在中间和右边部分

2.png



鉴权部分,我们独立实现公共的工具类,为什么?以下三点


JWT本质上是通过算法算出的加密字符串,也可以通过算法反向解析出来,他不依赖任何的框架,所以这个功能有可以单独提取出来的前提

我们的电商系统包含多个微服务,很显然我们每个服务都需要鉴权,于是我们把这个方法提取出来,方便复用

高性能鉴权,为什么不在授权中心做鉴权,首先他回头过http请求等一系列操作,我们在本地只用java的话 少去了很多步骤,性能得到倍数的增长

授权编码实现

我们创建新的一个服务来编写我们的鉴权中心


e-commerce-authority-center


导入相关的依赖

    <dependencies>
        <!-- spring cloud alibaba nacos discovery 依赖 -->
        <dependency>
            <groupId>com.alibaba.cloud</groupId>
            <artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
            <version>2.2.3.RELEASE</version>
        </dependency>
        <!-- Java Persistence API, ORM 规范 -->
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-jpa</artifactId>
        </dependency>
        <!-- MySQL 驱动, 注意, 这个需要与 MySQL 版本对应 -->
        <dependency>
            <groupId>mysql</groupId>
            <artifactId>mysql-connector-java</artifactId>
            <version>8.0.12</version>
            <scope>runtime</scope>
        </dependency>
        <dependency>
            <groupId>com.hyc.ecommerce</groupId>
            <artifactId>e-commerce-mvc-config</artifactId>
            <version>1.0-SNAPSHOT</version>
        </dependency>
        <!-- zipkin = spring-cloud-starter-sleuth + spring-cloud-sleuth-zipkin-->
        <dependency>
            <groupId>org.springframework.cloud</groupId>
            <artifactId>spring-cloud-starter-zipkin</artifactId>
        </dependency>
        <dependency>
            <groupId>org.springframework.kafka</groupId>
            <artifactId>spring-kafka</artifactId>
            <version>2.5.0.RELEASE</version>
        </dependency>
        <!-- screw 生成数据库文档 -->
        <dependency>
            <groupId>org.freemarker</groupId>
            <artifactId>freemarker</artifactId>
            <version>2.3.30</version>
        </dependency>
        <dependency>
            <groupId>cn.smallbun.screw</groupId>
            <artifactId>screw-core</artifactId>
            <version>1.0.3</version>
        </dependency>
    </dependencies>

导入好依赖之后我们 编写对应的配置,如注册到naocs 加入adminserver的监管,配置数据源等 这里我们使用jpa 来做orm


配置编写

server:
  port: 7000
  servlet:
    context-path: /ecommerce-authority-center
spring:
  application:
    name: e-commerce-authority-center
  cloud:
    nacos:
      discovery:
        enabled: true # 如果不想使用 Nacos 进行服务注册和发现, 设置为 false 即可
        server-addr: 127.0.0.1:8848 # Nacos 服务器地址
        # server-addr: 127.0.0.1:8848,127.0.0.1:8849,127.0.0.1:8850 # Nacos 服务器地址
        namespace: 1bc13fd5-843b-4ac0-aa55-695c25bc0ac6
        metadata:
          management:
            context-path: ${server.servlet.context-path}/actuator
  jpa:
    show-sql: true
    hibernate:
      ddl-auto: none
    properties:
      hibernate.show_sql: true
      hibernate.format_sql: true
    open-in-view: false
  datasource:
    # 数据源
    url: jdbc:mysql://127.0.0.1:3306/imooc_e_commerce?autoReconnect=true&useUnicode=true&characterEncoding=utf8&useSSL=false&serverTimezone=UTC
    username: root
    password: root
    type: com.zaxxer.hikari.HikariDataSource
    driver-class-name: com.mysql.cj.jdbc.Driver
    # 连接池
    hikari:
      maximum-pool-size: 8
      minimum-idle: 4
      idle-timeout: 30000
      connection-timeout: 30000
      max-lifetime: 45000
      auto-commit: true
      pool-name: ImoocEcommerceHikariCP
  kafka:
    bootstrap-servers: 127.0.0.1:9092
    producer:
      retries: 3
    consumer:
      auto-offset-reset: latest
  zipkin:
    sender:
      type: kafka # 默认是 web
    base-url: http://127.0.0.1:9411/
# 暴露端点
management:
  endpoints:
    web:
      exposure:
        include: '*'
  endpoint:
    health:
      show-details: always

配置完成之后,编写主启动类 @EnableJpaAuditing因为我们用到 自动加入创建时间和修改时间,所以我们需要打开 jpa的自动审计功能,不然会报错

@EnableJpaAuditing //允许 jpa 的自动审计
@SpringBootApplication
@EnableDiscoveryClient
public class AuthorityApplication {
    public static void main(String[] args) {
        SpringApplication.run(AuthorityApplication.class, args);
    }
}

test包下就测试环境是否正确

/**
 * 授权中心测试入口
 * 验证授权中心 环境可用性
 */
@SpringBootTest
@RunWith(SpringRunner.class)
public class AuthorityCenterApplicationTest {
    @Test
    public void conetextLoad() {
    }
}

环境ok之后


我们去测试 数据库操作是否可用


编写实体类ecommerceUser


/*
 * 用户表实体类定义
 * */
@Entity
@EntityListeners(AuditingEntityListener.class)
@Table(name = "t_ecommerce_user")
@Data
@NoArgsConstructor
@AllArgsConstructor
public class EcommerceUser {
    /* 自增组件*/
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id", nullable = false)
    private long id;
    /*用户名*/
    @Column(name = "username", nullable = false)
    private String username;
    /* MD5 密码*/
    @Column(name = "password", nullable = false)
    private String password;
    /*额外的信息 json 字符串存储*/
    @Column(name = "extra_info", nullable = false)
    private String extraInfo;
    /*自动加入创建时间 需要主启动类的注解*/
    @CreatedDate
    @Column(name = "create_time", nullable = false)
    private Date createTime;
    /*自动加入更新时间 需要主启动类的注解*/
    @CreatedDate
    @Column(name = "update_time", nullable = false)
    private Date updateTime;
}

有了实体类我们需要有数据操作的实现 于是编写Dao 接口


其实当我们创建接口的时候jpa就已经有了对应的基础增删改查的方法

2.png



这里我们实现两个自定义查询方法

/**
 * EcommerceUserDao 接口定义
 */
public interface EcommerceUserDao extends JpaRepository<EcommerceUser, Long> {
    /*
     * 根据用户名查询 EcommerceUser 对象
     * 等于 select * form t_ecommerce_user where username=?
     * */
    EcommerceUser findByUsername(String name);
    /*
     * 根据用户名查询 EcommerceUser 对象
     * 等于 select * form t_ecommerce_user where username=? and password=?
     * */
    EcommerceUser findByUsernameAndPassword(String name, String password);
}

之后创建 test service

/**
 * @author : 冷环渊
 * @date : 2021/12/4
 * @context: EcommerceUser 相关测试
 * @params :  null
 * @return :  * @return : null
 */
@SpringBootTest
@RunWith(SpringRunner.class)
@Slf4j
public class EcommerUserTest {
    @Autowired
    EcommerceUserDao ecommerceUserDao;
    /*测试  新增一个用户数据 */
    @Test
    public void createUserRecord() {
        EcommerceUser ecommerceUser = new EcommerceUser();
        //设置要插入的信息
        ecommerceUser.setUsername("hyc@qq.com");
        ecommerceUser.setPassword(MD5.create().digestHex("123456"));
        ecommerceUser.setExtraInfo("{}");
        //日志打印返回结果
        log.info("server user:[{}]", JSON.toJSON(ecommerceUserDao.save(ecommerceUser)));
    }
    /*测试 我们编写的自定义方法 查询 刚才创建的新角色*/
    @Test
    public void SelectUserInfo() {
        String username = "hyc@qq.com";
        log.info("select userinof:[{}]", JSON.toJSON(ecommerceUserDao.findByUsername(username)));
    }
}

测试相关的 方法 新增用户啊 或者是 按条件查询用户 ,测试均通过

2.png

生成RSA256的公钥 和 私钥 非对称加密算法

他通过 私钥加密 公钥解密来完成验证,目前很多的鉴权 都是 JWTRSA256的算法来加密鉴权的,如果了解不多,就是用RSA256就可以了


相关文章
|
1月前
|
Cloud Native Java API
聊聊从单体到微服务架构服务演化过程
本文介绍了从单体应用到微服务再到云原生架构的演进过程。单体应用虽易于搭建和部署,但难以局部更新;面向服务架构(SOA)通过模块化和服务总线提升了组件复用性和分布式部署能力;微服务则进一步实现了服务的独立开发与部署,提高了灵活性;云原生架构则利用容器化、微服务和自动化工具,实现了应用在动态环境中的弹性扩展与高效管理。这一演进体现了软件架构向着更灵活、更高效的方向发展。
|
1月前
|
存储 数据可视化 Java
基于MicrometerTracing门面和Zipkin实现集成springcloud2023的服务追踪
Sleuth将会停止维护,Sleuth最新版本也只支持springboot2。作为替代可以使用MicrometerTracing在微服务中作为服务追踪的工具。
85 1
|
14天前
|
Kubernetes 负载均衡 Docker
构建高效后端服务:微服务架构的探索与实践
【10月更文挑战第20天】 在数字化时代,后端服务的构建对于任何在线业务的成功至关重要。本文将深入探讨微服务架构的概念、优势以及如何在实际项目中有效实施。我们将从微服务的基本理念出发,逐步解析其在提高系统可维护性、扩展性和敏捷性方面的作用。通过实际案例分析,揭示微服务架构在不同场景下的应用策略和最佳实践。无论你是后端开发新手还是经验丰富的工程师,本文都将为你提供宝贵的见解和实用的指导。
|
7天前
|
运维 NoSQL Java
后端架构演进:微服务架构的优缺点与实战案例分析
【10月更文挑战第28天】本文探讨了微服务架构与单体架构的优缺点,并通过实战案例分析了微服务架构在实际应用中的表现。微服务架构具有高内聚、低耦合、独立部署等优势,但也面临分布式系统的复杂性和较高的运维成本。通过某电商平台的实际案例,展示了微服务架构在提升系统性能和团队协作效率方面的显著效果,同时也指出了其带来的挑战。
40 4
|
13天前
|
监控 API 持续交付
构建高效后端服务:微服务架构的深度探索
【10月更文挑战第20天】 在数字化时代,后端服务的构建对于支撑复杂的业务逻辑和海量数据处理至关重要。本文深入探讨了微服务架构的核心理念、实施策略以及面临的挑战,旨在为开发者提供一套构建高效、可扩展后端服务的方法论。通过案例分析,揭示微服务如何帮助企业应对快速变化的业务需求,同时保持系统的稳定性和灵活性。
43 9
|
15天前
|
监控 安全 Java
构建高效后端服务:微服务架构深度解析与最佳实践###
【10月更文挑战第19天】 在数字化转型加速的今天,企业对后端服务的响应速度、可扩展性和灵活性提出了更高要求。本文探讨了微服务架构作为解决方案,通过分析传统单体架构面临的挑战,深入剖析微服务的核心优势、关键组件及设计原则。我们将从实际案例入手,揭示成功实施微服务的策略与常见陷阱,为开发者和企业提供可操作的指导建议。本文目的是帮助读者理解如何利用微服务架构提升后端服务的整体效能,实现业务快速迭代与创新。 ###
44 2
|
20天前
|
消息中间件 Kafka 数据库
微服务架构中,如何确保服务之间的数据一致性?
微服务架构中,如何确保服务之间的数据一致性?
|
17天前
|
运维 Kubernetes 开发者
构建高效后端服务:微服务架构与容器化技术的结合
【10月更文挑战第18天】 在数字化转型的浪潮中,企业对后端服务的要求日益提高,追求更高的效率、更强的可伸缩性和更易于维护的系统。本文将探讨微服务架构与容器化技术如何结合,以构建一个既灵活又高效的后端服务体系。通过分析当前后端服务面临的挑战,介绍微服务和容器化的基本概念,以及它们如何相互配合来优化后端服务的性能和管理。本文旨在为开发者提供一种实现后端服务现代化的方法,从而帮助企业在竞争激烈的市场中脱颖而出。
20 0
|
2月前
|
运维 持续交付 API
深入理解并实践微服务架构:从理论到实战
深入理解并实践微服务架构:从理论到实战
128 3
|
2月前
|
SpringCloudAlibaba API 开发者
新版-SpringCloud+SpringCloud Alibaba
新版-SpringCloud+SpringCloud Alibaba