当前位置: 首页 > 面试题库 >

用于从Python修改Windows环境变量的界面

公良同
2023-03-14
问题内容

如何从Python脚本持久地修改Windows环境变量?(这是setup.py脚本)

我正在寻找用于此的标准功能或模块。我已经很熟悉注册表的实现方式,但是也欢迎对此提出任何意见。


问题答案:

使用setx的缺点很少,尤其是当您尝试附加到环境变量(例如setx PATH%Path%; C:\
mypath)时,这将在每次运行时重复附加到路径中,这可能是一个问题。更糟糕的是,它无法区分机器路径(存储在HKEY_LOCAL_MACHINE中)和用户路径(存储在HKEY_CURRENT_USER中)。您在命令提示符处看到的环境变量由这两个值的串联组成。因此,在调用setx之​​前:

user PATH == u
machine PATH == m
%PATH% == m;u

> setx PATH %PATH%;new

Calling setx sets the USER path by default, hence now:
user PATH == m;u;new
machine PATH == m
%PATH% == m;m;u;new

每次调用setx追加到PATH时,系统路径都会不可避免地在%PATH%环境变量中重复。这些更改是永久性的,永远不会通过重新启动进行重置,因此会在计算机的整个生命周期内不断累积。

试图在DOS中弥补这一点超出了我的能力范围。所以我转向了Python。我今天想出的解决方案,是通过调整注册表来设置环境变量,包括追加到PATH而不引入重复项,如下所示:

from os import system, environ
import win32con
from win32gui import SendMessage
from _winreg import (
    CloseKey, OpenKey, QueryValueEx, SetValueEx,
    HKEY_CURRENT_USER, HKEY_LOCAL_MACHINE,
    KEY_ALL_ACCESS, KEY_READ, REG_EXPAND_SZ, REG_SZ
)

def env_keys(user=True):
    if user:
        root = HKEY_CURRENT_USER
        subkey = 'Environment'
    else:
        root = HKEY_LOCAL_MACHINE
        subkey = r'SYSTEM\CurrentControlSet\Control\Session Manager\Environment'
    return root, subkey


def get_env(name, user=True):
    root, subkey = env_keys(user)
    key = OpenKey(root, subkey, 0, KEY_READ)
    try:
        value, _ = QueryValueEx(key, name)
    except WindowsError:
        return ''
    return value


def set_env(name, value):
    key = OpenKey(HKEY_CURRENT_USER, 'Environment', 0, KEY_ALL_ACCESS)
    SetValueEx(key, name, 0, REG_EXPAND_SZ, value)
    CloseKey(key)
    SendMessage(
        win32con.HWND_BROADCAST, win32con.WM_SETTINGCHANGE, 0, 'Environment')


def remove(paths, value):
    while value in paths:
        paths.remove(value)


def unique(paths):
    unique = []
    for value in paths:
        if value not in unique:
            unique.append(value)
    return unique


def prepend_env(name, values):
    for value in values:
        paths = get_env(name).split(';')
        remove(paths, '')
        paths = unique(paths)
        remove(paths, value)
        paths.insert(0, value)
        set_env(name, ';'.join(paths))


def prepend_env_pathext(values):
    prepend_env('PathExt_User', values)
    pathext = ';'.join([
        get_env('PathExt_User'),
        get_env('PathExt', user=False)
    ])
    set_env('PathExt', pathext)



set_env('Home', '%HomeDrive%%HomePath%')
set_env('Docs', '%HomeDrive%%HomePath%\docs')
set_env('Prompt', '$P$_$G$S')

prepend_env('Path', [
    r'%SystemDrive%\cygwin\bin', # Add cygwin binaries to path
    r'%HomeDrive%%HomePath%\bin', # shortcuts and 'pass-through' bat files
    r'%HomeDrive%%HomePath%\docs\bin\mswin', # copies of standalone executables
])

# allow running of these filetypes without having to type the extension
prepend_env_pathext(['.lnk', '.exe.lnk', '.py'])

它不会影响当前进程或父Shell,但会影响运行后打开的所有cmd窗口,而无需重新启动,并且可以安全地进行编辑和重新运行多次,而不会引入任何重复项。



 类似资料:
  • 本文向大家介绍Windows Powershell 环境变量,包括了Windows Powershell 环境变量的使用技巧和注意事项,需要的朋友参考一下 传统的控制台一般没有象Powershell这么高级的变量系统。它们都是依赖于机器本身的环境变量,进行操作 。环境变量对于powershell显得很重要,因为它涵盖了许多操作系统的细节信息。此外,powershell中的变量只存在于powersh

  • 本文向大家介绍Python环境变量,包括了Python环境变量的使用技巧和注意事项,需要的朋友参考一下 这是重要的环境变量,Python可以识别它们- 序号 变量与说明 1 PYTHONPATH 它的作用类似于PATH。这个变量告诉Python解释器在哪里可以找到导入程序的模块文件。它应该包括Python源库目录和包含Python源代码的目录。PYTHONPATH有时是由Python安装程序预设的

  • 我在Windows10机器上运行Docker1.12.0。我正在开发一个Java程序,使用Maven 3.3.9作为依赖项管理器。我有一个maven docker插件(https://github.com/fabric8io/docker-maven-plugin),它在干净安装时会出现以下错误。 [ERROR]未能执行目标IO.fabric8:docker-maven-plugin:0.15.1

  • 问题内容: 有没有办法使用python以平台独立的方式修改环境变量? 类似于? 问题答案: 您应该能够进行修改。 由于是分隔不同路径的字符,因此应使用此字符追加每个新路径: 或者,如果要在列表中添加多个路径: 如前所述,在必须从单独的部分构造路径的情况下,也可以用于必须附加的每个路径。

  • 问题内容: 我正在尝试从Windows命令提示符(Windows 10)运行python。因此,结果是未配置路径环境变量时的典型结果 但是,我不确定应该在path变量中设置哪个目录。 我尝试了一些变体,但没有一个起作用,包括: 他们都不起作用。 有没有人对这个特定的系统星座(Windows,anaconda)有经验。谢谢。 问题答案: 原来我错了。 解决方案是:在anaconda(以及其他实现中)

  • 本文向大家介绍Linux中修改环境变量及生效方法,包括了Linux中修改环境变量及生效方法的使用技巧和注意事项,需要的朋友参考一下 在/etc/profile文件中添加变量【对所有用户生效(永久的)】 用VI在文件/etc/profile文件中增加变量,该变量将会对Linux下所有用户有效,并且是“永久的”。 要让刚才的修改马上生效,需要执行以下代码 以上这篇Linux中修改环境变量及生效方法就是