随机ca证书

This commit is contained in:
xljiulang 2021-07-18 13:45:26 +08:00
parent 8312886db7
commit b8ac5864cc
6 changed files with 79 additions and 77 deletions

View File

@ -29,6 +29,31 @@ namespace FastGithub.ReverseProxy
{
private static readonly SecureRandom secureRandom = new();
/// <summary>
/// 生成自签名证书
/// </summary>
/// <param name="domains"></param>
/// <param name="keySizeBits"></param>
/// <param name="validFrom"></param>
/// <param name="validTo"></param>
/// <param name="caPublicCerPath"></param>
/// <param name="caPrivateKeyPath"></param>
public static void GenerateBySelf(IEnumerable<string> domains, int keySizeBits, DateTime validFrom, DateTime validTo, string caPublicCerPath, string caPrivateKeyPath)
{
var keys = GenerateRsaKeyPair(keySizeBits);
var cert = GenerateCertificate(domains, keys.Public, validFrom, validTo, domains.First(), null, keys.Private, null);
using var priWriter = new StreamWriter(caPrivateKeyPath);
var priPemWriter = new PemWriter(priWriter);
priPemWriter.WriteObject(keys.Private);
priPemWriter.Writer.Flush();
using var pubWriter = new StreamWriter(caPublicCerPath);
var pubPemWriter = new PemWriter(pubWriter);
pubPemWriter.WriteObject(cert);
pubPemWriter.Writer.Flush();
}
/// <summary>
/// 生成CA签名证书
/// </summary>
@ -39,7 +64,7 @@ namespace FastGithub.ReverseProxy
/// <param name="caPublicCerPath"></param>
/// <param name="caPrivateKeyPath"></param>
/// <returns></returns>
public static X509Certificate2 Generate(IEnumerable<string> domains, int keySizeBits, DateTime validFrom, DateTime validTo, string caPublicCerPath, string caPrivateKeyPath, string? password = default)
public static X509Certificate2 GenerateByCa(IEnumerable<string> domains, int keySizeBits, DateTime validFrom, DateTime validTo, string caPublicCerPath, string caPrivateKeyPath, string? password = default)
{
if (File.Exists(caPublicCerPath) == false)
{
@ -90,7 +115,7 @@ namespace FastGithub.ReverseProxy
/// <param name="issuerPrivate"></param>
/// <param name="CA_PathLengthConstraint"></param>
/// <returns></returns>
private static X509Certificate GenerateCertificate(IEnumerable<string> domains, AsymmetricKeyParameter subjectPublic, DateTime validFrom, DateTime validTo, string issuerName, AsymmetricKeyParameter issuerPublic, AsymmetricKeyParameter issuerPrivate, int? CA_PathLengthConstraint)
private static X509Certificate GenerateCertificate(IEnumerable<string> domains, AsymmetricKeyParameter subjectPublic, DateTime validFrom, DateTime validTo, string issuerName, AsymmetricKeyParameter? issuerPublic, AsymmetricKeyParameter issuerPrivate, int? CA_PathLengthConstraint)
{
var signatureFactory = issuerPrivate is ECPrivateKeyParameters
? new Asn1SignatureFactory(X9ObjectIdentifiers.ECDsaWithSha256.ToString(), issuerPrivate)

View File

@ -6,6 +6,7 @@ using Microsoft.Extensions.Logging;
using System;
using System.Collections.Concurrent;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Net.NetworkInformation;
@ -35,7 +36,9 @@ namespace FastGithub
{
var loggerFactory = kestrel.ApplicationServices.GetRequiredService<ILoggerFactory>();
var logger = loggerFactory.CreateLogger($"{nameof(FastGithub)}.{nameof(ReverseProxy)}");
TryInstallCaCert(caPublicCerPath, logger);
GeneratorCaCert(caPublicCerPath, caPrivateKeyPath);
InstallCaCert(caPublicCerPath, logger);
kestrel.ListenAnyIP(443, listen =>
listen.UseHttps(https =>
@ -45,6 +48,51 @@ namespace FastGithub
logger.LogInformation("https反向代理服务启动成功");
}
/// <summary>
/// 生成根证书
/// </summary>
/// <param name="caPublicCerPath"></param>
/// <param name="caPrivateKeyPath"></param>
private static void GeneratorCaCert(string caPublicCerPath, string caPrivateKeyPath)
{
if (File.Exists(caPublicCerPath) && File.Exists(caPublicCerPath))
{
return;
}
File.Delete(caPublicCerPath);
File.Delete(caPrivateKeyPath);
var validFrom = DateTime.Today.AddYears(-10);
var validTo = DateTime.Today.AddYears(50);
CertGenerator.GenerateBySelf(new[] { nameof(FastGithub) }, 2048, validFrom, validTo, caPublicCerPath, caPrivateKeyPath);
}
/// <summary>
/// 安装根证书
/// </summary>
/// <param name="caPublicCerPath"></param>
/// <param name="logger"></param>
private static void InstallCaCert(string caPublicCerPath, ILogger logger)
{
try
{
var caCert = new X509Certificate2(caPublicCerPath);
using var store = new X509Store(StoreName.Root, StoreLocation.LocalMachine);
store.Open(OpenFlags.ReadWrite);
if (store.Certificates.Find(X509FindType.FindByThumbprint, caCert.Thumbprint, true).Count == 0)
{
store.Add(caCert);
store.Close();
}
}
catch (Exception)
{
logger.LogWarning($"安装根证书{caPublicCerPath}失败:请手动安装到“将所有的证书都放入下载存储”\\“受信任的根证书颁发机构”");
}
}
/// <summary>
/// 获取颁发给指定域名的证书
/// </summary>
@ -63,7 +111,7 @@ namespace FastGithub
var domains = GetDomains(host).Distinct();
var validFrom = DateTime.Today.AddYears(-1);
var validTo = DateTime.Today.AddYears(10);
return CertGenerator.Generate(domains, 2048, validFrom, validTo, caPublicCerPath, caPrivateKeyPath);
return CertGenerator.GenerateByCa(domains, 2048, validFrom, validTo, caPublicCerPath, caPrivateKeyPath);
}, LazyThreadSafetyMode.ExecutionAndPublication);
}
}
@ -94,29 +142,5 @@ namespace FastGithub
}
}
}
/// <summary>
/// 安装根证书
/// </summary>
/// <param name="caPublicCerPath"></param>
/// <param name="logger"></param>
private static void TryInstallCaCert(string caPublicCerPath, ILogger logger)
{
try
{
var caCert = new X509Certificate2(caPublicCerPath);
using var store = new X509Store(StoreName.Root, StoreLocation.LocalMachine);
store.Open(OpenFlags.ReadWrite);
if (store.Certificates.Find(X509FindType.FindByThumbprint, caCert.Thumbprint, true).Count == 0)
{
store.Add(caCert);
store.Close();
}
}
catch (Exception)
{
logger.LogWarning($"安装根证书{caPublicCerPath}失败:请手动安装到“将所有的证书都放入下载存储”\\“受信任的根证书颁发机构”");
}
}
}
}

View File

@ -1,18 +0,0 @@
-----BEGIN CERTIFICATE-----
MIIC2DCCAcCgAwIBAgIQAKaUqwPmF9dDFtqNp34mRTANBgkqhkiG9w0BAQsFADAY
MRYwFAYDVQQDDA1GYXN0R2l0aHViX0NBMCAXDTExMDcxMzAwMDAwMFoYDzI1MjEw
NzEzMDAwMDAwWjAYMRYwFAYDVQQDDA1GYXN0R2l0aHViX0NBMIIBIjANBgkqhkiG
9w0BAQEFAAOCAQ8AMIIBCgKCAQEA1vNFkTGacoKdOY+H8Va7BN/z+nXyUHI1aZGC
11uzRVggi7EDxL2ThufzrQNEMqmh7aI6UbmnFMee+UtzexBSl2x8sH0uOPL31Pbh
fsrrgjMW0p8doApaTlEVyrXI5SVEapf+B13y/Nu6e2PQ4gRT4WZaBfLgqQdcaT9/
RdaexznlRYzet6HAKf/Hvs5tkbWkLY9mvctcMWm998wjVVD2vTyZ7Pe7s7L2w/fG
mcz0svonr18zI+kHK/hK/2u/jvnmC8HpvhnDbNp7brOvR0TF6oYjKB20Zicy32UK
0/PekVN9T8dzOwjkZXJ0xI7RRVLOLG1qkO8z8BhyznjQLLZSLwIDAQABoxwwGjAY
BgNVHREEETAPgg1GYXN0R2l0aHViX0NBMA0GCSqGSIb3DQEBCwUAA4IBAQCYR68q
oKqBiNKlWgaaY8o2w7PGL0NZ2QVGlZp4Yl8Jj60qx587TSN9YTjMgNpZnkCYJZbQ
AhJAcwVspFsAq90SG/md0A6o3TRHSEV2HJIvAoMTiT/LLG+ZU61/NxMl0WxoQPKz
OcleOo+fCklove9jYIhHsls30eQv/NGn+pKhnCI9VEC+sUxbxQd4LJQbBYouNV6I
Sd8axEazqWsQrfX+CvNb2UjH3aaARaPWcacTcVlO5XJz2eDnUzVQOWwgv57sLUmY
xn0HbGp4lATgNeUSBcn7pEHv/yjqraJn2cVl0l/ZaFcYcccYZFrA3qAi14aiGRtu
SSC6OWHrtXwXZnkn
-----END CERTIFICATE-----

View File

@ -35,9 +35,6 @@
<None Update="FastGithub.cer">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="FastGithub.key">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
<None Update="README.html">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>

View File

@ -1,27 +0,0 @@
-----BEGIN RSA PRIVATE KEY-----
MIIEpAIBAAKCAQEA1vNFkTGacoKdOY+H8Va7BN/z+nXyUHI1aZGC11uzRVggi7ED
xL2ThufzrQNEMqmh7aI6UbmnFMee+UtzexBSl2x8sH0uOPL31PbhfsrrgjMW0p8d
oApaTlEVyrXI5SVEapf+B13y/Nu6e2PQ4gRT4WZaBfLgqQdcaT9/RdaexznlRYze
t6HAKf/Hvs5tkbWkLY9mvctcMWm998wjVVD2vTyZ7Pe7s7L2w/fGmcz0svonr18z
I+kHK/hK/2u/jvnmC8HpvhnDbNp7brOvR0TF6oYjKB20Zicy32UK0/PekVN9T8dz
OwjkZXJ0xI7RRVLOLG1qkO8z8BhyznjQLLZSLwIDAQABAoIBABamHILviJgfRiTO
CGN4IY2icWlHK0ipuBIPGIvLqEiawBcoCD8fQJ+66hSlXva9pAfPi7iXyNCqNgiL
mDfz4Nf+wOax0gCDLXT9rIX5KLaX3oRD6tG1tY1CAvtQi0IF2r8mk8g/8H4PQweE
XXqrPRFngP3WeTCmS2j1nVoFAsb4E7ZOKVVD3z6wILWHUfXuAeV/R1/pqbDvc4Yn
i2+PZvHZVjftkOqy7FyNE18y2Q198TKWATV1WzrB/Tv0mVoQN/izM9HflERUvvMo
v+I9ZTKrLgnHo5bHprVLRQnHfBJo/SDHJTCtP57sGElUaYl9nFM6k47k0Jp71zID
2UrlY/kCgYEA+ZFD2L+q6y4nDXOngDUiRiLbRJDb2u5pOY6scRHa73KCvq+t+Bih
fxtE9h4EDa1zei/tR6gkQnoIe9Nviikz2YyTrZkqHzAK55who9H6GT9pErNUvXF2
dnje2KlRcjniMp8vcm1sbYMDEt+NFS2sL8rby97bZQ+V5WjLoYAhAacCgYEA3H2X
IPDudA6cFPczn+19qw76nKdrc3LkxToYdscb/8tH6dX+yrt02t1Ezm81kcMcqeHd
BzbxNeiN2NmBozLQ0SERMDkNJUUFlK3ALdx9USdwTTMywRMnkgLDuRaA6m1QDi24
RoFDjhEQREbjRD4WxJuzgvLKhF60bQnsAf5R7DkCgYBDpWBii/FkNepX9xVb5wsX
P7N3blxph132P/n13AUgCkXuMehR6zs7HMUggRpQKse2Qu9qEOVjL3jFN5ZwOKLZ
QQV2dKG6Omd6SBPGN9A2r71nWDyL7QlTK4gb6iktcQsi9YsC1S4isPRQVVAEgZC+
k5noNMv7JLJYsIMhj31i2QKBgQDbg9HVgujz9KOiH+Zuv4PQrQ4GrovEmct3K/q1
LlAK33iOLnYHoo+ZYpehKojbwLOl0m86QpHtCMVH8mwlbW8F9fTl3LbgtxHyTvW4
8v50sF4XDfTm0kogDM6NVAEu43vDUfNXhlQaeZSHVUfoZiRGw3j50vyawqrAsBMe
fPNUyQKBgQCMLr1WLgnDiMx7CLXlmKdw45z0UeP+ngZOuPICX9d5DOfznuP8VgS9
ZiwXHF8PbSdlMFPq9LkPbQTjfTLHXZx0mKl78PcFqwtryXTpUlP1qcfjE6Hl+POD
2OkWyGz7vA80+7ilQscm0L/gLIgwiGQOdBv6akLF8qDwncOX4yWOVQ==
-----END RSA PRIVATE KEY-----

View File

@ -2,6 +2,7 @@
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using System;
using System.IO;
namespace FastGithub
@ -51,7 +52,7 @@ namespace FastGithub
.ConfigureWebHostDefaults(web =>
{
web.Configure(app => app.UseHttpsReverseProxy("README.html"));
web.UseKestrel(kestrel => kestrel.ListenHttpsReverseProxy("FastGithub.cer", "FastGithub.key"));
web.UseKestrel(kestrel => kestrel.ListenHttpsReverseProxy($"FastGithub_{Environment.MachineName}.cer", $"FastGithub_{Environment.MachineName}.key"));
});
}
}