Skip to content

Instantly share code, notes, and snippets.

@milkey-mouse
Last active October 13, 2024 03:32
Show Gist options
  • Save milkey-mouse/c73d1c79370266b3295d1f293e47fc83 to your computer and use it in GitHub Desktop.
Save milkey-mouse/c73d1c79370266b3295d1f293e47fc83 to your computer and use it in GitHub Desktop.
#!/usr/bin/env python3
import os
import sys
import textwrap
# https://github.com/coreutils/coreutils/commit/fcfba90d0d27a1bacf2020bac4dbec74ed181028
IO_BUFSIZE = 256 * 1024
def print_usage(argv0: str = "./linecat.py") -> None:
print(
textwrap.dedent(
f"""\
usage: {argv0} [FILE]...
Write each line of FILE(s) or standard input shorter than PIPE_BUF to standard
output, with a separate write per line. (This allows multiple linecat's to write
to a single pipe simultaneously without interleaving within lines.) If a line is
more than PIPE_BUF (usually 4096) bytes long, it is skipped and sent to stderr.\
"""
)
)
def main() -> None:
try:
argv0, *args = sys.argv
except ValueError:
print_usage()
sys.exit(1)
for i, arg in enumerate(args):
if arg == "--":
del args[i]
break
elif arg in ("-h", "--help"):
print_usage(argv0)
sys.exit(0)
try:
stdout_pipe_buf = os.fpathconf(sys.stdout.fileno(), "PC_PIPE_BUF")
except (AttributeError, OSError, ValueError):
stdout_pipe_buf = 512 # POSIX guaranteed minimum value
stderr_isatty = sys.stderr.isatty()
for path in args or ("-",):
try:
with sys.stdin.buffer if path == "-" else open(path, "rb", IO_BUFSIZE) as f:
for line in f:
if len(line) > stdout_pipe_buf:
if stderr_isatty:
sys.stderr.buffer.raw.write(b"line too long: " + line)
else:
sys.stderr.buffer.raw.write(line)
else:
sys.stdout.buffer.raw.write(line)
except FileNotFoundError:
print(f"{argv0}: {path}: No such file or directory", file=sys.stderr)
sys.exit(1)
except OSError as e:
print(f"{argv0}: {path}: {e.strerror}", file=sys.stderr)
sys.exit(1)
if __name__ == "__main__":
main()
@milkey-mouse
Copy link
Author

License: CC0-1.0

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment