You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

128 lines
4.1 KiB

7 years ago
  1. from winreg import *
  2. import argparse
  3. import win32con
  4. import win32gui
  5. import re
  6. import saveto
  7. import itertools
  8. user = 'Environment'
  9. system = r'SYSTEM\CurrentControlSet\Control\Session Manager\Environment'
  10. class regkey(object):
  11. def __init__(self,root, path):
  12. self.path = path
  13. self.root = root
  14. reg = ConnectRegistry(None, root)
  15. self.key = OpenKey(reg, path, 0, KEY_ALL_ACCESS)
  16. def set_value(self, name, value,t=REG_EXPAND_SZ):
  17. SetValueEx(self.key, name, 0, t, value)
  18. win32gui.SendMessage(win32con.HWND_BROADCAST, win32con.WM_SETTINGCHANGE, 0, 'Environment')
  19. def get_value(self, name, ret_type = False):
  20. value, type_id = QueryValueEx(self.key, name)
  21. if ret_type:
  22. return value, type_id
  23. else:
  24. return value
  25. class path_key(regkey):
  26. def __init__(self,root=HKEY_CURRENT_USER, path=user):
  27. super(path_key,self).__init__(root,path)
  28. self.path_set = self.get_path_setobj()
  29. def get_path_setobj(self):
  30. path = self.get_value('Path')
  31. path = set(path.split(';'))
  32. return path
  33. def format_path(self):
  34. path = self.path_set
  35. return ';'.join(sorted(path))
  36. def add(self, path):
  37. self.path_set.add(path)
  38. def remove(self, path):
  39. self.path_set.discard(path)
  40. def commit(self):
  41. path = self.format_path()
  42. self.set_value('Path', path)
  43. def check(self,path):
  44. return path in self.path_set
  45. def search_remove(pathobj,pattern,action,regex=False,negate=False,dry_run=False):
  46. if negate:
  47. flt = itertools.filterfalse
  48. else:
  49. flt = filter
  50. if regex:
  51. pattern = re.compile(pattern,re.IGNORECASE)
  52. results = flt(lambda path: pattern.search(path),pathobj.path_set)
  53. else:
  54. pattern = pattern.lower()
  55. results = flt(lambda path: pattern in path.lower(),pathobj.path_set)
  56. for path in list(results):
  57. if dry_run:
  58. print('REM: {path}'.format(path=path))
  59. else:
  60. action(path)
  61. if __name__ == "__main__":
  62. parser = argparse.ArgumentParser(prog='path')
  63. parser.add_argument('-l','--list',action = 'store_true',help = 'list path entries')
  64. parser.add_argument('-s','--system',action = 'store_true',help = 'use system enviroment instead of current user')
  65. alts = parser.add_subparsers(dest='command')
  66. mod = alts.add_parser('mod')
  67. group = mod.add_mutually_exclusive_group(required=True)
  68. group.add_argument('-a', dest='add', action= 'store_true', help='add to PATH')
  69. group.add_argument('-r', dest='remove', action ='store_true', help='remove from PATH')
  70. mod.add_argument('-d',dest='dry_run',action='store_true',help='dry run')
  71. mod.add_argument('path', help = 'Path to be appended to PATH')
  72. search = alts.add_parser('map')
  73. search.add_argument('--regex',action='store_true',help='use regex')
  74. search.add_argument('-n',action = 'store_true',help = 'negate pattern')
  75. search.add_argument('-d',dest='dry_run',action='store_true',help='dry run')
  76. search.add_argument('pattern', help = 'pattern to search through path and remove matches')
  77. args = parser.parse_args()
  78. if args.system:
  79. try:
  80. path = path_key(HKEY_LOCAL_MACHINE,system)
  81. except PermissionError:
  82. print('Must be admin to view system keys')
  83. exit()
  84. else:
  85. path = path_key()
  86. if args.list:
  87. print('\n'.join(sorted(path.path_set)))
  88. elif args.command == 'mod':
  89. if args.dry_run:
  90. if args.add:
  91. print('ADD: {path}'.format(path=args.path))
  92. else:
  93. assert(path.check(args.path))
  94. print('REM: {path}'.format(path=args.path))
  95. else:
  96. if args.add:
  97. path.add(args.path)
  98. else:
  99. assert(path.check(args.path))
  100. path.remove(args.path)
  101. path.commit()
  102. elif args.command == 'map':
  103. search_remove(path,args.pattern,path.remove,args.regex,args.n,args.dry_run)
  104. if not args.dry_run:
  105. path.commit()
  106. else:
  107. parser.parse_args(['-h'])