You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用Java Spring Boot复现Postman中发送.cer和.key文件的场景

用Java Spring Boot实现客户端证书认证(基于X.509证书与RSA密钥)

场景说明

我持有X.509格式的.cer证书文件,以及用于客户端数据交互的RSA私钥.key文件,希望用Java Spring Boot复现Postman中配置客户端证书调用接口的场景(对应截图场景:配置客户端证书、私钥完成接口请求)。

实现步骤

1. 准备证书与密钥文件

  • 将.cer和.key文件放入Spring Boot项目的src/main/resources目录,或指定明确的绝对路径。
  • 若密钥设置了密码,需提前留存该密码。

2. 配置带客户端证书的RestTemplate

创建配置类,构建支持客户端证书认证的RestTemplate实例:

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.http.client.ClientHttpRequestFactory;
import org.springframework.http.client.HttpComponentsClientHttpRequestFactory;
import org.springframework.web.client.RestTemplate;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.conn.ssl.SSLContextBuilder;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import java.io.FileInputStream;
import java.security.KeyStore;
import java.security.PrivateKey;
import java.security.cert.Certificate;
import java.security.cert.CertificateFactory;
import java.security.spec.PKCS8EncodedKeySpec;
import java.security.KeyFactory;
import java.nio.file.Files;
import java.nio.file.Paths;
import java.util.Base64;

@Configuration
public class RestTemplateConfig {

    @Bean
    public RestTemplate clientCertRestTemplate() throws Exception {
        // 加载X.509证书
        CertificateFactory certFactory = CertificateFactory.getInstance("X.509");
        Certificate cert = certFactory.generateCertificate(new FileInputStream("src/main/resources/client.cer"));

        // 加载RSA私钥(去除PEM格式头尾与空白字符)
        String privateKeyContent = new String(Files.readAllBytes(Paths.get("src/main/resources/client.key")))
                .replace("-----BEGIN PRIVATE KEY-----", "")
                .replace("-----END PRIVATE KEY-----", "")
                .replaceAll("\\s", "");
        byte[] privateKeyBytes = Base64.getDecoder().decode(privateKeyContent);
        PKCS8EncodedKeySpec keySpec = new PKCS8EncodedKeySpec(privateKeyBytes);
        PrivateKey privateKey = KeyFactory.getInstance("RSA").generatePrivate(keySpec);

        // 创建密钥库并存入证书与私钥
        KeyStore keyStore = KeyStore.getInstance(KeyStore.getDefaultType());
        keyStore.load(null);
        keyStore.setCertificateEntry("client-cert", cert);
        keyStore.setKeyEntry("client-key", privateKey, "你的密钥密码".toCharArray(), new Certificate[]{cert});

        // 构建SSL上下文
        SSLContextBuilder sslContextBuilder = SSLContextBuilder.create()
                .loadKeyMaterial(keyStore, "你的密钥密码".toCharArray());

        // 创建SSL连接工厂
        SSLConnectionSocketFactory sslSocketFactory = new SSLConnectionSocketFactory(
                sslContextBuilder.build(),
                new String[]{"TLSv1.2"},
                null,
                SSLConnectionSocketFactory.getDefaultHostnameVerifier());

        // 构建HttpClient实例
        CloseableHttpClient httpClient = HttpClients.custom()
                .setSSLSocketFactory(sslSocketFactory)
                .build();

        ClientHttpRequestFactory requestFactory = new HttpComponentsClientHttpRequestFactory(httpClient);
        return new RestTemplate(requestFactory);
    }
}

3. 调用目标接口示例

在业务类中注入配置好的RestTemplate,发起带证书的请求:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.web.client.RestTemplate;

@Service
public class ApiClientService {

    private final RestTemplate clientCertRestTemplate;

    @Autowired
    public ApiClientService(RestTemplate clientCertRestTemplate) {
        this.clientCertRestTemplate = clientCertRestTemplate;
    }

    public String callSecureApi() {
        String targetApiUrl = "https://你的目标接口地址";
        // 根据接口需求选择GET/POST等请求方式
        return clientCertRestTemplate.getForObject(targetApiUrl, String.class);
    }
}

4. 关键注意事项

  • 若目标服务器的CA证书未被JVM信任,需额外配置信任库,将服务器CA证书加入信任链,避免SSL握手失败。
  • 确保私钥为PKCS#8格式(PEM头为-----BEGIN PRIVATE KEY-----),若为PKCS#1格式(头为-----BEGIN RSA PRIVATE KEY-----),可通过OpenSSL转换:
    openssl pkcs8 -topk8 -inform PEM -in client.key -outform PEM -nocrypt
    
  • 代码中的文件路径、密钥密码、目标接口地址需替换为实际值。

内容的提问来源于stack exchange,提问作者StormBreaker

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.27 21:32:40