feat: implement local, ssh, webhook Deployer
This commit is contained in:
17
internal/pkg/core/deployer/providers/local/define.go
Normal file
17
internal/pkg/core/deployer/providers/local/define.go
Normal file
@@ -0,0 +1,17 @@
|
||||
package local
|
||||
|
||||
type OutputFormatType string
|
||||
|
||||
const (
|
||||
OUTPUT_FORMAT_PEM = OutputFormatType("PEM")
|
||||
OUTPUT_FORMAT_PFX = OutputFormatType("PFX")
|
||||
OUTPUT_FORMAT_JKS = OutputFormatType("JKS")
|
||||
)
|
||||
|
||||
type ShellEnvType string
|
||||
|
||||
const (
|
||||
SHELL_ENV_SH = ShellEnvType("sh")
|
||||
SHELL_ENV_CMD = ShellEnvType("cmd")
|
||||
SHELL_ENV_POWERSHELL = ShellEnvType("powershell")
|
||||
)
|
||||
177
internal/pkg/core/deployer/providers/local/local.go
Normal file
177
internal/pkg/core/deployer/providers/local/local.go
Normal file
@@ -0,0 +1,177 @@
|
||||
package local
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"errors"
|
||||
"fmt"
|
||||
"os/exec"
|
||||
"runtime"
|
||||
|
||||
xerrors "github.com/pkg/errors"
|
||||
|
||||
"github.com/usual2970/certimate/internal/pkg/core/deployer"
|
||||
"github.com/usual2970/certimate/internal/pkg/utils/fs"
|
||||
"github.com/usual2970/certimate/internal/pkg/utils/x509"
|
||||
)
|
||||
|
||||
type LocalDeployerConfig struct {
|
||||
// Shell 执行环境。
|
||||
// 空值时默认根据操作系统决定。
|
||||
ShellEnv ShellEnvType `json:"shellEnv,omitempty"`
|
||||
// 前置命令。
|
||||
PreCommand string `json:"preCommand,omitempty"`
|
||||
// 后置命令。
|
||||
PostCommand string `json:"postCommand,omitempty"`
|
||||
// 输出证书格式。
|
||||
// 空值时默认为 [OUTPUT_FORMAT_PEM]。
|
||||
OutputFormat OutputFormatType `json:"outputFormat,omitempty"`
|
||||
// 输出证书文件路径。
|
||||
OutputCertPath string `json:"outputCertPath,omitempty"`
|
||||
// 输出私钥文件路径。
|
||||
OutputKeyPath string `json:"outputKeyPath,omitempty"`
|
||||
// PFX 导出密码。
|
||||
// 证书格式为 PFX 时必填。
|
||||
PfxPassword string `json:"pfxPassword,omitempty"`
|
||||
// JKS 别名。
|
||||
// 证书格式为 JKS 时必填。
|
||||
JksAlias string `json:"jksAlias,omitempty"`
|
||||
// JKS 密钥密码。
|
||||
// 证书格式为 JKS 时必填。
|
||||
JksKeypass string `json:"jksKeypass,omitempty"`
|
||||
// JKS 存储密码。
|
||||
// 证书格式为 JKS 时必填。
|
||||
JksStorepass string `json:"jksStorepass,omitempty"`
|
||||
}
|
||||
|
||||
type LocalDeployer struct {
|
||||
config *LocalDeployerConfig
|
||||
logger deployer.Logger
|
||||
}
|
||||
|
||||
func New(config *LocalDeployerConfig) (*LocalDeployer, error) {
|
||||
return NewWithLogger(config, deployer.NewNilLogger())
|
||||
}
|
||||
|
||||
func NewWithLogger(config *LocalDeployerConfig, logger deployer.Logger) (*LocalDeployer, error) {
|
||||
if config == nil {
|
||||
return nil, errors.New("config is nil")
|
||||
}
|
||||
|
||||
if logger == nil {
|
||||
return nil, errors.New("logger is nil")
|
||||
}
|
||||
|
||||
return &LocalDeployer{
|
||||
logger: logger,
|
||||
config: config,
|
||||
}, nil
|
||||
}
|
||||
|
||||
func (d *LocalDeployer) Deploy(ctx context.Context, certPem string, privkeyPem string) (*deployer.DeployResult, error) {
|
||||
// 执行前置命令
|
||||
if d.config.PreCommand != "" {
|
||||
stdout, stderr, err := execCommand(d.config.ShellEnv, d.config.PreCommand)
|
||||
if err != nil {
|
||||
return nil, xerrors.Wrapf(err, "failed to run pre-command, stdout: %s, stderr: %s", stdout, stderr)
|
||||
}
|
||||
|
||||
d.logger.Appendt("pre-command executed", stdout)
|
||||
}
|
||||
|
||||
// 写入证书和私钥文件
|
||||
switch d.config.OutputFormat {
|
||||
case "", OUTPUT_FORMAT_PEM:
|
||||
if err := fs.WriteFileString(d.config.OutputCertPath, certPem); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("certificate file saved")
|
||||
|
||||
if err := fs.WriteFileString(d.config.OutputKeyPath, privkeyPem); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("private key file saved")
|
||||
|
||||
case OUTPUT_FORMAT_PFX:
|
||||
pfxData, err := x509.TransformCertificateFromPEMToPFX(certPem, privkeyPem, d.config.PfxPassword)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("certificate transformed to PFX")
|
||||
|
||||
if err := fs.WriteFile(d.config.OutputCertPath, pfxData); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("certificate file saved")
|
||||
|
||||
case OUTPUT_FORMAT_JKS:
|
||||
jksData, err := x509.TransformCertificateFromPEMToJKS(certPem, privkeyPem, d.config.JksAlias, d.config.JksKeypass, d.config.JksStorepass)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("certificate transformed to JKS")
|
||||
|
||||
if err := fs.WriteFile(d.config.OutputCertPath, jksData); err != nil {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
d.logger.Appendt("certificate file uploaded")
|
||||
|
||||
default:
|
||||
return nil, fmt.Errorf("unsupported output format: %s", d.config.OutputFormat)
|
||||
}
|
||||
|
||||
// 执行后置命令
|
||||
if d.config.PostCommand != "" {
|
||||
stdout, stderr, err := execCommand(d.config.ShellEnv, d.config.PostCommand)
|
||||
if err != nil {
|
||||
return nil, xerrors.Wrapf(err, "failed to run command, stdout: %s, stderr: %s", stdout, stderr)
|
||||
}
|
||||
|
||||
d.logger.Appendt("post-command executed", stdout)
|
||||
}
|
||||
|
||||
return &deployer.DeployResult{}, nil
|
||||
}
|
||||
|
||||
func execCommand(shellEnv ShellEnvType, command string) (string, string, error) {
|
||||
var cmd *exec.Cmd
|
||||
|
||||
switch shellEnv {
|
||||
case SHELL_ENV_SH:
|
||||
cmd = exec.Command("sh", "-c", command)
|
||||
|
||||
case SHELL_ENV_CMD:
|
||||
cmd = exec.Command("cmd", "/C", command)
|
||||
|
||||
case SHELL_ENV_POWERSHELL:
|
||||
cmd = exec.Command("powershell", "-Command", command)
|
||||
|
||||
case "":
|
||||
if runtime.GOOS == "windows" {
|
||||
cmd = exec.Command("cmd", "/C", command)
|
||||
} else {
|
||||
cmd = exec.Command("sh", "-c", command)
|
||||
}
|
||||
|
||||
default:
|
||||
return "", "", fmt.Errorf("unsupported shell env: %s", shellEnv)
|
||||
}
|
||||
|
||||
var stdoutBuf bytes.Buffer
|
||||
cmd.Stdout = &stdoutBuf
|
||||
var stderrBuf bytes.Buffer
|
||||
cmd.Stderr = &stderrBuf
|
||||
|
||||
err := cmd.Run()
|
||||
if err != nil {
|
||||
return "", "", xerrors.Wrap(err, "failed to execute shell command")
|
||||
}
|
||||
|
||||
return stdoutBuf.String(), stderrBuf.String(), nil
|
||||
}
|
||||
Reference in New Issue
Block a user