欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

Eureka实战-5【启用https】

程序员文章站 2022-06-14 08:36:48
上一篇主要说的是开启http basic认证,从安全角度来讲,基于base64编码,容易被抓包后破解,在公网中很不安全,本文详谈如何在eureka server和eureka client中开启https。 公共依赖pom文件 1、eureka server工程 1.1、eureka server工 ......

上一篇主要说的是开启http basic认证,从安全角度来讲,基于base64编码,容易被抓包后破解,在公网中很不安全,本文详谈如何在eureka server和eureka client中开启https。

 

公共依赖pom文件

<parent>
        <groupid>org.springframework.boot</groupid>
        <artifactid>spring-boot-starter-parent</artifactid>
        <version>2.0.3.release</version>
        <relativepath/>
</parent>

<properties>
        <project.build.sourceencoding>utf-8</project.build.sourceencoding>
        <project.reporting.outputencoding>utf-8</project.reporting.outputencoding>
        <java.version>1.8</java.version>
        <spring-cloud.version>finchley.release</spring-cloud.version>
</properties>

<dependencymanagement>
        <dependencies>
            <dependency>
                <groupid>org.springframework.cloud</groupid>
                <artifactid>spring-cloud-dependencies</artifactid>
                <version>${spring-cloud.version}</version>
                <type>pom</type>
                <scope>import</scope>
            </dependency>
        </dependencies>
</dependencymanagement>

 

1、eureka server工程

1.1、eureka server工程pom:

<!--加上文章头部的公共依赖-->

<dependencies> <dependency> <groupid>org.springframework.cloud</groupid> <artifactid>spring-cloud-starter-netflix-eureka-server</artifactid> </dependency> </dependencies> <build> <plugins> <plugin> <groupid>org.springframework.boot</groupid> <artifactid>spring-boot-maven-plugin</artifactid> </plugin> </plugins> </build>

 

1.2、eureka server工程启动类:

import org.springframework.boot.springapplication;
import org.springframework.boot.autoconfigure.springbootapplication;
import org.springframework.cloud.netflix.eureka.server.enableeurekaserver;

@springbootapplication
@enableeurekaserver
public class eurekaserverapplication {

    public static void main(string[] args) {
        springapplication.run(eurekaserverapplication.class, args);
    }
}

 

1.3、生成证书

a、生成server工程的证书,使用命令行工具,执行下面的指令:

keytool -genkeypair -alias server -storetype pkcs12 -keyalg rsa -keysize 2048 -keystore server.p12 -validity 3650
输入密钥库口令:
再次输入新口令:
您的名字与姓氏是什么?
  [unknown]:  spring
您的组织单位名称是什么?
  [unknown]:  spring
您的组织名称是什么?
  [unknown]:  spring
您所在的城市或区域名称是什么?
  [unknown]:  spring
您所在的省/市/自治区名称是什么?
  [unknown]:  spring
该单位的双字母国家/地区代码是什么?
  [unknown]:  spring
cn=spring, ou=spring, o=spring, l=spring, st=spring, c=spring是否正确?
  [否]:  y

 

b、同样的方式生成client工程证书,执行下面的指令:

keytool -genkeypair -alias client -storetype pkcs12 -keyalg rsa -keysize 2048 -keystore client.p12 -validity 3650
//。。。同样需要设置密码,回答上面的那些问题


c、分别导出2个p12证书,执行指令:

keytool -export -alias server -file server.crt --keystore server.p12
输入密钥库口令: 这里的密码是生成server证书时设置的密码
存储在文件 <server.crt> 中的证书
keytool -export -alias client -file client.crt --keystore client.p12
输入密钥库口令: 这里的密码是生成client证书时设置的密码
存储在文件 <client.crt> 中的证书

 

d、将server.crt文件导入client.p12证书中,使client端信任server的证书,执行如下指令

keytool -import -alias server -file server.crt -keystore client.p12
输入密钥库口令: 这里的密码是生成client证书密码,密码错误会提示如下信息:
【密码错误时提示的信息:keytool 错误: java.io.ioexception: keystore password was incorrect】

