prometheus/node_exporter · error
failed to open sysfs
Error message
failed to open sysfs: %w
What it means
NewNVMeSubsystemCollector constructs a collector that reads NVMe-oF subsystem health from /sys/class/nvme-subsystem/ via the sysfs package. It calls sysfs.NewFS(*sysPath), where sysPath is the --path.sysfs flag, and wraps any failure in "failed to open sysfs". NewFS fails when the given path does not exist or is not usable as a filesystem root, so the collector cannot be constructed.
Solutions
- Mount or verify sysfs exists at the configured path (default /sys): check `ls /sys/class/nvme-subsystem` and mount -t sysfs sysfs /sys if missing
- Fix the --path.sysfs flag to point at a real sysfs root
- For tests, run `make test` (or unpack collector/fixtures/sys.ttar) so the sysfs fixtures exist
- Confirm NVMe-oF subsystems are present; note an empty /sys/class/nvme-subsystem is not this error (missing dir at Update time maps to ErrNoData instead)
Example fix
// before node_exporter --path.sysfs=/host/sys # path missing in container // after node_exporter --path.sysfs=/sys # or bind-mount host sysfs: -v /sys:/host/sys:ro
Defensive patterns
Strategy: try-catch
Validate before calling
if _, err := os.Stat(*sysPath); err != nil { return fmt.Errorf("sysfs path %q missing: %w", *sysPath, err) } Type guard
func sysfsAvailable(path string) bool { st, err := os.Stat(path); return err == nil && st.IsDir() } Try / catch
c, err := collector.NewNVMeSubsystemCollector(logger)
if err != nil {
if strings.Contains(err.Error(), "failed to open sysfs") {
logger.Warn("sysfs unavailable, NVMe metrics disabled", "err", err)
return nil // degrade gracefully
}
return err
} Prevention
- Verify /sys is mounted before starting node_exporter in containers
- Always pass a valid --path.sysfs; never point it at an empty placeholder dir
- Unpack test fixtures (make test) before running collector unit tests
- Bind-mount host /sys read-only when running in Docker/Kubernetes
When it happens
Trigger: NewNVMeSubsystemCollector returns this when sysfs.NewFS(*sysPath) fails: --path.sysfs points to a nonexistent path, or the path exists but statfs/mount checks fail (e.g. /sys not mounted, as in containers without sysfs, or a test fixture path that is missing).
Common situations: Running node_exporter in a minimal container or chroot without /sys mounted; passing a wrong --path.sysfs value; unit tests using newTestNVMeSubsystemCollector with a fixture directory that was not unpacked (make test unpacks collector/fixtures/sys.ttar); unrelated collector code reused on non-Linux.
Understand the failure class
Background: "open() failed", "failed to open file", "cannot create file" — what a file open error means and how to fix it — this error's family across 42 libraries.
Related errors
- failed to open sysfs
- failed to open sysfs
- failed to open sysfs
- failed to open sysfs
- error obtaining NVMe class info
AI-assisted analysis of prometheus/node_exporter@17ddd77c59 (2026-09-07).
Data as JSON: /api/errors/cbcf8937f0c3ca61.
Report an issue: GitHub.
Appendix: source
Thrown at collector/nvmesubsystem_linux.go:105
)
nvmesubsystemPathState = prometheus.NewDesc(
prometheus.BuildFQName(namespace, "nvmesubsystem", "path_state"),
"Current NVMe controller path state (1 for the current state, 0 for all others).",
[]string{"subsystem", "controller", "transport", "state"}, nil,
)
)
type nvmeSubsystemCollector struct {
fs sysfs.FS
logger *slog.Logger
}
// NewNVMeSubsystemCollector returns a new Collector exposing NVMe-oF subsystem
// path health from /sys/class/nvme-subsystem/.
func NewNVMeSubsystemCollector(logger *slog.Logger) (Collector, error) {
fs, err := sysfs.NewFS(*sysPath)
if err != nil {
return nil, fmt.Errorf("failed to open sysfs: %w", err)
}
return &nvmeSubsystemCollector{
fs: fs,
logger: logger,
}, nil
}
func (c *nvmeSubsystemCollector) Update(ch chan<- prometheus.Metric) error {
subsystems, err := c.fs.NVMeSubsystemClass()
if err != nil {
if errors.Is(err, os.ErrNotExist) || errors.Is(err, os.ErrPermission) {
c.logger.Debug("Could not read NVMe subsystem info", "err", err)
return ErrNoData
}
return fmt.Errorf("failed to scan NVMe subsystems: %w", err)
}
View on GitHub (pinned to 17ddd77c59)