Skip to content

Commit 87599be

Browse files
authored
Merge pull request #91 from dbcli/RW/add-jsonl-output-formats
Add two JSON-based output formats
2 parents be9bfcc + d17b7b8 commit 87599be

File tree

3 files changed

+68
-0
lines changed

3 files changed

+68
-0
lines changed

CHANGELOG

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
# Changelog
22

33
- Added noheader CSV and TSV output formats.
4+
- Added `jsonl` and `jsonl_escaped` output formats.
45

56
## Version 2.4.0
67

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,27 @@
1+
# -*- coding: utf-8 -*-
2+
"""A JSON data output adapter"""
3+
4+
from itertools import chain
5+
import json
6+
7+
from .preprocessors import bytes_to_string, override_missing_value, convert_to_string
8+
9+
supported_formats = ("jsonl", "jsonl_escaped")
10+
preprocessors = (override_missing_value, bytes_to_string, convert_to_string)
11+
12+
13+
def adapter(data, headers, table_format="jsonl", **_kwargs):
14+
"""Wrap the formatting inside a function for TabularOutputFormatter."""
15+
if table_format == "jsonl":
16+
ensure_ascii = False
17+
elif table_format == "jsonl_escaped":
18+
ensure_ascii = True
19+
else:
20+
raise ValueError("Invalid table_format specified.")
21+
22+
for row in chain(data):
23+
yield json.dumps(
24+
dict(zip(headers, row, strict=True)),
25+
separators=(",", ":"),
26+
ensure_ascii=ensure_ascii,
27+
)
Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
# -*- coding: utf-8 -*-
2+
"""Test the json output adapter."""
3+
4+
from __future__ import unicode_literals
5+
6+
from cli_helpers.tabular_output import json_output_adapter
7+
8+
9+
def test_jsonl_wrapper():
10+
"""Test the jsonl output adapter."""
11+
# Test jsonl output.
12+
data = [["ab\r\nc", 1], ["d", 456]]
13+
headers = ["letters", "number"]
14+
output = json_output_adapter.adapter(iter(data), headers, table_format="jsonl")
15+
assert (
16+
"\n".join(output)
17+
== """{"letters":"ab\\r\\nc","number":1}\n{"letters":"d","number":456}"""
18+
)
19+
20+
21+
def test_unicode_with_jsonl():
22+
"""Test that the jsonl wrapper can pass through non-ascii characters."""
23+
data = [["观音", 1], ["Ποσειδῶν", 456]]
24+
headers = ["letters", "number"]
25+
output = json_output_adapter.adapter(data, headers, table_format="jsonl")
26+
assert (
27+
"\n".join(output)
28+
== """{"letters":"观音","number":1}\n{"letters":"Ποσειδῶν","number":456}"""
29+
)
30+
31+
32+
def test_unicode_with_jsonl_esc():
33+
"""Test that the jsonl_escaped wrapper JSON-escapes non-ascii characters."""
34+
data = [["观音", 1], ["Ποσειδῶν", 456]]
35+
headers = ["letters", "number"]
36+
output = json_output_adapter.adapter(data, headers, table_format="jsonl_escaped")
37+
assert (
38+
"\n".join(output)
39+
== """{"letters":"\\u89c2\\u97f3","number":1}\n{"letters":"\\u03a0\\u03bf\\u03c3\\u03b5\\u03b9\\u03b4\\u1ff6\\u03bd","number":456}"""
40+
)

0 commit comments

Comments
 (0)