metrics_unix.go 2.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. //go:build !windows
  2. // +build !windows
  3. package daemon // import "github.com/docker/docker/daemon"
  4. import (
  5. "net"
  6. "net/http"
  7. "path/filepath"
  8. "strings"
  9. "time"
  10. "github.com/docker/docker/pkg/plugingetter"
  11. "github.com/docker/docker/pkg/plugins"
  12. "github.com/docker/docker/plugin"
  13. metrics "github.com/docker/go-metrics"
  14. specs "github.com/opencontainers/runtime-spec/specs-go"
  15. "github.com/pkg/errors"
  16. "github.com/sirupsen/logrus"
  17. "golang.org/x/sys/unix"
  18. )
  19. func (daemon *Daemon) listenMetricsSock() (string, error) {
  20. path := filepath.Join(daemon.configStore.ExecRoot, "metrics.sock")
  21. unix.Unlink(path)
  22. l, err := net.Listen("unix", path)
  23. if err != nil {
  24. return "", errors.Wrap(err, "error setting up metrics plugin listener")
  25. }
  26. mux := http.NewServeMux()
  27. mux.Handle("/metrics", metrics.Handler())
  28. go func() {
  29. logrus.Debugf("metrics API listening on %s", l.Addr())
  30. srv := &http.Server{
  31. Handler: mux,
  32. ReadHeaderTimeout: 5 * time.Minute, // "G112: Potential Slowloris Attack (gosec)"; not a real concern for our use, so setting a long timeout.
  33. }
  34. if err := srv.Serve(l); err != nil && !strings.Contains(err.Error(), "use of closed network connection") {
  35. logrus.WithError(err).Error("error serving metrics API")
  36. }
  37. }()
  38. daemon.metricsPluginListener = l
  39. return path, nil
  40. }
  41. func registerMetricsPluginCallback(store *plugin.Store, sockPath string) {
  42. store.RegisterRuntimeOpt(metricsPluginType, func(s *specs.Spec) {
  43. f := plugin.WithSpecMounts([]specs.Mount{
  44. {Type: "bind", Source: sockPath, Destination: "/run/docker/metrics.sock", Options: []string{"bind", "ro"}},
  45. })
  46. f(s)
  47. })
  48. store.Handle(metricsPluginType, func(name string, client *plugins.Client) {
  49. // Use lookup since nothing in the system can really reference it, no need
  50. // to protect against removal
  51. p, err := store.Get(name, metricsPluginType, plugingetter.Lookup)
  52. if err != nil {
  53. return
  54. }
  55. adapter, err := makePluginAdapter(p)
  56. if err != nil {
  57. logrus.WithError(err).WithField("plugin", p.Name()).Error("Error creating plugin adapter")
  58. }
  59. if err := adapter.StartMetrics(); err != nil {
  60. logrus.WithError(err).WithField("plugin", p.Name()).Error("Error starting metrics collector plugin")
  61. }
  62. })
  63. }