简体   繁体   中英

Python Subprocess not printing vnstat process

Thank you for taking the time to read this post.

I'm trying to do live bandwidth monitoring in python using vnstat. Unfortunately, It is not printing the output that i want, and i cant seem to figure out why. This is my code below.

from subprocess import Popen, PIPE
import time

def run(command):
 process = Popen(command, stdout=PIPE, bufsize=1, shell=True ,universal_newlines=True)
 while True:
    line = process.stdout.readline().rstrip()
    print(line)



if __name__ == "__main__":
 run("sudo vnstat -l -i wlan1") 

When i run this code in the terminal , this is the output i get :

sudo python testingLog.py
Monitoring wlan1...    (press CTRL-C to stop)

It does not show me the desired output when running "vnstat -l -i wlan1" in the terminal.

Desired Output :

Monitoring wlan1...    (press CTRL-C to stop)

rx:        0 kbit/s     0 p/s          tx:        0 kbit/s     0 p/s

What happens when i run vnstat -l -i wlan1 is that it will update it and be running live, so i suspect that my printing is wrong as it does not print the desired output but i cant seem to figure out why.

It's not that your printing is wrong, it's the fact that vnstat keeps updating the same line without issuing a new line so process.stdout.readline() hangs at one point, waiting for a new line that never comes.

If you just want to redirect vnstat STDOUT to Python's STDOUT you can just pipe it, ie:

import subprocess
import sys
import time

proc = subprocess.Popen(["vnstat", "-l", "-i", "wlan1"], stdout=sys.stdout)
while proc.poll() is None:  # loop until the process ends (kill vnstat to see the effect)
    time.sleep(1)  # wait a second...
print("\nProcess finished.")

If you want to capture the output and deal with it yourself, however, you'll have to stream the STDOUT a character (or safe buffer) at the time to capture whatever vnstat publishes and then decide what to do with it. For example, to simulate the above piping but with you in the driver's seat you can do something like:

import subprocess
import sys

proc = subprocess.Popen(["vnstat", "-l", "-i", "wlan1"], stdout=subprocess.PIPE)
while True:  # a STDOUT read loop
    output = proc.stdout.read(1)  # grab one character from vnstat's STDOUT
    if output == "" and proc.poll() is not None:  # process finished, exit the loop
        break
    sys.stdout.write(output)  # write the output to Python's own STDOUT
    sys.stdout.flush()  # flush it...
    # of course, you can collect the output instead of printing it to the screen...
print("\nProcess finished.")

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM