6 Punkte von GN⁺ 2025-10-15 | 2 Kommentare | Auf WhatsApp teilen
  • Software hat sich rasant weiterentwickelt, doch das System der Umgebungsvariablen des Betriebssystems hält noch immer an einer Struktur aus vergangenen Jahrzehnten fest
  • Umgebungsvariablen sind ein globales String-Dictionary, also eine einfache Struktur ohne Namespace und ohne Typen
  • Unter Linux werden Umgebungsvariablen über den Systemaufruf execve vom Elternprozess an den Kindprozess übergeben
  • Bash, glibc, Python usw. verwalten Umgebungsvariablen jeweils als Hashmap, Array oder Dictionary-Wrapper
  • Der POSIX-Standard verlangt nicht, dass Namen nur aus Großbuchstaben bestehen; tatsächlich wird etwa die Verwendung von Kleinbuchstaben empfohlen, was auf flexible Regeln hinweist

Was sind Umgebungsvariablen?

  • Obwohl sich Programmiersprachen schnell weiterentwickelt haben, hat sich die vom Betriebssystem bereitgestellte Basisstruktur zur Prozessausführung – insbesondere der Teil mit den Umgebungsvariablen – kaum verändert
  • Wenn beim Start einer Anwendung Laufzeitparameter ohne separate Datei oder IPC übergeben werden sollen, bleibt in der Praxis oft nur eine auf Umgebungsvariablen basierende Schnittstelle
  • Umgebungsvariablen fungieren als flaches String-Dictionary ohne Namespace und ohne Typen

Struktur zur Erzeugung und Weitergabe von Umgebungsvariablen

  • Umgebungsvariablen sind eine traditionelle Methode zur Übergabe von Werten zwischen Prozessen und werden beim Start eines Kindprozesses vom Elternprozess mitgegeben
    • Das heißt, sie werden vom Elternprozess an den Kindprozess vererbt
  • Unter Linux nimmt der Systemaufruf execve die ausführbare Datei, Argumente und das Array der Umgebungsvariablen (envp) als Parameter entgegen
    • Beispiel für einen ausgeführten Befehl: ls -lah
      • filename: /usr/bin/ls
      • argv: ['ls', '-lah']
      • envp: ['PATH=...','USER=...']
  • Der Elternprozess kann dem Kind die bestehende Umgebung unverändert übergeben oder auch eine vollständig neue Umgebung zusammenstellen
    • Fast alle Werkzeuge (Bash, Pythons subprocess.run, die C-Bibliothek execl usw.) reichen die Umgebungsvariablen unverändert weiter
    • Eine Ausnahme bilden einige Werkzeuge wie login, die eine neue Umgebung aufbauen

Speicherort und interne Verarbeitung von Umgebungsvariablen

  • Der Kernel legt Umgebungsvariablen beim Programmstart als null-terminierte Strings auf dem Stack ab
  • Diese Daten lassen sich vom Programm nicht leicht direkt verändern; üblicherweise werden sie kopiert und in einer eigenen Struktur verwaltet
  • Wie verschiedene Sprachen und Shells Umgebungsvariablen speichern
    • Bash: Verwaltung in einer Hashmap (Dictionary) mit Stack-Struktur
      • Bei jedem Funktionsaufruf wird eine Map mit lokalem Scope erzeugt
      • Nur per export markierte Variablen werden an Kindprozesse weitergegeben
      • Auch mit local deklarierte Variablen können per export an Kindprozesse übergeben werden
        • Beispiel: Mit export PATH wird eine lokale Änderung an Kindprozesse weitergegeben, ohne die globale Umgebung zu beeinflussen
    • glibc (C-Bibliothek): verwaltet environ als dynamisches Array über putenv und getenv
      • Wegen der Array-Struktur haben sowohl Abfragen als auch Änderungen lineare Zeitkomplexität
      • Daher ist sie für die Speicherung leistungsrelevanter Daten ungeeignet
    • Python: stellt intern mit os.environ eine Dictionary-ähnliche Schnittstelle bereit, tatsächlich ist diese aber mit dem environ-Array der C-Bibliothek gekoppelt
      • Bei Änderungen an os.environ wird os.putenv aufgerufen und auch die C-Bibliothek aktualisiert
      • In die Gegenrichtung erfolgt keine Synchronisierung, es gibt also eine Einwegkopplung

Format und zulässiger Bereich von Umgebungsvariablen

  • Linux-Kernel und glibc sind beim Format von Umgebungsvariablen sehr großzügig
    • Derselbe Name kann mehrfach vorkommen und mehrere Werte haben
    • Auch Einträge ohne = sind möglich, und selbst Sonderzeichen wie Emojis sind nicht eingeschränkt
  • Verfügbare Größenbeschränkungen
    • Einzelne Variable: 128 KiB (typisch in x64-Umgebungen)
    • Gesamtsumme: 2 MiB (gemeinsam mit den Kommandozeilenargumenten)
    • Umgebungsvariablen sind auf höchstens ein Viertel des Stack-Speichers begrenzt

Besonderheiten und Edge Cases bei Umgebungsvariablen

  • Bash entfernt bei ungewöhnlichen Umgebungsvariablen (doppelte Namen, Einträge ohne = usw.) doppelte Namen und ignoriert fehlerhafte Einträge
  • Wenn Variablennamen Leerzeichen enthalten, kann Bash sie zwar nicht referenzieren, aber sie lassen sich dennoch an Kindprozesse weitergeben
    • Nushell, Python usw. können beispielsweise Variablen mit Leerzeichen im Namen erzeugen
    • Bash verwaltet solche Einträge in einer separaten Hashmap (invalid_env)

Standardformat und Namensregeln für Umgebungsvariablen

  • Der POSIX-Standard erkennt jeden Namen ohne Gleichheitszeichen (=) als Variable an
    • Offizielle Empfehlung: Im Namen sind nur Großbuchstaben, Ziffern und Unterstriche erlaubt (an erster Stelle keine Ziffer)
    • Kleinbuchstaben-Variablen sind für anwendungsspezifische Namespaces gedacht
    • Standardwerkzeuge verwenden nur Großbuchstaben, doch auch Kleinbuchstaben-Variablen sind zulässig
  • In der Praxis benennen Entwickler Variablen meist im Stil ALL_UPPERCASE
  • Empfohlene Regel: Für Variablennamen den regulären Ausdruck ^[A-Z_][A-Z0-9_]*$ verwenden, für Werte UTF-8
    • Wenn Ausnahmen oder Kompatibilitätsprobleme zu erwarten sind, wird die Verwendung des Portable Character Set (ASCII) aus POSIX empfohlen

Fazit

  • Umgebungsvariablen sind weiterhin eine veraltete, aber unverzichtbare Schnittstelle und bilden die Grenzfläche zwischen Betriebssystem und Anwendung
  • Trotz ihrer strukturellen Grenzen werden sie von Bash, C, Python usw. jeweils auf unterschiedliche Weise gekapselt und genutzt
  • In modernen Systemen werden Konfigurationsverfahren mit klarem Namespace und Typsystem zunehmend wichtiger

2 Kommentare

 
howudoin 2025-10-15

