2022-10-14 14:53:06 +00:00
|
|
|
import csv
|
2022-02-17 22:54:30 +00:00
|
|
|
from io import StringIO
|
2020-01-20 15:19:53 +00:00
|
|
|
|
2022-10-14 14:53:06 +00:00
|
|
|
from benedict.serializers.abstract import AbstractSerializer
|
|
|
|
from benedict.utils import type_util
|
2020-01-20 15:19:53 +00:00
|
|
|
|
|
|
|
|
|
|
|
class CSVSerializer(AbstractSerializer):
|
2022-02-13 10:56:44 +00:00
|
|
|
"""
|
|
|
|
This class describes a csv serializer.
|
|
|
|
"""
|
|
|
|
|
2020-02-20 16:14:48 +00:00
|
|
|
def __init__(self):
|
2022-12-31 17:33:20 +00:00
|
|
|
super().__init__(
|
2022-10-05 14:43:46 +00:00
|
|
|
extensions=[
|
|
|
|
"csv",
|
|
|
|
],
|
|
|
|
)
|
2020-02-20 16:14:48 +00:00
|
|
|
|
|
|
|
def decode(self, s, **kwargs):
|
2020-01-20 15:19:53 +00:00
|
|
|
# kwargs.setdefault('delimiter', ',')
|
2022-02-13 10:35:43 +00:00
|
|
|
if kwargs.pop("quote", False):
|
2020-01-31 12:02:07 +00:00
|
|
|
# TODO: add tests coverage
|
2022-02-13 10:35:43 +00:00
|
|
|
kwargs.setdefault("quoting", csv.QUOTE_ALL)
|
|
|
|
columns = kwargs.pop("columns", None)
|
|
|
|
columns_row = kwargs.pop("columns_row", True)
|
2020-01-20 15:19:53 +00:00
|
|
|
f = StringIO(s)
|
|
|
|
r = csv.reader(f, **kwargs)
|
|
|
|
ln = 0
|
|
|
|
data = []
|
|
|
|
for row in r:
|
|
|
|
if ln == 0 and columns_row:
|
|
|
|
if not columns:
|
|
|
|
columns = row
|
|
|
|
ln += 1
|
|
|
|
continue
|
|
|
|
d = dict(zip(columns, row))
|
|
|
|
data.append(d)
|
|
|
|
ln += 1
|
|
|
|
return data
|
|
|
|
|
2020-02-20 16:14:48 +00:00
|
|
|
def encode(self, d, **kwargs):
|
2022-03-24 12:26:18 +00:00
|
|
|
ls = d
|
2020-01-20 15:19:53 +00:00
|
|
|
# kwargs.setdefault('delimiter', ',')
|
2022-02-13 10:35:43 +00:00
|
|
|
if kwargs.pop("quote", False):
|
|
|
|
kwargs.setdefault("quoting", csv.QUOTE_ALL)
|
|
|
|
kwargs.setdefault("lineterminator", "\n")
|
|
|
|
columns = kwargs.pop("columns", None)
|
|
|
|
columns_row = kwargs.pop("columns_row", True)
|
2022-03-24 12:26:18 +00:00
|
|
|
if not columns and len(ls) and type_util.is_dict(ls[0]):
|
|
|
|
keys = [str(key) for key in ls[0].keys()]
|
2020-01-20 15:19:53 +00:00
|
|
|
columns = list(sorted(keys))
|
|
|
|
f = StringIO()
|
|
|
|
w = csv.writer(f, **kwargs)
|
|
|
|
if columns_row and columns:
|
|
|
|
w.writerow(columns)
|
2022-03-24 12:26:18 +00:00
|
|
|
for item in ls:
|
2020-01-30 14:31:53 +00:00
|
|
|
if type_util.is_dict(item):
|
2022-02-13 10:35:43 +00:00
|
|
|
row = [item.get(key, "") for key in columns]
|
2020-01-30 14:31:53 +00:00
|
|
|
elif type_util.is_collection(item):
|
2020-01-31 12:02:07 +00:00
|
|
|
# TODO: add tests coverage
|
2020-01-20 15:19:53 +00:00
|
|
|
row = item
|
|
|
|
else:
|
2020-01-31 12:02:07 +00:00
|
|
|
# TODO: add tests coverage
|
2020-01-20 15:19:53 +00:00
|
|
|
row = [item]
|
|
|
|
w.writerow(row)
|
|
|
|
data = f.getvalue()
|
|
|
|
return data
|