在python中,如何解析多层JSON?

时间:2019-12-04 12:50:25

标签: python json

请在Python 3中,我有一个脚本来使用请求访问API,然后将其转换为JSON

但是,某些信息位于较深的子级别,我似乎无法访问它。见下文:

private void BgColorList_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
    ListView view = (ListView)sender;
    var selected = view.SelectedItem;
    var container = view.ContainerFromItem(selected);
    if (container != null)
    {
        Ellipse ellipse = FindVisualChild<Ellipse>(container);
        if (ellipse != null)
        {
            //...
        }
    }
}

private static T FindVisualChild<T>(DependencyObject obj) where T : DependencyObject
{
    for (int i = 0; i < VisualTreeHelper.GetChildrenCount(obj); i++)
    {
        DependencyObject child = VisualTreeHelper.GetChild(obj, i);
        if (child != null && child is T)
            return (T)child;
        else
        {
            T childOfChild = FindVisualChild<T>(child);
            if (childOfChild != null)
                return childOfChild;
        }
    }
    return null;
}

当我尝试捕获“ NomeAutor”时,错误为typerror

这是项目的内容:

import requests

headers = {"Accept" : "application/json"}

url = "http://legis.senado.leg.br/dadosabertos/materia/20050"

try:
    r = requests.get(url, headers=headers)
except requests.exceptions.HTTPError as errh:
    print ("Http Error:",errh)
except requests.exceptions.ConnectionError as errc:
    print ("Error Connecting:",errc) 
except requests.exceptions.Timeout as errt:
    print ("Timeout Error:",errt)
except requests.exceptions.RequestException as err:
    print ("OOps: Something Else",err)

projects = r.json()

try:
    NomeAutor= str(projects['DetalheMateria']['Materia']['Autoria']['Autor']['NomeAutor'])
    print("ok")
except KeyError:
    NomeAutor = None                
    print("keyerror")
except TypeError:
    NomeAutor = None                     
    print("typerror")

print(NomeAutor)

请问有人知道为什么不捕获信息吗?

还有什么更简单的方法来捕获深度JSON子级别上的信息,而不必一路打通?

1 个答案:

答案 0 :(得分:2)

有2个问题:

  • 您正在加载的数据不是有效的json

  • Autorlist的字典,但您尝试将其作为dict来访问。


我建议您尝试python-benedict,它是具有许多功能的开源dict子类,包括标准化的I / O操作和键路径支持。 https://github.com/fabiocaccamo/python-benedict

安装:pip install python-benedict

然后:

from benedict import benedict as bdict

data_source = {
    'DetalheMateria': {
        '@xmlns:xsi': 'http://www.w3.org/2001/XMLSchema-instance',
        '@xsi:noNamespaceSchemaLocation': 'http://legis.senado.leg.br/dadosabertos/dados/DetalheMateriav5.xsd',
        'Metadados': {
            'Versao': '03/12/2019 21:36:18',
            'VersaoServico': '5',
            'DataVersaoServico': '2017-02-01',
            'DescricaoDataSet': 'Dados básicos da matéria, incluindo autoria, norma gerada e outras informações. A partir de fevereiro de 2019, os requerimentos de comissões permanentes passam a ser numerados com a mesma sistemática dos requerimentos das comissões temporárias, seguindo, portanto, o padrão: REQ 99/2019 - SIGLA_COMISSÃO. Dessa forma, para se buscar um requerimento de determinada comissão (com ano a partir de 2019), deve-se informar .../materia/sigla/número/ano?comissao=sigla da comissão.'
        },
        'Materia': {
            'IdentificacaoMateria': {
                'CodigoMateria': '20050',
                'SiglaCasaIdentificacaoMateria': 'SF',
                'NomeCasaIdentificacaoMateria': 'Senado Federal',
                'SiglaSubtipoMateria': 'PLC',
                'DescricaoSubtipoMateria': 'PROJETO DE LEI DA CÂMARA',
                'NumeroMateria': '00035',
                'AnoMateria': '1988',
                'DescricaoObjetivoProcesso': 'Revisora',
                'DescricaoIdentificacaoMateria': 'PLC 35/1988',
                'IndicadorTramitando': 'Não'
            },
            'DadosBasicosMateria': {
                'EmentaMateria': "DECLARA FERIADO NACIONAL O DIA 20 DE NOVEMBRO, ANIVERSARIO DA MORTE   \n      DE ZUMBI DOS PALMARES, CONSAGRADO PELA COMUNIDADE AFRO-BRASILEIRA     \n      COMO 'DIA NACIONAL DA CONSCIENCIA NEGRA.'                          \n      ",
                'IndicadorComplementar': 'Não',
                'DataApresentacao': '1987-12-01',
                'DataLeitura': '1987-12-01'
            },
            'Autoria': {
                'Autor': [
                    {'NomeAutor': 'Câmara dos Deputados', 'SiglaTipoAutor': 'CAMARA', 'DescricaoTipoAutor': 'Câmara dos Deputados', 'NumOrdemAutor': '1', 'IndicadorOutrosAutores': 'Não'}
                ]
            },
            'Iniciativa': {
                'SiglaTipoIniciativa': 'DEPUTADO',
                'DescricaoTipoIniciativa': 'Deputado',
                'DescricaoIniciativa': 'BENEDITA DA SILVA'
            },
            'OrigemMateria': {
                'SiglaCasaOrigem': 'CD',
                'NomeCasaOrigem': 'Câmara dos Deputados'
            },
            'CasaIniciadoraNoLegislativo': {
                'SiglaCasaIniciadora': 'SF',
                'NomeCasaIniciadora': 'Senado Federal'
            },
            'OutrosNumerosDaMateria': {
                'OutroNumeroDaMateria': {
                    'IdentificacaoMateria': {
                        'SiglaCasaIdentificacaoMateria': 'CD',
                        'NomeCasaIdentificacaoMateria': 'Câmara dos Deputados',
                        'SiglaSubtipoMateria': 'PL',
                        'DescricaoSubtipoMateria': 'PROJETO DE LEI',
                        'NumeroMateria': '00293',
                        'AnoMateria': '1987'
                    },
                    'DescricaoTipoNumeracao': 'CasaIniciadora'
                }
            },
            'SituacaoAtual': {
                'Autuacoes': {
                    'Autuacao': [
                        {
                            'NumeroAutuacao': '1',
                            'Situacao': {
                                'DataSituacao': '1996-01-23',
                                'CodigoSituacao': '28',
                                'SiglaSituacao': 'ARQVD',
                                'DescricaoSituacao': 'ARQUIVADA AO FINAL DA LEGISLATURA'
                            },
                            'Local': {
                                'DataLocal': '1996-01-23',
                                'CodigoLocal': '206',
                                'TipoLocal': 'A',
                                'SiglaCasaLocal': 'SF',
                                'NomeCasaLocal': 'Senado Federal',
                                'SiglaLocal': 'SSEXP',
                                'NomeLocal': 'SUBSECRETARIA DE EXPEDIENTE'
                            }
                        }
                    ]
                }
            },
            'OutrasInformacoes': {
                'Servico': [
                    {
                        'NomeServico': 'EmendaMateria',
                        'DescricaoServico': 'Emendas da matéria',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/materia/emendas/20050?v=6'
                    },
                    {
                        'NomeServico': 'MovimentacaoMateria',
                        'DescricaoServico': 'Movimentações da matéria, como tramitações, despachos e prazos.\n      Evoluções:\n      14/8/2019\n      - criada nova Tag "DeliberacoesMPV" para as deliberações de MPV;\n - criada nova Tag "DescricaoItemCalendario" subord',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/materia/movimentacoes/20050?v=6'
                    },
                    {
                        'NomeServico': 'RelatoriaMateria',
                        'DescricaoServico': 'Relatoria atual e relatorias encerradas (histórico) da matéria',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/materia/relatorias/20050?v=5'
                    },
                    {
                        'NomeServico': 'TextoMateria',
                        'DescricaoServico': 'Textos da matéria. \n      Evoluções da versão: \n      28/8/2019 - incluída a tag "AutoriaTexto", sob a tag "Texto".',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/materia/textos/20050?v=5'
                    },
                    {
                        'NomeServico': 'VotacaoMateria',
                        'DescricaoServico': 'Votações da matéria',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/materia/votacoes/20050?v=5'
                    },
                    {
                        'NomeServico': 'VotacoesComissao',
                        'UrlServico': 'http://legis.senado.leg.br/dadosabertos/votacaoComissao/materia/PLC/00035/1988?v=1'
                    }
                ]
            },
            'UrlGlossario': 'http://legis.senado.leg.br/dadosabertos/glossario/lista'
        }
    }
}

data = bdict(data_source)

# once your url will return a valid json you could just do:
# data = bdict.from_json('http://legis.senado.leg.br/dadosabertos/materia/20050')

author = data[['DetalheMateria', 'Materia', 'Autoria', 'Autor']][0]
# or: author = data['DetalheMateria.Materia.Autoria.Autor'][0]
author_name = author['NomeAutor']
print(author_name) # --> Câmara dos Deputados