path/program_path_provider.py
"""
This module is about path resolving for the program path.
This is required to execute Rainmeter.exe for example to refresh the current skin.
"""
import os
from functools import lru_cache
import winreg
import sublime
from .. import logger
def get_rm_path_from_default_path():
r"""
Default location is "C:\Program Files\Rainmeter" in windows.
We can get "C:\Program Files" through the environmental variables
%PROGRAMFILES%
"""
programfiles = os.getenv("PROGRAMFILES")
rainmeterpath = os.path.join(programfiles, "Rainmeter")
return rainmeterpath
def _get_rainmeter_registry_key():
r"""
Throw FileNotFoundException if Software\WOW6432Node\Rainmeter does not exist.
not much we can do to handle that
"""
return winreg.OpenKey(winreg.HKEY_LOCAL_MACHINE, "SOFTWARE\\WOW6432Node\\Rainmeter")
def get_rm_path_from_registry():
"""Registry."""
rainmeter_key = _get_rainmeter_registry_key()
rainmeter_path = winreg.QueryValue(rainmeter_key, None)
return rainmeter_path
def _executable_exists(rm_path):
"""Check if Rainmeter executable exists."""
# normalize path
rainmeter_exe = os.path.join(rm_path, "Rainmeter.exe")
if not os.path.exists(rainmeter_exe):
message = """Rainmeter path was found, but no Rainmeter.exe found.
Check if you have installed Rainmeter correctly."""
logger.error(message)
sublime.error_message(message)
return False
return True
@lru_cache(maxsize=None)
def get_cached_program_path():
"""Try to retrieve the program path of RM through magic.
Possible options are:
* It is given through settings
* It is in the default installation path
* It is registered in the registry
* Ask the user for the path
"""
# Load setting
settings = sublime.load_settings("Rainmeter.sublime-settings")
rm_path = settings.get("rainmeter_path", None)
# If setting is not set, try default location
if not rm_path:
logger.info("rainmeter_path not found in settings. Trying default location.")
rm_path = get_rm_path_from_default_path()
# if it is not even specified by default,
# try using the registry to retrieve the installation path
if not os.path.isdir(rm_path):
rm_path = get_rm_path_from_registry()
# Check if path exists and contains Rainmeter.exe
if not os.path.isdir(rm_path):
message = """Path to Rainmeter.exe could neither be found:
* in the settings,
* in the standard directory,
* nor via registry.
Check your \"rainmeter_path\" setting."""
logger.info(message)
return
if not _executable_exists(rm_path):
return
logger.info("Rainmeter found in " + rm_path)
return rm_path + "\\"