Ajout export P12
This commit is contained in:
@@ -1,13 +1,16 @@
|
||||
package api
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto/x509"
|
||||
"fmt"
|
||||
"net/http"
|
||||
|
||||
"pki-manager/internal/models"
|
||||
"pki-manager/internal/repository"
|
||||
"pki-manager/internal/services"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
"software.sslmate.com/src/go-pkcs12"
|
||||
)
|
||||
|
||||
type Handlers struct {
|
||||
@@ -334,6 +337,19 @@ func (h *Handlers) DownloadCACertificate(c *gin.Context) {
|
||||
c.String(http.StatusOK, ca.Certificate)
|
||||
}
|
||||
|
||||
func (h *Handlers) DownloadCAPrivateKey(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
cert, err := h.repo.GetCA(c.Request.Context(), id)
|
||||
if err != nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "Certificate not found"})
|
||||
return
|
||||
}
|
||||
|
||||
c.Header("Content-Type", "application/x-pem-file")
|
||||
c.Header("Content-Disposition", "attachment; filename="+cert.CommonName+".key")
|
||||
c.String(http.StatusOK, cert.PrivateKey)
|
||||
}
|
||||
|
||||
func (h *Handlers) DownloadSubCACertificate(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
subca, err := h.repo.GetSubCA(c.Request.Context(), id)
|
||||
@@ -347,6 +363,19 @@ func (h *Handlers) DownloadSubCACertificate(c *gin.Context) {
|
||||
c.String(http.StatusOK, subca.Certificate)
|
||||
}
|
||||
|
||||
func (h *Handlers) DownloadSubCAPrivateKey(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
cert, err := h.repo.GetSubCA(c.Request.Context(), id)
|
||||
if err != nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "Certificate not found"})
|
||||
return
|
||||
}
|
||||
|
||||
c.Header("Content-Type", "application/x-pem-file")
|
||||
c.Header("Content-Disposition", "attachment; filename="+cert.CommonName+".key")
|
||||
c.String(http.StatusOK, cert.PrivateKey)
|
||||
}
|
||||
|
||||
// Download handlers
|
||||
func (h *Handlers) DownloadCertificate(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
@@ -374,6 +403,70 @@ func (h *Handlers) DownloadPrivateKey(c *gin.Context) {
|
||||
c.String(http.StatusOK, cert.PrivateKey)
|
||||
}
|
||||
|
||||
func (h *Handlers) DownloadP12(c *gin.Context) {
|
||||
id := c.Param("id")
|
||||
var p12Data []byte
|
||||
|
||||
cert, err := h.repo.GetCertificate(c.Request.Context(), id)
|
||||
if err != nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "Certificate not found"})
|
||||
return
|
||||
}
|
||||
|
||||
ca, err := h.repo.GetCA(c.Request.Context(), cert.IssuerCAID)
|
||||
if err != nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "Certificate CA not found"})
|
||||
return
|
||||
}
|
||||
|
||||
// Choisir la méthode d'encodage selon la configuration
|
||||
|
||||
x509cert, err := h.cryptoService.ParseCertificate([]byte(cert.Certificate))
|
||||
if err != nil {
|
||||
message := fmt.Sprintf("Certificateformat PEM invalide %s", err)
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": message})
|
||||
return
|
||||
}
|
||||
x509key, err := h.cryptoService.ParsePrivateKey([]byte(cert.PrivateKey))
|
||||
if err != nil {
|
||||
message := fmt.Sprintf("Keyformat PEM invalide %s", err)
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": message})
|
||||
return
|
||||
}
|
||||
|
||||
x509cacert, err := h.cryptoService.ParseCertificate([]byte(ca.Certificate))
|
||||
if err != nil {
|
||||
message := fmt.Sprintf("CA Certificateformat PEM invalide %s", err)
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": message})
|
||||
return
|
||||
}
|
||||
|
||||
caCerts := []*x509.Certificate{x509cacert}
|
||||
|
||||
p12Data, err = pkcs12.Modern.Encode(x509key, x509cert, caCerts, "password")
|
||||
if err != nil {
|
||||
c.JSON(http.StatusNotFound, gin.H{"error": "échec encodage P12"})
|
||||
return
|
||||
}
|
||||
buffer := bytes.NewBuffer(p12Data)
|
||||
securityLevel := c.DefaultQuery("security", "modern")
|
||||
filename := cert.CommonName + ".p12"
|
||||
c.Header("Content-Disposition", fmt.Sprintf(`attachment; filename="%s"`, filename))
|
||||
c.Header("Content-Type", "application/x-pkcs12")
|
||||
c.Header("Content-Length", fmt.Sprintf("%d", buffer.Len()))
|
||||
c.Header("Content-Transfer-Encoding", "binary")
|
||||
c.Header("X-Security-Level", securityLevel)
|
||||
|
||||
// Retourner les données
|
||||
c.DataFromReader(
|
||||
http.StatusOK,
|
||||
int64(buffer.Len()),
|
||||
"application/x-pkcs12",
|
||||
buffer,
|
||||
map[string]string{"Content-Disposition": fmt.Sprintf(`attachment; filename="%s"`, filename)},
|
||||
)
|
||||
}
|
||||
|
||||
// Web Interface
|
||||
func (h *Handlers) ServeWebInterface(c *gin.Context) {
|
||||
c.HTML(http.StatusOK, "index.html", nil)
|
||||
|
||||
@@ -39,6 +39,8 @@ func SetupRoutes(router *gin.Engine, repo repository.Repository, jwtSecret strin
|
||||
ca.PUT("/:id", handlers.UpdateCA)
|
||||
ca.DELETE("/:id", handlers.DeleteCA)
|
||||
ca.GET("/:id/download/cert", handlers.DownloadCACertificate)
|
||||
ca.GET("/:id/download/key", handlers.DownloadCAPrivateKey)
|
||||
|
||||
}
|
||||
|
||||
// SubCA routes
|
||||
@@ -50,6 +52,8 @@ func SetupRoutes(router *gin.Engine, repo repository.Repository, jwtSecret strin
|
||||
subca.PUT("/:id", handlers.UpdateSubCA)
|
||||
subca.DELETE("/:id", handlers.DeleteSubCA)
|
||||
subca.GET("/:id/download/cert", handlers.DownloadSubCACertificate)
|
||||
subca.GET("/:id/download/key", handlers.DownloadSubCAPrivateKey)
|
||||
|
||||
}
|
||||
|
||||
// Certificate routes
|
||||
@@ -62,6 +66,7 @@ func SetupRoutes(router *gin.Engine, repo repository.Repository, jwtSecret strin
|
||||
cert.POST("/:id/revoke", handlers.RevokeCertificate)
|
||||
cert.GET("/:id/download/cert", handlers.DownloadCertificate)
|
||||
cert.GET("/:id/download/key", handlers.DownloadPrivateKey)
|
||||
cert.GET("/:id/download/p12", handlers.DownloadP12)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user