Skip to content

Instantly share code, notes, and snippets.

@agateau-gg
Created November 15, 2023 13:39
Show Gist options
  • Save agateau-gg/1bcafbfd85c34177d247cf475a0f8bd6 to your computer and use it in GitHub Desktop.
Save agateau-gg/1bcafbfd85c34177d247cf475a0f8bd6 to your computer and use it in GitHub Desktop.
Like cat, but highlight invisible characters
#!/usr/bin/env python3
"""
Like cat, but highlight invisible characters
"""
import argparse
import sys
if sys.stdout.isatty():
BOLD = "\033[01m"
RED = "\033[31m"
GREEN = "\033[32m"
ORANGE = "\033[33m"
PURPLE = "\033[35m"
CYAN = "\033[36m"
GREY = "\033[37m"
RESET = "\033[0;0m"
else:
BOLD = ""
RED = ""
GREEN = ""
ORANGE = ""
PURPLE = ""
CYAN = ""
GREY = ""
RESET = ""
def show_file(fp):
while block := fp.read(4096):
for ch in block:
if ch == "\0":
sys.stdout.write(f"{ORANGE}[0]{RESET}")
elif ch == "\n":
print(f"{CYAN}\\n{RESET}")
elif ord(ch) < 32:
sys.stdout.write(f"{RED}.{RESET}")
else:
sys.stdout.write(ch)
def main():
parser = argparse.ArgumentParser(
formatter_class=argparse.RawDescriptionHelpFormatter, description=__doc__
)
parser.add_argument("file", nargs="*", help="files to show, use stdin if not set")
args = parser.parse_args()
if args.file:
for path in args.file:
with open(path) as fp:
show_file(fp)
else:
show_file(sys.stdin)
return 0
if __name__ == "__main__":
sys.exit(main())
# vi: ts=4 sw=4 et
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment