Skip to content

Instantly share code, notes, and snippets.

@DarthPumpkin
Created April 1, 2025 15:42
Show Gist options
  • Save DarthPumpkin/4aa4e54fcffe13d2c47a845b41a97d71 to your computer and use it in GitHub Desktop.
Save DarthPumpkin/4aa4e54fcffe13d2c47a845b41a97d71 to your computer and use it in GitHub Desktop.
CLI: Find largest files in directory
import os
import argparse
import shutil
import textwrap
def list_files_by_size(directory_path):
files_with_sizes = []
for root, dirs, files in os.walk(directory_path):
for file in files:
full_path = os.path.join(root, file)
try:
size = os.path.getsize(full_path)
files_with_sizes.append((full_path, size))
except OSError as e:
print(f"Could not access file {full_path}: {e}")
return sorted(files_with_sizes, key=lambda x: x[1])
def human_readable_size(size, decimal_places=2):
for unit in ['B', 'KB', 'MB', 'GB', 'TB', 'PB']:
if size < 1024:
return f"{size:.{decimal_places}f} {unit}"
size /= 1024
return f"{size:.{decimal_places}f} PB"
def format_table(data, col_width, size_col_width=12):
# Headers
header_path = "File Path".ljust(col_width)
header_size = "Size".rjust(size_col_width)
separator = f"+{'-' * col_width}+{'-' * size_col_width}+"
lines = [separator, f"|{header_path}|{header_size}|", separator]
# Rows
for path, size in data:
wrapped_path = textwrap.wrap(path, width=col_width)
size_str = human_readable_size(size)
for i, line in enumerate(wrapped_path):
if i == 0:
lines.append(f"|{line.ljust(col_width)}|{size_str.rjust(size_col_width)}|")
else:
lines.append(f"|{line.ljust(col_width)}|{'':>{size_col_width}}|")
lines.append(separator)
return '\n'.join(lines)
def main():
parser = argparse.ArgumentParser(description='List files in a directory (recursively), sorted by size.')
parser.add_argument('directory', type=str, help='Path to the directory')
parser.add_argument('--reverse', action='store_true', help='Sort by size in descending order')
parser.add_argument('--limit', type=int, default=None, help='Limit the number of results displayed')
parser.add_argument('--width', type=int, default=None, help='Max width for file name column')
args = parser.parse_args()
files = list_files_by_size(args.directory)
if args.reverse:
files.reverse()
if args.limit is not None:
files = files[:args.limit]
default_width = shutil.get_terminal_size(fallback=(80, 20)).columns - 15
width = args.width or default_width
print(format_table(files, col_width=width))
if __name__ == "__main__":
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment