Skip to content

Allow config files to import/include other config files (in-file split for custom commands) #6152

Open

Description

@HaleTom

Is your feature request related to a problem? Please describe.

I split complex custom commands into their own files (e.g. all tag-related commands in tags.yml, loaded via LG_CONFIG_FILE=".../config.yml,.../tags.yml"). This works, but the file list lives outside the config itself: it must be re-declared in every shell/launcher via the env var (or --use-config-file), and it grows with each additional split file. There is no way for config.yml to pull in another file on its own, so a dotfiles-managed config directory still depends on shell wiring to load completely.

Describe the solution you'd like

Support an in-file key, e.g. import: ["tags.yml"] (paths resolved relative to the importing file), with entries processed in listed order using the exact merge rules LG_CONFIG_FILE uses today (per-key override with last-file-wins, customCommands appended across files, Validate() per file). Cycle safety is cheap: keep a visited set of canonicalized absolute paths (filepath.Abs + EvalSymlinks) and merge each file once. The existing loadUserConfig loop already merges an ordered file list, so this only changes how that list is built.

Describe alternatives you've considered

  • LG_CONFIG_FILE comma-separated list (status quo): works, but it is process-global and maintained separately from the files it references.
  • Repo-scoped files (.git/lazygit.yml, parent-dir .lazygit.yml): wrong scope, they are per-repo rather than a global grouping mechanism.

Additional context

Related history: #1255 (2021) asked about extending/splitting config and was resolved by documenting the LG_CONFIG_FILE list; an in-file import was never evaluated there. I searched open and closed issues for "import config include", "include config file", and "multiple config files" and found no duplicate request for an in-file import directive.

Activity

  1. HaleTom commented on Oct 24, 2026

    @HaleTom
    Author

    Spelling out the cycle/diamond handling, since it's cheaper than it looks — no new merge semantics are needed:

    Linearize, then reuse the existing rules. Resolve import: entries depth-first in listed order into the same ordered file list loadUserConfig already consumes. The current rules then apply unchanged: per-key override with last-file-wins, customCommands appended across files, Validate() per file. A diamond (A imports B and C, both import D) resolves exactly like listing those files in LG_CONFIG_FILE today — same order-dependence, no new conflict-resolution logic.

    Cycles: keep a visited set of canonicalized absolute paths (filepath.Abs + EvalSymlinks, so ./tags.yml, tags.yml, and symlinked spellings compare equal) and merge each file once — #pragma once semantics. An optional depth cap is a cheap backstop, but the visited set alone terminates.

    So the "already supported" part is real: ordering, override, and append semantics all exist and are documented; an import: key would only change how the file list is assembled, not how it's merged.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions