feat(inputs.x509_cert): add smtp protocol (#11271)

Co-authored-by: dreiekk <dreiekk@users.noreply.github.com>
This commit is contained in:
skillor 2022-06-15 18:46:26 +02:00 committed by GitHub
parent 72e91baeac
commit 05285a1fdb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 55 additions and 5 deletions

View File

@ -1,7 +1,7 @@
# x509 Certificate Input Plugin
This plugin provides information about X509 certificate accessible via local
file or network connection.
file, tcp, udp, https or smtp protocol.
When using a UDP address as a certificate source, the server must support
[DTLS](https://en.wikipedia.org/wiki/Datagram_Transport_Layer_Security).
@ -14,7 +14,8 @@ When using a UDP address as a certificate source, the server must support
## List certificate sources, support wildcard expands for files
## Prefix your entry with 'file://' if you intend to use relative paths
sources = ["tcp://example.org:443", "https://influxdata.com:443",
"udp://127.0.0.1:4433", "/etc/ssl/certs/ssl-cert-snakeoil.pem",
"smtp://mail.localhost:25", "udp://127.0.0.1:4433",
"/etc/ssl/certs/ssl-cert-snakeoil.pem",
"/etc/mycerts/*.mydomain.org.pem", "file:///path/to/*.pem"]
## Timeout for SSL connection

View File

@ -3,7 +3,8 @@
## List certificate sources, support wildcard expands for files
## Prefix your entry with 'file://' if you intend to use relative paths
sources = ["tcp://example.org:443", "https://influxdata.com:443",
"udp://127.0.0.1:4433", "/etc/ssl/certs/ssl-cert-snakeoil.pem",
"smtp://mail.localhost:25", "udp://127.0.0.1:4433",
"/etc/ssl/certs/ssl-cert-snakeoil.pem",
"/etc/mycerts/*.mydomain.org.pem", "file:///path/to/*.pem"]
## Timeout for SSL connection

View File

@ -10,6 +10,7 @@ import (
"encoding/pem"
"fmt"
"net"
"net/smtp"
"net/url"
"os"
"path/filepath"
@ -176,6 +177,53 @@ func (c *X509Cert) getCert(u *url.URL, timeout time.Duration) ([]*x509.Certifica
}
content = rest
}
return certs, nil
case "smtp":
ipConn, err := net.DialTimeout("tcp", u.Host, timeout)
if err != nil {
return nil, err
}
defer ipConn.Close()
serverName, err := c.serverName(u)
if err != nil {
return nil, err
}
c.tlsCfg.ServerName = serverName
c.tlsCfg.InsecureSkipVerify = true
smtpConn, err := smtp.NewClient(ipConn, u.Host)
if err != nil {
return nil, err
}
err = smtpConn.Hello(c.tlsCfg.ServerName)
if err != nil {
return nil, err
}
id, err := smtpConn.Text.Cmd("STARTTLS")
if err != nil {
return nil, err
}
smtpConn.Text.StartResponse(id)
defer smtpConn.Text.EndResponse(id)
_, _, err = smtpConn.Text.ReadResponse(220)
if err != nil {
return nil, fmt.Errorf("did not get 220 after STARTTLS: %s", err.Error())
}
tlsConn := tls.Client(ipConn, c.tlsCfg)
defer tlsConn.Close()
hsErr := tlsConn.Handshake()
if hsErr != nil {
return nil, hsErr
}
certs := tlsConn.ConnectionState().PeerCertificates
return certs, nil
default:
return nil, fmt.Errorf("unsupported scheme '%s' in location %s", u.Scheme, u.String())

View File

@ -355,12 +355,12 @@ func TestGatherCertMustNotTimeout(t *testing.T) {
func TestSourcesToURLs(t *testing.T) {
m := &X509Cert{
Sources: []string{"https://www.influxdata.com:443", "tcp://influxdata.com:443", "file:///dummy_test_path_file.pem", "/tmp/dummy_test_path_glob*.pem"},
Sources: []string{"https://www.influxdata.com:443", "tcp://influxdata.com:443", "smtp://influxdata.com:25", "file:///dummy_test_path_file.pem", "/tmp/dummy_test_path_glob*.pem"},
}
require.NoError(t, m.Init())
require.Equal(t, len(m.globpaths), 2)
require.Equal(t, len(m.locations), 2)
require.Equal(t, len(m.locations), 3)
}
func TestServerName(t *testing.T) {