mirror of
https://github.com/minio/minio.git
synced 2025-01-11 15:03:22 -05:00
Add support for mTLS for Audit log target (#11645)
This commit is contained in:
parent
10bdb78699
commit
bbd1244a88
@ -553,7 +553,7 @@ If you need help to migrate smoothly visit: https://min.io/pricing`
|
|||||||
http.WithAuthToken(l.AuthToken),
|
http.WithAuthToken(l.AuthToken),
|
||||||
http.WithUserAgent(loggerUserAgent),
|
http.WithUserAgent(loggerUserAgent),
|
||||||
http.WithLogKind(string(logger.All)),
|
http.WithLogKind(string(logger.All)),
|
||||||
http.WithTransport(NewGatewayHTTPTransport()),
|
http.WithTransport(NewGatewayHTTPTransportWithClientCerts(l.ClientCert, l.ClientKey)),
|
||||||
),
|
),
|
||||||
); err != nil {
|
); err != nil {
|
||||||
logger.LogIf(ctx, fmt.Errorf("Unable to initialize audit HTTP target: %w", err))
|
logger.LogIf(ctx, fmt.Errorf("Unable to initialize audit HTTP target: %w", err))
|
||||||
|
@ -23,6 +23,7 @@ import (
|
|||||||
"crypto/tls"
|
"crypto/tls"
|
||||||
"crypto/x509"
|
"crypto/x509"
|
||||||
"encoding/pem"
|
"encoding/pem"
|
||||||
|
"errors"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
|
|
||||||
"github.com/minio/minio/pkg/env"
|
"github.com/minio/minio/pkg/env"
|
||||||
@ -113,3 +114,12 @@ func LoadX509KeyPair(certFile, keyFile string) (tls.Certificate, error) {
|
|||||||
}
|
}
|
||||||
return cert, nil
|
return cert, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// EnsureCertAndKey checks if both client certificate and key paths are provided
|
||||||
|
func EnsureCertAndKey(ClientCert, ClientKey string) error {
|
||||||
|
if (ClientCert != "" && ClientKey == "") ||
|
||||||
|
(ClientCert == "" && ClientKey != "") {
|
||||||
|
return errors.New("cert and key must be specified as a pair")
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
@ -30,9 +30,11 @@ type Console struct {
|
|||||||
|
|
||||||
// HTTP logger target
|
// HTTP logger target
|
||||||
type HTTP struct {
|
type HTTP struct {
|
||||||
Enabled bool `json:"enabled"`
|
Enabled bool `json:"enabled"`
|
||||||
Endpoint string `json:"endpoint"`
|
Endpoint string `json:"endpoint"`
|
||||||
AuthToken string `json:"authToken"`
|
AuthToken string `json:"authToken"`
|
||||||
|
ClientCert string `json:"clientCert"`
|
||||||
|
ClientKey string `json:"clientKey"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Config console and http logger targets
|
// Config console and http logger targets
|
||||||
@ -44,16 +46,20 @@ type Config struct {
|
|||||||
|
|
||||||
// HTTP endpoint logger
|
// HTTP endpoint logger
|
||||||
const (
|
const (
|
||||||
Endpoint = "endpoint"
|
Endpoint = "endpoint"
|
||||||
AuthToken = "auth_token"
|
AuthToken = "auth_token"
|
||||||
|
ClientCert = "client_cert"
|
||||||
|
ClientKey = "client_key"
|
||||||
|
|
||||||
EnvLoggerWebhookEnable = "MINIO_LOGGER_WEBHOOK_ENABLE"
|
EnvLoggerWebhookEnable = "MINIO_LOGGER_WEBHOOK_ENABLE"
|
||||||
EnvLoggerWebhookEndpoint = "MINIO_LOGGER_WEBHOOK_ENDPOINT"
|
EnvLoggerWebhookEndpoint = "MINIO_LOGGER_WEBHOOK_ENDPOINT"
|
||||||
EnvLoggerWebhookAuthToken = "MINIO_LOGGER_WEBHOOK_AUTH_TOKEN"
|
EnvLoggerWebhookAuthToken = "MINIO_LOGGER_WEBHOOK_AUTH_TOKEN"
|
||||||
|
|
||||||
EnvAuditWebhookEnable = "MINIO_AUDIT_WEBHOOK_ENABLE"
|
EnvAuditWebhookEnable = "MINIO_AUDIT_WEBHOOK_ENABLE"
|
||||||
EnvAuditWebhookEndpoint = "MINIO_AUDIT_WEBHOOK_ENDPOINT"
|
EnvAuditWebhookEndpoint = "MINIO_AUDIT_WEBHOOK_ENDPOINT"
|
||||||
EnvAuditWebhookAuthToken = "MINIO_AUDIT_WEBHOOK_AUTH_TOKEN"
|
EnvAuditWebhookAuthToken = "MINIO_AUDIT_WEBHOOK_AUTH_TOKEN"
|
||||||
|
EnvAuditWebhookClientCert = "MINIO_AUDIT_WEBHOOK_CLIENT_CERT"
|
||||||
|
EnvAuditWebhookClientKey = "MINIO_AUDIT_WEBHOOK_CLIENT_KEY"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Default KVS for loggerHTTP and loggerAuditHTTP
|
// Default KVS for loggerHTTP and loggerAuditHTTP
|
||||||
@ -85,6 +91,14 @@ var (
|
|||||||
Key: AuthToken,
|
Key: AuthToken,
|
||||||
Value: "",
|
Value: "",
|
||||||
},
|
},
|
||||||
|
config.KV{
|
||||||
|
Key: ClientCert,
|
||||||
|
Value: "",
|
||||||
|
},
|
||||||
|
config.KV{
|
||||||
|
Key: ClientKey,
|
||||||
|
Value: "",
|
||||||
|
},
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -251,10 +265,24 @@ func LookupConfig(scfg config.Config) (Config, error) {
|
|||||||
if target != config.Default {
|
if target != config.Default {
|
||||||
authTokenEnv = EnvAuditWebhookAuthToken + config.Default + target
|
authTokenEnv = EnvAuditWebhookAuthToken + config.Default + target
|
||||||
}
|
}
|
||||||
|
clientCertEnv := EnvAuditWebhookClientCert
|
||||||
|
if target != config.Default {
|
||||||
|
clientCertEnv = EnvAuditWebhookClientCert + config.Default + target
|
||||||
|
}
|
||||||
|
clientKeyEnv := EnvAuditWebhookClientKey
|
||||||
|
if target != config.Default {
|
||||||
|
clientKeyEnv = EnvAuditWebhookClientKey + config.Default + target
|
||||||
|
}
|
||||||
|
err = config.EnsureCertAndKey(env.Get(clientCertEnv, ""), env.Get(clientKeyEnv, ""))
|
||||||
|
if err != nil {
|
||||||
|
return cfg, err
|
||||||
|
}
|
||||||
cfg.Audit[target] = HTTP{
|
cfg.Audit[target] = HTTP{
|
||||||
Enabled: true,
|
Enabled: true,
|
||||||
Endpoint: env.Get(endpointEnv, ""),
|
Endpoint: env.Get(endpointEnv, ""),
|
||||||
AuthToken: env.Get(authTokenEnv, ""),
|
AuthToken: env.Get(authTokenEnv, ""),
|
||||||
|
ClientCert: env.Get(clientCertEnv, ""),
|
||||||
|
ClientKey: env.Get(clientKeyEnv, ""),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -307,10 +335,16 @@ func LookupConfig(scfg config.Config) (Config, error) {
|
|||||||
if !enabled {
|
if !enabled {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
err = config.EnsureCertAndKey(kv.Get(ClientCert), kv.Get(ClientKey))
|
||||||
|
if err != nil {
|
||||||
|
return cfg, err
|
||||||
|
}
|
||||||
cfg.Audit[starget] = HTTP{
|
cfg.Audit[starget] = HTTP{
|
||||||
Enabled: true,
|
Enabled: true,
|
||||||
Endpoint: kv.Get(Endpoint),
|
Endpoint: kv.Get(Endpoint),
|
||||||
AuthToken: kv.Get(AuthToken),
|
AuthToken: kv.Get(AuthToken),
|
||||||
|
ClientCert: kv.Get(ClientCert),
|
||||||
|
ClientKey: kv.Get(ClientKey),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,7 +16,9 @@
|
|||||||
|
|
||||||
package logger
|
package logger
|
||||||
|
|
||||||
import "github.com/minio/minio/cmd/config"
|
import (
|
||||||
|
"github.com/minio/minio/cmd/config"
|
||||||
|
)
|
||||||
|
|
||||||
// Help template for logger http and audit
|
// Help template for logger http and audit
|
||||||
var (
|
var (
|
||||||
@ -58,5 +60,17 @@ var (
|
|||||||
Optional: true,
|
Optional: true,
|
||||||
Type: "sentence",
|
Type: "sentence",
|
||||||
},
|
},
|
||||||
|
config.HelpKV{
|
||||||
|
Key: ClientCert,
|
||||||
|
Description: "mTLS certificate for Audit Webhook authentication",
|
||||||
|
Optional: true,
|
||||||
|
Type: "string",
|
||||||
|
},
|
||||||
|
config.HelpKV{
|
||||||
|
Key: ClientKey,
|
||||||
|
Description: "mTLS certificate key for Audit Webhook authentication",
|
||||||
|
Optional: true,
|
||||||
|
Type: "string",
|
||||||
|
},
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
20
cmd/utils.go
20
cmd/utils.go
@ -43,6 +43,7 @@ import (
|
|||||||
"github.com/gorilla/mux"
|
"github.com/gorilla/mux"
|
||||||
xhttp "github.com/minio/minio/cmd/http"
|
xhttp "github.com/minio/minio/cmd/http"
|
||||||
"github.com/minio/minio/cmd/logger"
|
"github.com/minio/minio/cmd/logger"
|
||||||
|
"github.com/minio/minio/pkg/certs"
|
||||||
"github.com/minio/minio/pkg/handlers"
|
"github.com/minio/minio/pkg/handlers"
|
||||||
"github.com/minio/minio/pkg/madmin"
|
"github.com/minio/minio/pkg/madmin"
|
||||||
"golang.org/x/net/http2"
|
"golang.org/x/net/http2"
|
||||||
@ -606,6 +607,25 @@ func newCustomHTTPTransport(tlsConfig *tls.Config, dialTimeout time.Duration) fu
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// NewGatewayHTTPTransportWithClientCerts returns a new http configuration
|
||||||
|
// used while communicating with the cloud backends.
|
||||||
|
func NewGatewayHTTPTransportWithClientCerts(clientCert, clientKey string) *http.Transport {
|
||||||
|
transport := newGatewayHTTPTransport(1 * time.Minute)
|
||||||
|
if clientCert != "" && clientKey != "" {
|
||||||
|
ctx, cancel := context.WithTimeout(context.Background(), time.Second)
|
||||||
|
defer cancel()
|
||||||
|
c, err := certs.NewManager(ctx, clientCert, clientKey, tls.LoadX509KeyPair)
|
||||||
|
if err != nil {
|
||||||
|
logger.LogIf(ctx, fmt.Errorf("failed to load client key and cert, please check your endpoint configuration: %s",
|
||||||
|
err.Error()))
|
||||||
|
}
|
||||||
|
if c != nil {
|
||||||
|
transport.TLSClientConfig.GetClientCertificate = c.GetClientCertificate
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return transport
|
||||||
|
}
|
||||||
|
|
||||||
// NewGatewayHTTPTransport returns a new http configuration
|
// NewGatewayHTTPTransport returns a new http configuration
|
||||||
// used while communicating with the cloud backends.
|
// used while communicating with the cloud backends.
|
||||||
func NewGatewayHTTPTransport() *http.Transport {
|
func NewGatewayHTTPTransport() *http.Transport {
|
||||||
|
@ -38,7 +38,7 @@ minio server /mnt/data
|
|||||||
Assuming `mc` is already [configured](https://docs.min.io/docs/minio-client-quickstart-guide.html)
|
Assuming `mc` is already [configured](https://docs.min.io/docs/minio-client-quickstart-guide.html)
|
||||||
```
|
```
|
||||||
mc admin config get myminio/ audit_webhook
|
mc admin config get myminio/ audit_webhook
|
||||||
audit_webhook:name1 auth_token="" endpoint=""
|
audit_webhook:name1 enable=off endpoint= auth_token= client_cert= client_key=
|
||||||
```
|
```
|
||||||
|
|
||||||
```
|
```
|
||||||
@ -53,6 +53,8 @@ MinIO also honors environment variable for HTTP target Audit logging as shown be
|
|||||||
export MINIO_AUDIT_WEBHOOK_ENABLE_target1="on"
|
export MINIO_AUDIT_WEBHOOK_ENABLE_target1="on"
|
||||||
export MINIO_AUDIT_WEBHOOK_AUTH_TOKEN_target1="token"
|
export MINIO_AUDIT_WEBHOOK_AUTH_TOKEN_target1="token"
|
||||||
export MINIO_AUDIT_WEBHOOK_ENDPOINT_target1=http://localhost:8080/minio/logs
|
export MINIO_AUDIT_WEBHOOK_ENDPOINT_target1=http://localhost:8080/minio/logs
|
||||||
|
export MINIO_AUDIT_WEBHOOK_CLIENT_CERT="/tmp/cert.pem"
|
||||||
|
export MINIO_AUDIT_WEBHOOK_CLIENT_KEY=="/tmp/key.pem"
|
||||||
minio server /mnt/data
|
minio server /mnt/data
|
||||||
```
|
```
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user