所有者: cn=spring, ou=spring, o=spring, l=spring, st=spring, c=spring 发布者: cn=spring, ou=spring, o=spring, l=spring, st=spring, c=spring 序列号: 2b87a269 有效期为 fri oct 04 20:11:07 cst 2019 至 mon oct 01 20:11:07 cst 2029 证书指纹: md5: ef:a3:6b:32:de:8f:e4:34:46:e6:0d:48:b9:8f:b8:7e sha1: ae:42:78:14:d8:6b:b2:e9:46:f4:76:e8:d9:d0:51:e0:3a:e6:c9:2e sha256: 54:6d:93:7e:b3:d3:c4:49:87:84:9d:46:66:b1:b8:1b:95:5b:dc:05:9a:8a:a4:df:43:e4:a7:a7:4a:81:f7:b0 签名算法名称: sha256withrsa 主体公共密钥算法: 2048 位 rsa 密钥 版本: 3 扩展: #1: objectid: 2.5.29.14 criticality=false subjectkeyidentifier [ keyidentifier [ 0000: 6c 1a e4 01 eb 84 0b c2 90 97 81 3d db 0d c3 f1 l..........=.... 0010: 4a fb 2a f4 j.*. ] ] 是否信任此证书? [否]: y 证书已添加到密钥库中

 

e、将client.crt文件导入server.p12文件,使server服务信任client的证书,执行如下指令:

keytool -import -alias client -file client.crt -keystore server.p12
输入密钥库口令: 这里的密码是生成server证书密码
所有者: cn=cloud, ou=cloud, o=cloud, l=cloud, st=cloud, c=cloud
发布者: cn=cloud, ou=cloud, o=cloud, l=cloud, st=cloud, c=cloud
序列号: 6ea2a01
有效期为 fri oct 04 20:27:38 cst 2019 至 mon oct 01 20:27:38 cst 2029
证书指纹:
     md5:  e9:22:2c:8d:c4:08:27:ad:02:75:93:31:c2:17:35:8e
     sha1: bb:b0:9a:3a:98:43:5e:02:fc:8a:bc:85:33:dd:82:4a:4e:df:3a:5c
     sha256: 20:96:61:27:d1:ca:55:e5:b6:0e:41:ca:bc:84:f8:8f:1f:d8:25:87:10:50:90:e3:bc:12:39:35:74:16:4a:b3
签名算法名称: sha256withrsa
主体公共密钥算法: 2048 位 rsa 密钥
版本: 3

扩展:

#1: objectid: 2.5.29.14 criticality=false
subjectkeyidentifier [
keyidentifier [
0000: 91 e6 46 ef 4c 9e 88 b1   2f 63 12 4b 39 53 9d 32  ..f.l.../c.k9s.2
0010: ef 0f 42 f9                                        ..b.
]
]

是否信任此证书? [否]:  y
证书已添加到密钥库中

 

1.4、将生成的server.p12、server.crt、client.crt三个文件放在eureka server工程resources目录下。

 

1.5、添加eureka server工程相关resources配置文件

application-https.yml:

server:
  port: 8766
  ssl:
    enabled: true
    key-store: classpath:server.p12
    key-store-password: hello2019 #生成server证书时设置的密码
    key-store-type: pkcs12
    key-alias: server
eureka:
  instance:
    hostname: localhost
    secureport: ${server.port}
    secureportenabled: true
    nonsecureportenabled: false
    homepageurl: https://${eureka.instance.hostname}:${server.port}/
    statuspageurl: https://${eureka.instance.hostname}:${server.port}/
  client:
    registerwitheureka: false
    fetchregistry: false
    serviceurl:
      defaultzone: https://${eureka.instance.hostname}:${server.port}/eureka/
  server:
      waittimeinmswhensyncempty: 0
      enableselfpreservation: false

application.yml:

spring:
  profiles:
    active: https

 

1.6、启动eureka server工程,执行指令:

mvn spring-boot:run -dspring.profiles.active=https

