How to read JSON/XML/YAML data into Sphinx RST file to programmatically generate a documentation page?

Viewed 648

Lets say I have a JSON/YAML/XML etc of zoo animals and I want to make some documentation for all of the animals in the zoo. So I have a JSON like:

{
  "zooName": "C town's Zoo",
  "animals": [
    "tiger": {
      "species":"some_species_name_here",
      "weight": 120
    },
    "bear":{
      "species":"some_other_species_name",
      "weight": 100
    }
  ]
}

In another SSG, I could do something like

 > Bring in a JSON file from /data/myfile.json

 > Access some index of that file like [animals][tiger], etc... 

> Show that data as a part of the HTML template that is made by, say, `tiger.rst`

How would I accomplish that in Sphinx? Let's say I have an animals.rst with a toc-tree for all my animals and then a file like this for each individual one.

Tiger
=======================================

Tiger info here.

Species: 
[[ Access my json here and show content from jsonfile[animals][tiger][species] ]]

Weight: 
[[ Access my json here and show content from jsonfile[animals][tiger][weight] ]]
1 Answers

You could create a Sphinx extension (e.g. dhellmann's datatemplates)... but a crude update.py preprocessing script would probably do:

#!/usr/bin/env python
"""To launch: ``$ python update.py > animals.rst``  """

import json

def headline(text, adorn='='):
    return text + '\n' + adorn*len(text)

def main():
    header = headline('Animals') + '\n\nAnimal info here.\n'
    footer = '\n.. End of document\n'
    mask = '* {name} -- {species}'

    with open('animals.json', 'r') as infile:
        data = json.load(infile)

    print(header)
    for beast in data['animals']:
        print(mask.format(**beast))
    print(footer)

if __name__ == '__main__':
    main()

For any more advanced layout, upgrade from Python string format to Jinja2 templates.

animals.json is slightly different from your example:

{
  "zooName": "C town's Zoo",
  "animals": [
    {"name": "tiger", "species": "some_species_name_here",  "weight": 120},
    {"name": "bear",  "species": "some_other_species_name", "weight": 100}
  ]
}

finally, add a rule to the Sphinx Makefile that triggers the script if JSON content changed.

Related