Schien zunächst an Bedeutung zu verlieren, ist mit dem Aufkommen von Docker und der Cloud aber wieder unvermeidlich geworden.

 
GN⁺ 2025-10-15
Hacker-News-Kommentare
  • Ich arbeite als SRE/Sysadmin/DevOps/was auch immer, und obwohl im Blog nur recht unkompliziert über die Standardisierung von Umgebungsvariablen gesprochen wurde, möchte ich darauf hinweisen, dass Alternativen ähnlich frustrierend sein können, besonders wenn Geheimnisse (Secrets) im Spiel sind
    Eine Struktur, bei der eine Anwendung auf einen bestimmten Secret-Store wie Hashicorp Vault/OpenBao/Secrets Manager zugreift, führt schnell zu ernsthaftem Vendor Lock-in, und ein Austausch wird sehr schwierig, weil sich das bis auf Bibliotheksebene ausweitet
    Die Verfügbarkeit von Vault wird dadurch äußerst kritisch, und wenn Upgrades oder Wartung nötig sind, bringt das das Ops-Team stark in Bedrängnis
    Wenn man Geheimnisse über Konfigurationsdateien weitergibt, ist es schwierig, wie man sie darin unterbringt, weil Konfigurationsdateien oft an öffentlich zugänglichen Pfaden liegen
    Am Ende ist man darauf angewiesen, entweder „vor der Übergabe an die App durch ein privilegiertes System in ein Template einzusetzen“ oder „die komplette Konfigurationsdatei im Secret-Store zu speichern und an die App weiterzugeben“
    Template-Arbeit ist fehleranfällig, und auch beim Verschieben der gesamten Konfigurationsdatei in den Secret-Store besteht die Gefahr, dass jemand etwas falsch hochlädt, was zusätzlichen Stress erzeugt
    Heutzutage laufen die meisten Systeme auf Containern, und wenn ein Unternehmen seine Infrastruktur nicht sehr gut im Griff hat, liegen Konfigurationsdateien ständig an seltsamen Orten, was den Mount-Prozess noch verwirrender macht und häufig Fehler verursacht
    Egal ob JSON/YAML/TOML oder ein anderes Format, eigenartige Bugs gehören zum Alltag, zum Beispiel das Norway-Problem in YAML
    Ich habe auch gesehen, dass Secrets über die Kubernetes Secrets API bezogen werden, aber auch das bringt starke Vendor-Lock-in-Probleme mit sich
    Wenn man nicht gerade gezielt ein System wie einen Operator entwirft, würde ich diese Methode nicht aktiv empfehlen
    Ich habe auch Probleme beim Setzen von Umgebungsvariablen über Subprocesses gesehen, aber heutige Teams verwenden meiner Meinung nach eher Message-Bus-basierte Systeme, die robuster sind und unabhängige Skalierung ermöglichen

    • In unserem Team hatten wir einmal die Erfahrung, eine leichte, allgemeine Secrets-Bibliothek zu bauen und dahinter nur vendor-spezifische Backends wie AWS Secrets Manager per Plugin anzubinden
      Mit lokalem Cache und der Möglichkeit, den Cache pro Parameter zu umgehen, blieb die eigentliche vendor-abhängige Logik nur im Backend, während Bibliothek und Anwendung vendor-unabhängig bleiben konnten
      Selbst beim Umstieg auf Vault mussten wir nur ein Backend ergänzen und die Konfiguration ändern, und es funktionierte ohne größere Probleme

    • Ich frage mich, warum die Kubernetes Secret API als Vendor-Lock-in-Problem wahrgenommen wird
      Meinst du Fälle, in denen Deployment-YAMLs für andere Zwecke als Kubernetes-Deployments verwendet werden sollten?
      In den meisten Apps kann man Secrets in den Container mounten und dann als Umgebungsvariablen oder als JSON-Datei in die App injizieren, sodass sie relativ umgebungsunabhängig gelesen und geschrieben werden können
      Soweit ich weiß, kann auch die Verschlüsselung des etcd-Backends über KMS konfiguriert werden

    • Ich verstehe auch nicht ganz, warum das Beziehen von Secrets über die Kubernetes Secrets API Lock-in sein soll
      Grundsätzlich werden K8s-Secrets nicht verschlüsselt gespeichert, deshalb ergibt das meiner Ansicht nach nur Sinn, wenn man (0) ohnehin K8s nutzt, (1) im Control Plane die Verschlüsselung eingerichtet hat und (2) unbedingt zusätzliche Lösungen wie einen CSI-Treiber einsetzt
      Und der Secret Store CSI Driver unterstützt verschiedene Backends wie Conjur, also ist das eher das Gegenteil von Lock-in

    • Aus diesen Gründen nutzen wir für Konfigurationen immer noch hauptsächlich Env Vars und dotenv
      Eine auf Umgebungsvariablen basierende Konfigurationsstruktur ist einfach zu simpel, und sie funktioniert auch gut mit verschiedenen Tools wie Secret-Managern zusammen
      In den letzten Jahren interessiere ich mich zunehmend für YAML-basiertes sOps
      YAML ist wirklich intuitiv, um Anwendungsstruktur für Konfigurationen auszudrücken, und mit sops lässt sich eine partielle Verschlüsselung leicht verwalten
      Das Management von GPG-Schlüsseln ist allerdings etwas mühsam, kann aber mit Vault oder OpenBao gelöst werden
      Allerdings entsteht dabei wieder das Problem von Vendor Lock-in, wobei OpenBao in dieser Hinsicht etwas besser zu sein scheint

    • Man kann Umgebungsvariablen auch aus dem Ergebnis eines Kommandoaufrufs beziehen, sodass sich das ohne Template-Prozess und ohne Vendor Lock-in lösen lässt

  • Noch ein interessanter Fakt: setenv() ist unter POSIX grundlegend kaputt, deshalb sollte man es meiner Meinung nach in Bibliothekscode niemals verwenden
    Selbst in Anwendungscode ist es nur das letzte Mittel und sollte nur verwendet werden, bevor Threads erzeugt werden
    getenv() gibt den Originalzeiger auf die Umgebungsvariable direkt zurück, sodass es keinerlei Schutz gibt, wenn setenv() einen Wert überschreibt
    Man muss damit äußerst vorsichtig sein

    • Um Umgebungsvariablen korrekt zu setzen, ist execve() meiner Meinung nach der richtige Weg
      Diese Methode ist nur dann geeignet, wenn Informationen ausschließlich vor oder nach exec() über Umgebungsvariablen übergeben werden

    • Ich verstehe nicht, warum man in Bibliothekscode überhaupt setenv verwenden sollte

    • Solaris hat dieses Problem gelöst, aber Linux hält immer noch am gleichen Ansatz fest

    • In NetBSD gibt es mit getenv_r() schon lange eine sichere Alternative, und kürzlich wurde sie auch in FreeBSD eingeführt
      macOS wird vermutlich bald folgen
      Es gab bereits Versuche, das in glibc oder POSIX aufzunehmen, aber sie wurden abgelehnt
      Wenn es sich auf mehreren Plattformen verbreitet, wird es vielleicht irgendwann offiziell akzeptiert
      NetBSD-Dokumentation zu getenv_r
      FreeBSD-Commit

  • Umgebungsvariablen werden oft verwendet, um Geheimnisse zu übergeben, aber ich halte das nicht für eine besonders gute Praxis
    Unter Linux können alle Prozesse, die unter demselben Benutzer laufen, gegenseitig ihre Umgebungsvariablen einsehen
    Egal welches Bedrohungsmodell man ansetzt: Gerade auf Entwicklersystemen laufen so viele Prozesse unter demselben Benutzer, dass das besorgniserregend ist
    Dieses Problem wird noch ernster, wenn wie bei LLM-Agenten viele Prozesse außerhalb von Containern herumlaufen
    Außerdem werden Umgebungsvariablen normalerweise unverändert an Kindprozesse vererbt, wodurch sie unnötig breit offengelegt werden, selbst wenn nur ein einziger Prozess das Secret braucht
    systemd zeigt Umgebungsvariablen über DBUS allen System-Clients an, und die offizielle Dokumentation warnt ausdrücklich davor, Secrets in Umgebungsvariablen abzulegen
    Wenn das stimmt, würde das bedeuten, dass Umgebungsvariablen, die in einer nur für root bestimmten Unit gesetzt werden, auch für normale Benutzer sichtbar sein könnten, was für viele Systemadministratoren ziemlich schockierend wäre
    Letztlich scheint mir deshalb nur ein Modell praktikabel, bei dem ein Secret-Manager Geheimnisse über gemeinsam genutzte temporäre Dateien weitergibt, wie bei der op-CLI von 1Password, flask, terraform usw., weil man so sowohl Umgebungsvariablen als auch Klartextdateien vermeiden kann
    systemds Credentials-System ist so aufgebaut. Die Unterstützung dafür ist aber noch schwach
    Wenn jemand einen guten Weg kennt, Secrets ohne Umgebungsvariablen oder Klartextdateien zu übergeben, würde ich das gern hören
    Bei der op-CLI von 1Password ist es zum Beispiel so, dass sie für jede Sitzung meine Zustimmung verlangt, weshalb sie sich für CLI-Sitzungen sicher anfühlt; selbst wenn ein bösartiger Prozess die op-Binärdatei aufruft, wäre eine zusätzliche Genehmigung erforderlich
    Das verbleibende Problem ist nun, wie man dieses Secret an genau den Prozess weitergibt, der es tatsächlich braucht, und damit ist man irgendwie wieder am Ausgangspunkt
    Referenzlink zur offiziellen systemd-Dokumentation über Umgebungsvariablen

    • Seit etwa 2012 sind Umgebungsvariablen so sicher wie normaler Arbeitsspeicher
      Zugehöriger Commit
      Um die Umgebungsvariablen eines anderen Prozesses zu lesen, braucht man zwingend ptrace-Berechtigungen, und wenn man per ptrace ohnehin lesen kann, kann man in Wirklichkeit alle Geheimnisse lesen, daher sei die Sorge bedeutungslos
      Kommandozeileninformationen (cmdline) sind ein anderes Thema, aber Umgebungsvariablen lassen sich auf diese Weise nicht mehr so leicht offenlegen

    • Im Sicherheitsmodell der meisten Betriebssysteme bedeutet das Ausführen unter einem Benutzer im Wesentlichen, dass man alle Rechte dieses Benutzers vollständig überträgt
      Es gibt zwar zusätzliche Sicherheitsmechanismen wie Capsicum in FreeBSD, Landlock, SELinux, AppArmor oder Integrity Labels unter Windows, aber die meisten davon haben deutliche Grenzen
      Letztlich kann ich meine eigenen Prozesse frei beenden, anhalten oder debuggen, und über ptrace/process_vm_readv/ReadProcessMemory usw. kann ich jederzeit auf Secrets in Prozessen zugreifen, die mir gehören
      Es gibt zwar völlig andere Sicherheitsmodelle, etwa echte Capability-basierte Betriebssysteme, aber die meisten Systeme folgen diesem Modell, deshalb muss man seine Grenzen und Verantwortlichkeiten kennen

    • Als gute Methode, Geheimnisse ohne Umgebungsvariablen oder Klartextdateien zu übergeben, fällt mir memfd_secret ein
      memfd_secret-Manpage
      Es gibt dafür nicht viel Unterstützung nach Sprache oder Framework, daher könnte man das insbesondere in Rust oder, falls möglich, auch in Go über FFI ausprobieren
      Ich hatte schon einmal überlegt, das direkt für PHP zu wrappen, habe das aber aufgegeben, weil ich nicht auch noch php-fpm ändern wollte
      In der Praxis wäre es wohl am sichersten, wenn ein Prozessmanager den Secret-Dateideskriptor im Voraus öffnet und an den Kindprozess weiterreicht, sodass er ohne Offenlegung im Speicher oder anderswo genutzt werden kann

    • Das klassische Unix-Sicherheitsmodell wird in leicht verbesserter Form noch immer viel verwendet, hat aber in billigen oder modernen Rechenumgebungen deutliche Grenzen
      Wenn man Geheimnisse vor anderen Prozessen verstecken muss, sollte man die Prozesse grundsätzlich unter verschiedenen Benutzern trennen
      Oder man geht gleich auf einen Remote-Zugriff, was aber ebenfalls Nachteile und zusätzliche Komplexität mit sich bringt

    • Heutzutage wird auf Container-Plattformen eher empfohlen, Konfigurationen oder Secrets über Umgebungsvariablen zu übergeben
      Innerhalb des Containers ist es so gestaltet, dass andere Prozesse nicht auf die Umgebungsvariablen zugreifen können
      Dass Umgebungsvariablen an Kindprozesse vererbt werden, ist ebenfalls Absicht im Design, weil die Stelle, die die Umgebung mit Secret-Werten konfiguriert, diese Umgebung auch direkt setzt
      Die meisten der hier geäußerten Sorgen halte ich nicht für besonders problematisch, aber ich wäre bereit, das konkret zu diskutieren, falls nötig

  • Viele Kommentare konzentrieren sich auf Secret-Management und die Probleme dabei, aber man kann auch einmal über die Vorteile von Umgebungsvariablen nachdenken
    Umgebungsvariablen sind die „dynamisch gebundenen Variablen mit unbegrenztem Scope“ zur strukturellen Verbindung von Unix-Prozessen
    Statt sie nur mit einer einfachen Textdatei zu vergleichen, sollte man sich daran erinnern, dass der eigentliche Zweck von Umgebungsvariablen die Kontextweitergabe ist, um Informationen sicher an Kindprozesse zu übergeben
    Je komplexer die Prozessstruktur wird, etwa mit verschachtelten Shells oder Unterprozessen komplexer Programme, desto stärker zeigt sich aus meiner Sicht der Nutzen von Umgebungsvariablen

  • Ich möchte Varlock wirklich als nützlich empfehlen
    Es macht klar definiert und leicht verwaltbar, welche Umgebungsvariablen ein Projekt braucht, welche verpflichtend oder optional sind, welchen Datentyp sie haben und woher sie bezogen werden sollen
    Offizielle Varlock-Website

  • Als Beispiel dafür, wie komplex Umgebungsvariablen in der Praxis werden können: In einer früheren Firma bin ich einmal völlig verzweifelt, als ich debuggen wollte, wo genau eine bestimmte ENV-Variable gesetzt wird
    Zuerst dachte ich, sie würde irgendwo simpel in .bashrc oder an einer einzigen Stelle gesetzt, aber tatsächlich kam sie über mindestens zehn Ebenen von Layern: unternehmensweit, regional, Geschäftsbereich, Team, persönlich usw.
    Am Ende konnte ich nur durch das Aktivieren der Bash-Debug-Flags Schritt für Schritt nachverfolgen, wo sie gesetzt wurde

    • Ich weiß nicht, ob andere Sprachen das auch unterstützen, aber Node.js hat kürzlich einen Kommandozeilen-Flag hinzugefügt, der Zugriffe auf Umgebungsvariablen sowie deren Änderungen präzise nachverfolgt
      Node.js-Dokumentation zu --trace-env
      Weil Werte über unzählige APIs gesetzt oder verändert werden können, dürfte das bei kompliziertem Debugging sehr nützlich sein

    • Das ist so ein Fall, bei dem man denkt: „Würde nicht ein einziger Namespace reichen?“

  • Ich habe die Verwendung von Umgebungsvariablen schon vor langer Zeit aufgegeben
    Jetzt betreibe ich es so, dass neben dem Compiler eine dmd.conf-Datei liegt und der Compiler diese Datei direkt einliest

  • Das schwerwiegendste Problem von Umgebungsvariablen ist ihre implizite und intransparente Natur
    In der *nix-Welt neigen die meisten Apps dazu, sich auf Umgebungsvariablen zu stützen
    Selbst wenn zusätzlich explizite und transparente Konfigurationsmethoden unterstützt werden, etwa Konfigurationsdateien, Remote-Services oder Kommandozeilenargumente, gehört die Unterstützung für Umgebungsvariablen in dieser Welt einfach zur Tradition
    Letztlich sind Umgebungsvariablen auch nur eine globale Hashmap, die für Kindprozesse geklont und erweitert wird; 1979 war das vielleicht ein vernünftiges Design, heute ist es aber oft eher schädlich
    Kubernetes verschmutzt zum Beispiel standardmäßig die Container-Umgebung mit „service link“-Umgebungsvariablen
    Wenn die von einer App erwarteten Umgebungsvariablen mit solchen Default-Env-Vars kollidieren, wird Debugging extrem schwierig
    Referenz in der offiziellen Kubernetes-Dokumentation
    Darüber hinaus gibt es viele weitere Gewohnheiten, bei denen alte Strukturen wie /bin, /usr/bin, /lib, /usr/lib unkritisch beibehalten werden
    Siehe auch: Ubuntu-Q&A zur Beibehaltung alter Verzeichnisse

    • Auch Tastenkombinationen wie hjkl können als repräsentatives Beispiel für solche überkommenen Konventionen gelten
      hjkl in vi stammt von einem Dumb Terminal vor 40 Jahren, und dieses Terminal wurde sogar seltener verkauft als das Nokia N9
  • Jedes Mal, wenn ich unter Linux Umgebungsvariablen setze, werde ich nervös
    Offiziell funktionierende Wege unterscheiden sich je nach Distribution etwas, und selbst wenn man Anleitungen aus dem Internet befolgt, ist nach einem Neustart oder nach dem Schließen des Terminals oft wieder alles verschwunden
    Ich wünschte, es gäbe wie unter Windows einen einfachen GUI-Editor für globale Umgebungsvariablen
    Unter Windows ist es zwar umständlich, dass man ein Terminal neu öffnen muss, damit Änderungen übernommen werden, aber abgesehen davon funktioniert es immer gut

    • Umgebungsvariablen bleiben natürlich nicht über Sitzungswechsel hinweg erhalten, deshalb müssen sie an einer Stelle eingetragen werden, die bei jeder Sitzung erneut ausgeführt wird, etwa beim Login oder beim Start eines Terminals
      Beim Login wird .bash_profile ausgeführt, in Kind-Sitzungen .bashrc
      Wenn man in .bash_profile die .bashrc sourced und die meisten Einstellungen in .bashrc hält, ist die Verwaltung einfacher
      Wenn man statt Bash eine andere Shell wie zsh oder fish verwendet, muss man es entsprechend für diese Shell anpassen
      Unter Linux gibt es keinen offiziellen und vereinheitlichten GUI-Mechanismus für Umgebungsvariablen, der in allen Terminals gilt
      Man könnte zwar eine komplexe Parsing-GUI bauen, aber am Ende ist es einfacher, die Werte mit einem Texteditor zu ändern

    • Aus meiner Perspektive als jemand, der überwiegend Linux benutzt, wirkt das Verhalten von Windows eher unangenehmer
      Zu viele Apps verschmutzen die Umgebungsvariablen, und wenn dann etwas nicht funktioniert, stellt sich oft heraus, dass $SOFTWARE aus irgendeinem seltsamen Ordner gestartet wurde oder Ähnliches

    • Wenn man systemd verwendet, kann man auch KEY=VALUE in /etc/environment oder /etc/environment.d/ eintragen
      Dafür ließe sich in der Praxis wahrscheinlich auch eine GUI bauen
      Allerdings kann man Umgebungsvariablen nicht in bereits laufende Prozesse injizieren; sie werden erst nach einem Neustart wirksam, was eine grundsätzliche Grenze ist
      Siehe offizielle systemd-Dokumentation

    • xkcd-Comic zu Standards
      Das illustriert auf unterhaltsame Weise, dass Linux bereits 14 konkurrierende Methoden zum Setzen von Umgebungsvariablen hat und dass ein Versuch, „alles zu vereinheitlichen“, am nächsten Tag nur zu einem 15. Standard führen würde

  • Meine liebste Umgebungsvariablen-Trivia ist, dass Dinge wie PS1, die alle selbstverständlich für Umgebungsvariablen halten, in Wirklichkeit gar keine sind, sondern Shell-Variablen
    PS1 kann man mit dem Befehl env nicht einmal sehen