访问:https://localhost:8766

Eureka实战-5【启用https】

 

 由此看出确实使用的是https,不妨在试一下访问:http://localhost:8766

Eureka实战-5【启用https】

 

 

2、eureka client工程

2.1、client工程pom文件:

<!--加上文章头部的公共依赖-->

<dependencies> <dependency> <groupid>org.apache.httpcomponents</groupid> <artifactid>httpclient</artifactid> <version>4.5.5</version> </dependency> <dependency> <groupid>org.springframework.cloud</groupid> <artifactid>spring-cloud-starter-netflix-eureka-client</artifactid> </dependency> </dependencies> <build> <plugins> <plugin> <groupid>org.springframework.boot</groupid> <artifactid>spring-boot-maven-plugin</artifactid> </plugin> </plugins> </build>

 

2.2、client工程启动类:

import org.springframework.boot.springapplication;
import org.springframework.boot.autoconfigure.springbootapplication;
import org.springframework.cloud.netflix.eureka.enableeurekaclient;

@springbootapplication
@enableeurekaclient
public class eurekaclientapplication {

    public static void main(string[] args) {
        springapplication.run(eurekaclientapplication.class, args);
    }
}

 

2.2、client工程resources配置文件

先将client.crt、client.p12、server.crt三个文件放在client工程的resources目录下。

application.yml:

spring:
  profiles:
    active: https

application-https.yml:

server:
  port: 8081

spring:
  application:
    name: client1

eureka:
  client:
    secureportenabled: true
    ssl:
      key-store: client.p12
      key-store-password: hello2020
    serviceurl:
      defaultzone: https://localhost:8766/eureka/

这里没有指定整个应用实例启用https,仅仅是开启访问eureka server的https配置,自定义eureka.client.ssl.key-store和eureka.client.ssl.key-store-password两个属性,指定client访问server的sslcontext配置,需要在代码里指定discoveryclient.discoveryclientoptionalargs:

import com.netflix.discovery.discoveryclient;
import com.netflix.discovery.shared.transport.jersey.eurekajerseyclientimpl;
import org.apache.http.ssl.sslcontextbuilder;
import org.springframework.beans.factory.annotation.value;
import org.springframework.context.annotation.bean;
import org.springframework.context.annotation.configuration;
import org.springframework.context.annotation.profile;

import javax.net.ssl.sslcontext;
import java.io.ioexception;
import java.security.keymanagementexception;
import java.security.keystoreexception;
import java.security.nosuchalgorithmexception;
import java.security.cert.certificateexception;

/**
 * 指定client访问server的sslcontext配置
 */
@profile({"https"})
@configuration
public class eurekahttpsclientconfig {

    @value("${eureka.client.ssl.key-store}")
    string keystorefilename;

    @value("${eureka.client.ssl.key-store-password}")
    string keystorepassword;

    @bean
    public discoveryclient.discoveryclientoptionalargs discoveryclientoptionalargs() throws certificateexception, nosuchalgorithmexception, keystoreexception, ioexception, keymanagementexception {
        eurekajerseyclientimpl.eurekajerseyclientbuilder builder = new eurekajerseyclientimpl.eurekajerseyclientbuilder();
        builder.withclientname("eureka-https-client");
        sslcontext sslcontext = new sslcontextbuilder()
                .loadtrustmaterial(
                        this.getclass().getclassloader().getresource(keystorefilename),keystorepassword.tochararray()
                )
                .build();
        builder.withcustomssl(sslcontext);

        builder.withmaxtotalconnections(10);
        builder.withmaxconnectionsperhost(10);

        discoveryclient.discoveryclientoptionalargs args = new discoveryclient.discoveryclientoptionalargs();
        args.seteurekajerseyclient(builder.build());
        return args;
    }
}

 

2.3、执行指令,启动client工程:

 mvn spring-boot:run -dspring.profiles.active=https

访问https://localhost:8766/

Eureka实战-5【启用https】

 

 可以看到client工程已经成功注册到了server服务上。