Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Convert Python Pretty table to CSV using shell or batch command line

Whats an easy way convert the output of Python Pretty table to grammatically usable format such as CSV.

The output looks like this :

C:\test> nova list

    spu+--------------------------------------+--------+--------+------------+-------------+-----------------------------------+
     | ID                                   | Name   | Status | Task State | Power State | Networks                          |
     +--------------------------------------+--------+--------+------------+-------------+-----------------------------------+
     | 6bca09f8-a320-44d4-a11f-647dcec0aaa1 | tester | ACTIVE | -          |  Running     | OpenStack-net=10.0.0.1, 10.0.0.3 |
     +--------------------------------------+--------+--------+------------+-------------+-----------------------------------+
like image 491
CodeEmpower Avatar asked Feb 10 '23 06:02

CodeEmpower


2 Answers

Perhaps this will get you close:

nova list | grep -v '\-\-\-\-' | sed 's/^[^|]\+|//g' | sed 's/|\(.\)/,\1/g' | tr '|' '\n'

This will strip the --- lines Remove the leading | Replace all but the last | with , Replace the last | with \n

like image 162
Stanton Avatar answered Feb 11 '23 23:02

Stanton


Here's a real ugly one-liner

import csv

s = """\
  spu+--------------------------------------+--------+--------+------------+-------------+-----------------------------------+
     | ID                                   | Name   | Status | Task State | Power State | Networks                          |
     +--------------------------------------+--------+--------+------------+-------------+-----------------------------------+
     | 6bca09f8-a320-44d4-a11f-647dcec0aaa1 | tester | ACTIVE | -          |  Running     | OpenStack-net=10.0.0.1, 10.0.0.3 |
     +--------------------------------------+--------+--------+------------+-------------+-----------------------------------+"""

result = [tuple(filter(None, map(str.strip, splitline))) for line in s.splitlines() for splitline in [line.split("|")] if len(splitline) > 1]

with open('output.csv', 'wb') as outcsv:
    writer = csv.writer(outcsv)
    writer.writerows(result)

I can unwrap it a bit to make it nicer:

splitlines = s.splitlines()
splitdata = line.split("|")
splitdata = filter(lambda line: len(line) > 1, data)
# toss the lines that don't have any data in them -- pure separator lines
header, *data = [[field.strip() for field in line if field.strip()] for line in splitdata]

result = [header] + data
# I'm really just separating these, then re-joining them, but sometimes having
# the headers separately is an important thing!

Or possibly more helpful:

result = []

for line in s.splitlines():
    splitdata = line.split("|")
    if len(splitdata) == 1:
        continue  # skip lines with no separators
    linedata = []
    for field in splitdata:
        field = field.strip()
        if field:
            linedata.append(field)
    result.append(linedata)
like image 36
Adam Smith Avatar answered Feb 12 '23 00:02

Adam Smith