Reputation: 1241
I am using google Gson library to parse JSON files, which are ipython note book files. Is it possible to collect the line number where a JSON object or array starts or end.
JsonReader reader = new JsonReader(new FileReader(notebookFile));
Gson gson = new GsonBuilder().create();
// Read file in stream mode
reader.beginObject();
while (reader.hasNext()) {
String name = reader.nextName();
if (name.equals("cells")) {
//can we determine line number of name
reader.beginArray();
.....
}
....
}
Part of a notebook:
"metadata": {
"name": "5-Scatterplots"
},
"nbformat": 3,
"nbformat_minor": 0,
"worksheets": [
{
"cells": [
{
"cell_type": "code",
"collapsed": false,
"input": [
"import pandas as pd\n",
"store = pd.HDFStore('/Volumes/FreshBooks/data/store.h5')\n",
"may07 = store['may07']\n",
"may08 = store['may08']"
],
"language": "python",
"metadata": {},
"outputs": [],
"prompt_number": 1
},
Upvotes: 1
Views: 5699
Reputation: 41
Full disclosure: I'm the maintainer of the package below.
There is now a new Python package that solves this use case: https://github.com/open-alchemy/json-source-map
Installation: pip install json_source_map
For example, in your case:
from json_source_map import calculate
source = '''
{
"metadata": {
"name": "5-Scatterplots"
},
"nbformat": 3,
"nbformat_minor": 0,
"worksheets": [
{
"cells": [
{
"cell_type": "code",
"collapsed": false,
"input": [
"import pandas as pd\\n",
"store = pd.HDFStore('/Volumes/FreshBooks/data/store.h5')\\n",
"may07 = store['may07']\\n",
"may08 = store['may08']"
],
"language": "python",
"metadata": {},
"outputs": [],
"prompt_number": 1
}
]
}
]
}
'''
print(calculate(source))
This prints:
{
"": Entry(
value_start=Location(line=1, column=0, position=1),
value_end=Location(line=27, column=1, position=568),
key_start=None,
key_end=None,
),
"/metadata": Entry(
value_start=Location(line=2, column=14, position=17),
value_end=Location(line=4, column=3, position=51),
key_start=Location(line=2, column=2, position=5),
key_end=Location(line=2, column=12, position=15),
),
"/metadata/name": Entry(
value_start=Location(line=3, column=12, position=31),
value_end=Location(line=3, column=28, position=47),
key_start=Location(line=3, column=4, position=23),
key_end=Location(line=3, column=10, position=29),
),
"/nbformat": Entry(
value_start=Location(line=5, column=14, position=67),
value_end=Location(line=5, column=15, position=68),
key_start=Location(line=5, column=2, position=55),
key_end=Location(line=5, column=12, position=65),
),
"/nbformat_minor": Entry(
value_start=Location(line=6, column=20, position=90),
value_end=Location(line=6, column=21, position=91),
key_start=Location(line=6, column=2, position=72),
key_end=Location(line=6, column=18, position=88),
),
"/worksheets": Entry(
value_start=Location(line=7, column=16, position=109),
value_end=Location(line=26, column=3, position=566),
key_start=Location(line=7, column=2, position=95),
key_end=Location(line=7, column=14, position=107),
),
"/worksheets/0": Entry(
value_start=Location(line=8, column=4, position=115),
value_end=Location(line=25, column=5, position=562),
key_start=None,
key_end=None,
),
"/worksheets/0/cells": Entry(
value_start=Location(line=9, column=15, position=132),
value_end=Location(line=24, column=7, position=556),
key_start=Location(line=9, column=6, position=123),
key_end=Location(line=9, column=13, position=130),
),
"/worksheets/0/cells/0": Entry(
value_start=Location(line=10, column=8, position=142),
value_end=Location(line=23, column=9, position=548),
key_start=None,
key_end=None,
),
"/worksheets/0/cells/0/cell_type": Entry(
value_start=Location(line=11, column=23, position=167),
value_end=Location(line=11, column=29, position=173),
key_start=Location(line=11, column=10, position=154),
key_end=Location(line=11, column=21, position=165),
),
"/worksheets/0/cells/0/collapsed": Entry(
value_start=Location(line=12, column=23, position=198),
value_end=Location(line=12, column=28, position=203),
key_start=Location(line=12, column=10, position=185),
key_end=Location(line=12, column=21, position=196),
),
"/worksheets/0/cells/0/input": Entry(
value_start=Location(line=13, column=19, position=224),
value_end=Location(line=18, column=11, position=425),
key_start=Location(line=13, column=10, position=215),
key_end=Location(line=13, column=17, position=222),
),
"/worksheets/0/cells/0/input/0": Entry(
value_start=Location(line=14, column=12, position=238),
value_end=Location(line=14, column=35, position=261),
key_start=None,
key_end=None,
),
"/worksheets/0/cells/0/input/1": Entry(
value_start=Location(line=15, column=12, position=275),
value_end=Location(line=15, column=72, position=335),
key_start=None,
key_end=None,
),
"/worksheets/0/cells/0/input/2": Entry(
value_start=Location(line=16, column=12, position=349),
value_end=Location(line=16, column=38, position=375),
key_start=None,
key_end=None,
),
"/worksheets/0/cells/0/input/3": Entry(
value_start=Location(line=17, column=12, position=389),
value_end=Location(line=17, column=36, position=413),
key_start=None,
key_end=None,
),
"/worksheets/0/cells/0/language": Entry(
value_start=Location(line=19, column=22, position=449),
value_end=Location(line=19, column=30, position=457),
key_start=Location(line=19, column=10, position=437),
key_end=Location(line=19, column=20, position=447),
),
"/worksheets/0/cells/0/metadata": Entry(
value_start=Location(line=20, column=22, position=481),
value_end=Location(line=20, column=24, position=483),
key_start=Location(line=20, column=10, position=469),
key_end=Location(line=20, column=20, position=479),
),
"/worksheets/0/cells/0/outputs": Entry(
value_start=Location(line=21, column=21, position=506),
value_end=Location(line=21, column=23, position=508),
key_start=Location(line=21, column=10, position=495),
key_end=Location(line=21, column=19, position=504),
),
"/worksheets/0/cells/0/prompt_number": Entry(
value_start=Location(line=22, column=27, position=537),
value_end=Location(line=22, column=28, position=538),
key_start=Location(line=22, column=10, position=520),
key_end=Location(line=22, column=25, position=535),
),
}
This tells you the line, column and character position for the start and end location for each value in the JSON document.
Upvotes: 2
Reputation: 121
You can accomplish this in python using https://pypi.org/project/json-cfg/
Here's a recursive strategy for printing the line number for each key and each value.
import jsoncfg
from jsoncfg.config_classes import ConfigJSONObject, ConfigJSONArray, ConfigJSONScalar
def recursivePrint(element):
if isinstance(element, ConfigJSONObject):
# Dictionary
for key, value in element:
print(f"key \"{key}\" at line {jsoncfg.node_location(element[key]).line}")
recursivePrint(element[key])
elif isinstance(element, ConfigJSONArray):
# Array
for item in element:
recursivePrint(item)
elif isinstance(element, ConfigJSONScalar):
value = element()
if isinstance(value, str):
value = value.strip()
print(f"value \"{value}\" at line {jsoncfg.node_location(element).line}")
parsed = jsoncfg.load_config("example.json")
recursivePrint(parsed)
Screenshot of results
Upvotes: 2