Skip to content

Instantly share code, notes, and snippets.

@koiralakiran1
Last active April 26, 2024 07:26
Show Gist options
  • Save koiralakiran1/8da786fa210e8f5277eb28f9540019fa to your computer and use it in GitHub Desktop.
Save koiralakiran1/8da786fa210e8f5277eb28f9540019fa to your computer and use it in GitHub Desktop.
Wrap yay on arch distros to remember installed packages to a file
#!/usr/bin/env python
# pylint: disable=line-too-long,missing-module-docstring
import os
import sys
import logging
import subprocess
class YayRemember():
"""Wraps yay to save packages to packagelist"""
IS_DRY_RUN = False
PACKAGE_LIST_FILE = os.path.expanduser('~/.packagelist') # Later to install: `yay -S --needed --noconfirm - < ~/.packagelist`
PACKAGE_MANAGER = 'yay'
def __init__(self) -> None:
self.logger = self._get_logger()
def _get_logger(self):
handler = logging.StreamHandler()
handler.setLevel(logging.NOTSET)
handler.setFormatter(self._CustomFormatter())
logger = logging.getLogger('YayRemember')
logger.setLevel(logging.DEBUG)
logger.addHandler(handler)
return logger
class _CustomFormatter(logging.Formatter):
"""Custom log formatter"""
grey = "\x1b[38m"
green = "\x1B[32m"
yellow = "\x1b[33m"
red = "\x1b[31m"
bold_red = "\x1b[31;1m"
reset = "\x1b[0m"
message_format = "%(asctime)s - %(name)s - %(levelname)s -> %(message)s (%(filename)s:%(lineno)d)"
FORMATS = {
logging.DEBUG: grey + message_format + reset,
logging.INFO: green + message_format + reset,
logging.WARNING: yellow + message_format + reset,
logging.ERROR: red + message_format + reset,
logging.CRITICAL: bold_red + message_format + reset
}
def format(self, record):
log_fmt = self.FORMATS.get(record.levelno)
formatter = logging.Formatter(log_fmt)
return formatter.format(record)
def main(self, args):
"""Main function to wrap yay"""
yay_arguments = args[1:]
first_arg = yay_arguments[0]
is_installation_command = not first_arg.startswith('-Ss') and first_arg.startswith('-S')
subprocess.run([self.PACKAGE_MANAGER, *yay_arguments], check=True)
if not is_installation_command:
return
answer = input('Remember package(s)? (y/n/yes/no) [default=y]? ') or 'y'
answer = str(answer).lower().strip()
if answer != 'y' and answer != 'yes':
self.logger.info('Package(s) not saved!')
return
packages = yay_arguments[1:]
self.logger.info('Packages being installed (all): %s', packages)
try:
with open(self.PACKAGE_LIST_FILE, 'r', encoding='UTF-8') as package_file:
lines = package_file.readlines()
for line in lines:
packages = list(filter(lambda p, l = line: p.strip() != l.replace('\\n', '').strip(), packages))
except Exception:
pass
if len(packages) == 0:
return
self.logger.info('Adding new packages: %s', packages)
with open(self.PACKAGE_LIST_FILE, 'a+', encoding='UTF-8') as write_file:
write_file.writelines(map(lambda p: f'{p.strip()}\n', packages))
self.logger.info('Package(s) saved! %s', packages)
if __name__ == '__main__':
obj = YayRemember()
sys.exit(obj.main(sys.argv))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment