Tenho uma API no Protheus que faz uma consulta na SC7 utilizando o TcQuery na SC7 informação de cabeçalho e itens ficam na mesma tabela e eu quero montar um json com a seguinte estrutura:
{
"cabecalho": { .... },
"itens": [{...},{...}]
}
Para isso eu montei o seguinte código em ADVPL:
dbSelectArea("SC7")
cQrySC7 := " SELECT * "
cQrySC7 += " FROM " + RetSqlName("SC7") + " "
cQrySC7 += " WHERE D_E_L_E_T_ = ' ' "
TcQuery cQrySC7 New Alias cQryAli
If cQryAli->(!Eof())
oObjGet["success"] := .T.
oObjGet["message"] := ""
oObjGet["data"] := {}
While cQryAli->(!Eof())
oObjDta := JsonObject():New()
oObjDta["itens"] := {}
// Busca os itens do pedido de compra
oObjItens := JsonObject():New()
cQryItem := " SELECT * "
cQryItem += " FROM " + RetSqlName("SC7") + " "
cQryItem += " WHERE C7_NUM = '" + cQryAli->C7_NUM + "' "
cQryItem += " AND D_E_L_E_T_ = ' ' "
TcQuery cQryItem New Alias cAliItem
If cAliItem->(!Eof())
cAliItem->( DbGotop() )
While cAliItem->(!Eof())
oObjItens["codigo_produto"] := validaRetornoBanco(cAliItem->C7_PRODUTO)
oObjItens["descricao_produto"] := validaRetornoBanco(cAliItem->C7_DESCRI)
oObjItens["quantidade"] := validaRetornoBanco(cAliItem->C7_QUANT)
oObjItens["preco_unitario"] := validaRetornoBanco(cAliItem->C7_PRECO)
oObjItens["preco_total"] := validaRetornoBanco(cAliItem->C7_TOTAL)
oObjItens["desconto_item"] := validaRetornoBanco(cAliItem->C7_VLDESC)
oObjItens["condicao_pagamento"] := validaRetornoBanco(cAliItem->C7_COND)
oObjItens["codigo_fornecedor"] := validaRetornoBanco(cAliItem->C7_FORNECE)
oObjItens["data_entrega"] := validaRetornoBanco(cAliItem->C7_DATPRF)
oObjItens["observacoes"] := validaRetornoBanco(cAliItem->C7_OBSM)
oObjItens["aliquota_ipi"] := validaRetornoBanco(cAliItem->C7_IPI)
oObjItens["nmr_solicitacao_compra"] := validaRetornoBanco(cAliItem->C7_NUMSC)
oObjItens["valor_frete"] := validaRetornoBanco(cAliItem->C7_VALFRE)
aAdd( oObjDta["itens"], oObjItens )
cAliItem->(dbSkip())
EndDo
Else
lRet := .F.
ConOut("Itens do pedido de compra não encontrado!")
SetRestFault(404, EncodeUTF8("Itens do pedido de compra não encontrado"))
EndIf
// Transformando os dados do SQL para o objeto JSON
oObjDta["data_emissao_pedido"] := validaRetornoBanco(cQryAli->C7_EMISSAO)
oObjDta["codigo_fornecedor"] := validaRetornoBanco(cQryAli->C7_FORNECE)
oObjDta["loja_fornecedor"] := validaRetornoBanco(cQryAli->C7_LOJA)
oObjDta["condicao_pagamento"] := validaRetornoBanco(cQryAli->C7_COND)
oObjDta["contato_fornecedor"] := validaRetornoBanco(cQryAli->C7_CONTATO)
oObjDta["filial_entrada_mercador"] := validaRetornoBanco(cQryAli->C7_FILENT)
oObjDta["moeda_pedido"] := validaRetornoBanco(cQryAli->C7_MOEDA)
oObjDta["taxa_cambio"] := validaRetornoBanco(cQryAli->C7_TXMOEDA)
oObjDta["numero_solicitacao"] := validaRetornoBanco(cQryAli->C7_NUMSC)
aAdd( oObjGet["data"], oObjDta )
cQryAli->(dbSkip())
EndDo
Else
lRet := .F.
ConOut("Pedido não localizados!")
SetRestFault(404, EncodeUTF8("Pedido não localizados"))
EndIf
// cAliItem->(dbCloseArea())
cQryAli->(dbCloseArea())
Mas dessa maneira a API me retorna um status 500 com o erro “internal server error”, e se eu remover o While que executa dentro desse While ele retorna corretamente.
Minha dúvida, é possível utilizar um While dentro de outro While, se não como posso fazer essa busca?