kubernetes/kops · error

creating directories %q: %w

Error message

creating directories %q: %w

What it means

In kOps' OpenTelemetry setup (newTraceProvider), when the OTel exporter destination is a directory, the code ensures it exists with os.MkdirAll(dest, 0755). If directory creation fails, the error is wrapped as "creating directories %q: %w" and OTel SDK setup is aborted. It reports filesystem permission or path problems, wrapped with %w so os.Err* checks work.

Source

Thrown at cmd/kops/otel.go:119

		dest = os.Getenv("OTEL_EXPORTER_OTLP_TRACES_DIR")
		if dest != "" {
			destIsDirectory = true
		}
	}
	if dest == "" {
		dest = os.Getenv("OTEL_EXPORTER_OTLP_DIR")
		if dest != "" {
			destIsDirectory = true
		}
	}
	if dest == "" {
		return nil, nil
	}

	// If we are writing to a directory, construct a (likely) unique name
	if destIsDirectory {
		if err := os.MkdirAll(dest, 0755); err != nil {
			return nil, fmt.Errorf("creating directories %q: %w", dest, err)
		}
		processName, err := os.Executable()
		if err != nil {
			return nil, fmt.Errorf("getting process name: %w", err)
		}
		processName = filepath.Base(processName)
		processName = strings.TrimSuffix(processName, ".exe")
		pid := os.Getpid()
		timestamp := time.Now().UTC().Format(time.RFC3339)
		filename := fmt.Sprintf("%s-%d-%s.otel", processName, pid, timestamp)
		dest = filepath.Join(dest, filename)
	}

	traceExporter, err := otlptracefile.New(ctx, otlptracefile.WithPath(dest))
	if err != nil {
		return nil, err
	}

View on GitHub (pinned to 4c8573c808)

Solutions

  1. Pre-create the directory with correct ownership: mkdir -p <dest> && chmod/chown appropriately for the kOps process user
  2. Verify the path is a directory, not an existing file, and the parent chain is writable
  3. Check the wrapped os error (e.g. mkdir /x: permission denied) and adjust the OTEL destination env var to a writable location such as /tmp/traces

Example fix

# before
OTEL_EXPORTER_OTLP_ENDPOINT=/var/lib/traces   # dir missing, non-root user
# after
mkdir -p /var/lib/traces && chown $(id -u) /var/lib/traces
export OTEL_EXPORTER_OTLP_ENDPOINT=/var/lib/traces
Defensive patterns

Strategy: validation

Validate before calling

dest="$OTEL_EXPORTER_OTLP_ENDPOINT"
if [ -n "$dest" ]; then
  mkdir -p "$dest" 2>/dev/null || { echo "cannot create OTel dest '$dest': check permissions/path"; exit 1; }
  [ -d "$dest" ] || { echo "$dest exists and is not a directory"; exit 1; }
  [ -w "$dest" ] || { echo "$dest not writable by current user"; exit 1; }
fi

Try / catch

provider, shutdown, err := newTraceProvider(ctx, dest)
if err != nil {
	if errors.Is(err, os.ErrPermission) || errors.Is(err, os.ErrNotExist) {
		// degrade gracefully: run without tracing
		return noopTracer(), nil
	}
	return err
}

Prevention

When it happens

Trigger: Running a kOps binary with OTLP file exporter configured (OTEL_EXPORTER_OTLP_ENDPOINT or traces destination set to a directory path) where the parent path does not exist and cannot be created, exists as a file, or the process lacks write permission (e.g. under / or another user's home).

Common situations: Container running as non-root with OTEL_* env vars pointing to /var/lib/traces; a file already exists at the destination path; typo'd path like /tpm instead of /tmp; read-only root filesystem.

Understand the failure class

Background: mkdir permission denied (EACCES): failed to create directory errors explained — this error's family across 32 libraries.

Related errors


AI-assisted analysis of kubernetes/kops@4c8573c808 (2026-09-05). Data as JSON: /api/errors/651e6fb60ca765ff. Report an issue: GitHub.