package src import ( "bytes" "crypto/cipher" "crypto/des" "crypto/rand" "crypto/rsa" "crypto/x509" "encoding/pem" "github.com/gin-gonic/gin" "io" "log" "os" "path" "path/filepath" "strconv" ) func InitHttpServer(host string, port int) { log.Println("Start http server, Listen " + strconv.Itoa(port)) h := gin.Default() h.GET("/api/v1/refresh", refreshCert) h.GET("/api/v1/cert", getCert) err := h.Run(host + ":" + strconv.Itoa(port)) if err != nil { return } } func getCert(c *gin.Context) { name := c.Param("name") token := getToken(c) dir := GetAppConfig().CertDir dir = filepath.Join(dir, name) _, err := os.Stat(dir) if os.IsNotExist(err) { c.JSON(200, gin.H{ "code": 500, "msg": "Name does not exist.", }) return } crtFilePath := path.Join(dir, CertFileName) crtContent, err := os.ReadFile(crtFilePath) if err != nil { c.JSON(200, gin.H{ "code": 500, "msg": "Failed to read crt file.", }) return } crt := string(crtContent) keyFilePath := path.Join(dir, KeyFileName) keyContent, err := os.ReadFile(keyFilePath) if err != nil { c.JSON(200, gin.H{ "code": 500, "msg": "Failed to read key file.", }) return } key := string(keyContent) c.JSON(200, gin.H{ "code": 200, "msg": "Success", "data": gin.H{ "crt": encryptResult(crt, token), "key": encryptResult(key, token), }, }) } func refreshCert(c *gin.Context) { name := c.Param("name") domain := GetAppConfig().FindDomain(name) if domain == nil { c.JSON(200, gin.H{ "code": 500, "msg": "Name does not exist.", }) return } Apply(*domain) c.JSON(200, gin.H{ "code": 200, "msg": "Success", }) } func getToken(c *gin.Context) (token string) { token = decryptParam(c.Param("token")) return } func decryptParam(param string) string { priKey := GetAppConfig().Encrypt.PriKey // 使用RSA解密 block, _ := pem.Decode([]byte(priKey)) if block == nil { log.Fatal("failed to parse PEM block containing the private key") } privateKey, err := x509.ParsePKCS1PrivateKey(block.Bytes) if err != nil { log.Fatal(err) } paramData := []byte(param) plaintext, err := rsa.DecryptPKCS1v15(nil, privateKey, paramData) if err != nil { log.Fatal(err) } return string(plaintext) } func encryptResult(content string, token string) string { key := []byte(token) plaintext := []byte(content) block, err := des.NewCipher(key) if err != nil { log.Fatal(err) } plaintext = pad(plaintext, block.BlockSize()) iv := make([]byte, block.BlockSize()) if _, err := io.ReadFull(rand.Reader, iv); err != nil { log.Fatal("Error generating random IV:", err) } mode := cipher.NewCBCEncrypter(block, iv) ciphertext := make([]byte, len(plaintext)) mode.CryptBlocks(ciphertext, plaintext) return string(ciphertext) } func pad(src []byte, blockSize int) []byte { padding := blockSize - len(src)%blockSize padText := bytes.Repeat([]byte{byte(padding)}, padding) return append(src, padText...) }