2

I wish to create a python program that is used from the command line.
It has one positional argument that is a file name.
I want to also be able to pass it input from a pipe

I want to create my python program so that it behaves the same here:

my_program.py input_data.txt

as it does here

cat input_data.txt | my_program.py

I have built programs that do one or the other, but I'm not sure how to conveniently handle both.
I usually use argparse to do this stuff so I was hoping there is an argparse based solution but if not that's fine.

John Kugelman
  • 349,597
  • 67
  • 533
  • 578
Acceptance
  • 110
  • 1
  • 5
  • Your program is supposed to read the contents of the csv file correct? – anarchy Oct 11 '22 at 12:31
  • 1
    Seriously, don't bother. It's extra work that you do not need to do. Instead of `my_program.py input_data.txt`, you let the shell do the work and write `my_program.py < input_data.txt`. It's a better mind set anyway. – William Pursell Oct 11 '22 at 12:40
  • 1
    As an aside, that's a [useless use of `cat`](https://stackoverflow.com/questions/11710552/useless-use-of-cat)) – tripleee Oct 11 '22 at 12:56

2 Answers2

1

You really shouldn't do this. Get in the habit of redirecting input, and life becomes much better. If you do want to do this, just add a few lines at the start:

if len(sys.argv) > 1:
    in_file = open(sys.argv[1], 'r')
else:
    in_file = sys.stdin
William Pursell
  • 204,365
  • 48
  • 270
  • 300
0

Make my_program.py read the name of the file in the argument.

If there is an argument, it will do the standard csv reader. But if it is piped a program, it will read the standard input from the pipe.

#! /usr/bin/python

import sys
import csv

arg = sys.argv[1] #this saves the filename to arg from the command line

if len(sys.argv) > 1: #if given an argument, run this
    with open(arg, newline='') as f:
        reader = csv.reader(f)
        for row in reader:
            print(row)

else: #if not given an argument, run this
    for line in sys.stdin:
        sys.stdout.write(line)

        with open(line, newline='') as f:
            reader = csv.reader(f)
            for row in reader:
                print(row)

You can edit the contents of the csv reader below depending on what your file looks like.

anarchy
  • 3,709
  • 2
  • 16
  • 48