浏览代码

改进账户加载和错误处理

改进了账户加载逻辑,增加了对空账户和注册失败情况的检查。新增了私钥读取工具函数,并在多个文件中优化了错误处理,确保返回更详细的错误信息。
SongZihuan 3 月之前
父节点
当前提交
f13d8930c5

+ 2 - 0
src/certssl/account/data.go

@@ -21,6 +21,8 @@ func newAccount(email string, client *lego.Client) (Account, error) {
 	res, err := register(client)
 	if err != nil {
 		return Account{}, fmt.Errorf("new account failed: %s", err.Error())
+	} else if res == nil {
+		return Account{}, fmt.Errorf("new account failed: register return nil, unknown error")
 	}
 
 	now := time.Now()

+ 0 - 1
src/certssl/account/load.go

@@ -12,7 +12,6 @@ var ErrExpiredAccount = fmt.Errorf("account not found")
 
 func loadAccount(dir string, email string) (Account, error) {
 	filepath := path.Join(dir, fmt.Sprintf("%s.account", email))
-
 	file, err := os.Open(filepath)
 	if err != nil {
 		return Account{}, fmt.Errorf("open account file failed: %s", err.Error())

+ 6 - 5
src/certssl/account/main.go

@@ -1,7 +1,6 @@
 package account
 
 import (
-	"errors"
 	"fmt"
 	"github.com/go-acme/lego/v4/lego"
 	"github.com/go-acme/lego/v4/registration"
@@ -15,10 +14,12 @@ func GetAccount(dir string, email string, client *lego.Client) (*registration.Re
 	}
 
 	account, err := loadAccount(dir, email)
-	if err != nil && errors.Is(err, ErrExpiredAccount) {
+	if err != nil {
 		account, err = newAccount(email, client)
 		if err != nil {
 			return nil, fmt.Errorf("not local account, new account failed: %s", err.Error())
+		} else if account.Email == "" {
+			return nil, fmt.Errorf("not local account, new account failed: return empty account, not email, unknown reason")
 		}
 
 		err = saveAccount(dir, account)
@@ -26,9 +27,9 @@ func GetAccount(dir string, email string, client *lego.Client) (*registration.Re
 			return nil, fmt.Errorf("not local account, save account failed: %s", err.Error())
 		}
 
-		fmt.Printf("account register success %s\n", email)
-	} else if err != nil {
-		return nil, nil
+		fmt.Printf("account register success email: %s\n", email)
+	} else {
+		fmt.Printf("load local account success email: %s\n", email)
 	}
 
 	return &account.Resource, nil

+ 6 - 1
src/certssl/account/save.go

@@ -22,5 +22,10 @@ func saveAccount(dir string, account Account) error {
 		return err
 	}
 
-	return os.WriteFile(filepath, buff.Bytes(), 0644)
+	err = os.WriteFile(filepath, buff.Bytes(), 0644)
+	if err != nil {
+		return fmt.Errorf("failed to write account %s: %s", filepath, err.Error())
+	}
+
+	return nil
 }

+ 4 - 0
src/certssl/applycert/main.go

@@ -32,6 +32,8 @@ func ApplyCert(basedir string, email string, httpsAddress string, domain string)
 	iface, port, err := net.SplitHostPort(httpsAddress)
 	if err != nil {
 		return nil, nil, fmt.Errorf("split host port failed: %s", err.Error())
+	} else if port == "" {
+		port = "443"
 	}
 
 	err = client.Challenge.SetHTTP01Provider(http01.NewProviderServer(domain, port))
@@ -42,6 +44,8 @@ func ApplyCert(basedir string, email string, httpsAddress string, domain string)
 	reg, err := account.GetAccount(path.Join(basedir, "account"), user.GetEmail(), client)
 	if err != nil {
 		return nil, nil, fmt.Errorf("get account failed: %s", err.Error())
+	} else if reg == nil {
+		return nil, nil, fmt.Errorf("get account failed: return nil account.resurce, unknown reason")
 	}
 	user.setRegistration(reg)
 

+ 9 - 38
src/certssl/applycert/read.go

@@ -3,9 +3,9 @@ package applycert
 import (
 	"crypto"
 	"crypto/x509"
-	"encoding/pem"
 	"fmt"
 	"github.com/SongZihuan/Http-Demo/src/certssl/filename"
+	"github.com/SongZihuan/Http-Demo/src/utils"
 	"os"
 	"path"
 )
@@ -25,59 +25,30 @@ func ReadLocalCertificateAndPrivateKey(basedir string) (crypto.PrivateKey, *x509
 }
 
 func readCertificate(basedir string) (*x509.Certificate, error) {
-	// 请替换为你的证书文件路径
-	certPath := path.Join(basedir, filename.FileCertificate)
-
-	// 读取PEM编码的证书文件
-	pemData, err := os.ReadFile(certPath)
+	filepath := path.Join(basedir, filename.FileCertificate)
+	data, err := os.ReadFile(filepath)
 	if err != nil {
 		return nil, fmt.Errorf("failed to read certificate file: %v", err)
 	}
 
-	// 解析PEM编码的数据
-	block, _ := pem.Decode(pemData)
-	if block == nil || block.Type != "CERTIFICATE" {
-		return nil, fmt.Errorf("failed to decode PEM block containing certificate")
-	}
-
-	// 解析证书
-	cert, err := x509.ParseCertificate(block.Bytes)
+	cert, err := utils.ReadCertificate(data)
 	if err != nil {
-		return nil, fmt.Errorf("failed to parse certificate: %v", err)
+		return nil, fmt.Errorf("failed to parser certificate file: %v", err)
 	}
 
 	return cert, nil
 }
 
 func readPrivateKey(basedir string) (crypto.PrivateKey, error) {
-	// 请替换为你的RSA私钥文件路径
-	keyPath := path.Join(basedir, filename.FilePrivateKey)
-
-	// 读取PEM编码的私钥文件
-	pemData, err := os.ReadFile(keyPath)
+	filepath := path.Join(basedir, filename.FilePrivateKey)
+	data, err := os.ReadFile(filepath)
 	if err != nil {
 		return nil, fmt.Errorf("failed to read key file: %v", err)
 	}
 
-	// 解析PEM块
-	block, _ := pem.Decode(pemData)
-	if block == nil {
-		return nil, fmt.Errorf("failed to decode PEM block containing private key")
-	}
-
-	// 根据PEM块类型解析私钥
-	var privateKey crypto.PrivateKey
-	if block.Type == "RSA PRIVATE KEY" {
-		privateKey, err = x509.ParsePKCS1PrivateKey(block.Bytes)
-	} else if block.Type == "EC PRIVATE KEY" {
-		privateKey, err = x509.ParseECPrivateKey(block.Bytes)
-	} else if block.Type == "PRIVATE KEY" {
-		privateKey, err = x509.ParsePKCS8PrivateKey(block.Bytes)
-	} else {
-		return nil, fmt.Errorf("unknown private key type: %s", block.Type)
-	}
+	privateKey, err := utils.ReadPrivateKey(data)
 	if err != nil {
-		return nil, fmt.Errorf("failed to parse private key: %v", err)
+		return nil, fmt.Errorf("failed to parser key file: %v", err)
 	}
 
 	return privateKey, nil

+ 2 - 0
src/certssl/main.go

@@ -30,6 +30,8 @@ func GetCertificateAndPrivateKey(basedir string, email string, httpsAddress stri
 	privateKey, resource, err := applycert.ApplyCert(basedir, email, httpsAddress, domain)
 	if err != nil {
 		return nil, nil, fmt.Errorf("apply cert failed: %s", err.Error())
+	} else if privateKey == nil || cert == nil {
+		return nil, nil, fmt.Errorf("read cert failed: private key or certificate (resource) is nil, unknown reason")
 	}
 
 	cert, err = utils.ReadCertificate(resource.Certificate)

+ 37 - 0
src/utils/privatekey.go

@@ -0,0 +1,37 @@
+package utils
+
+import (
+	"crypto"
+	"crypto/x509"
+	"encoding/pem"
+	"fmt"
+)
+
+func ReadPrivateKey(data []byte) (crypto.PrivateKey, error) {
+	// 解析PEM块
+	block, _ := pem.Decode(data)
+	if block == nil {
+		return nil, fmt.Errorf("failed to decode PEM block containing private key")
+	}
+
+	// 根据PEM块类型解析私钥
+	var err error
+	var privateKey crypto.PrivateKey
+	if block.Type == "RSA PRIVATE KEY" {
+		privateKey, err = x509.ParsePKCS1PrivateKey(block.Bytes)
+	} else if block.Type == "EC PRIVATE KEY" {
+		privateKey, err = x509.ParseECPrivateKey(block.Bytes)
+	} else if block.Type == "PRIVATE KEY" {
+		privateKey, err = x509.ParsePKCS8PrivateKey(block.Bytes)
+	} else {
+		return nil, fmt.Errorf("unknown private key type: %s", block.Type)
+	}
+
+	if err != nil {
+		return nil, fmt.Errorf("failed to parse private key: %s", err.Error())
+	} else if privateKey == nil {
+		return nil, fmt.Errorf("failed to parse private ket: return nil, unknown reason")
+	}
+
+	return privateKey, nil
+}

+ 3 - 1
src/utils/x509.go

@@ -15,7 +15,9 @@ func ReadCertificate(data []byte) (*x509.Certificate, error) {
 
 	cert, err := x509.ParseCertificate(block.Bytes)
 	if err != nil {
-		return nil, fmt.Errorf("failed to parse certificate: %v", err)
+		return nil, fmt.Errorf("failed to parse certificate: %s", err.Error())
+	} else if cert == nil {
+		return nil, fmt.Errorf("failed to parse certificate: return nil, unknown reason")
 	}
 
 	return cert, nil