Árvore de páginas

Disponibiliza uma API REST no Dashboard para visualizar um gráfico de Pizza ou Polar.




Exemplo2.prw
#INCLUDE "TOTVS.CH"
#INCLUDE "RESTFUL.CH"

//------------------------------------------------------------------------
/*/{Protheus.doc} Exemplo2
    Exemplo de API de integração de Graficos de Pizza e/ou Polar

    @author     Squad CRM & Faturamento
    @since      26/03/2020
    @version    12.1.27  
/*/
//------------------------------------------------------------------------
WSRESTFUL Exemplo2 DESCRIPTION "Exemplo de API - Grafico Pizza e Polar"

    WSDATA JsonFilter       AS STRING	OPTIONAL
    WSDATA drillDownFilter  AS STRING	OPTIONAL
    WSDATA Page				AS INTEGER	OPTIONAL
    WSDATA PageSize			AS INTEGER	OPTIONAL

    WSMETHOD GET form ;
        DESCRIPTION "Form de Cadastro do Gráfico" ;
        WSSYNTAX "/charts/form/" ;
        PATH "/charts/form";
        PRODUCES APPLICATION_JSON

    WSMETHOD GET filterItens ;
        DESCRIPTION "Carrega os filtros adicionais disponíveis para o gráfico" ;
        WSSYNTAX "/charts/filterItens/" ;
        PATH "/charts/filterItens";
        PRODUCES APPLICATION_JSON

    WSMETHOD POST retdados ;
        DESCRIPTION "Retorna as Informações do Gráfico" ;
        WSSYNTAX "/charts/retdados/{JsonFilter}" ;
        PATH "/charts/retdados";
        PRODUCES APPLICATION_JSON

    WSMETHOD POST itemsDetails ;
        DESCRIPTION "Carrega o detalhamento do gráfico" ;
        WSSYNTAX "/charts/itemsDetails/{JsonFilter}" ;
        PATH "/charts/itemsDetails";
        PRODUCES APPLICATION_JSON

ENDWSRESTFUL

//-------------------------------------------------------------------
/*/{Protheus.doc} GET form
    Retorna os campos que apresentados no Cadastro do Grafico.
    Devera seguir o formato do Dynamic Form do PO-UI.
    https://po-ui.io/tools/dynamic-form
    
    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
WSMETHOD GET form WSSERVICE Exemplo2

    Local oResponse   := JsonObject():New()
    Local oCoreDash   := CoreDash():New()

    oCoreDash:SetPOForm("Tipo de Gráfico"    , "charttype"     , 6   , "Tipo de Gráfico"     , .T., "string",;
     oCoreDash:SetPOCombo({{"pie","Pizza"},{"polarArea","Polar"}}))
    oCoreDash:SetPOForm("Datas"              , "datainicio"      , 6   , "Dt. Emissão De"      , .T., "date")
    oCoreDash:SetPOForm(""                   , "datafim"         , 6   , "Dt. Emissão Ate"     , .T., "date")    

    oResponse  := oCoreDash:GetPOForm()

    Self:SetResponse( EncodeUtf8(oResponse:ToJson()))

Return .T.

//-------------------------------------------------------------------
/*/{Protheus.doc} GET filterItens
    Retorna os campos que poderão ser filtrados

    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
WSMETHOD GET filterItens WSSERVICE Exemplo2

    Local aItems        := {}   
    Local oResponse     := JsonObject():New()
    Local oCoreDash     := CoreDash():New()
 
    aAdd(aItems, { "customerId" , "Cod. Cliente"    })
    aAdd(aItems, { "store"      , "Loja"            })
    aAdd(aItems, { "state"      , "Estado"          })
 
    /*Retorna um Objeto no formato de property e Label*/
    oResponse["items"] := oCoreDash:SetPOHeader(aItems)
 
    Self:SetResponse( EncodeUtf8(oResponse:ToJson()))

Return .T.

//-------------------------------------------------------------------
/*/{Protheus.doc} POST retdados
    Retorna um objeto JSON com as informações e valores do Grafico

    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
WSMETHOD POST retdados WSRECEIVE JsonFilter WSSERVICE Exemplo2

    Local oResponse   := JsonObject():New()
    Local oCoreDash   := CoreDash():New()
    Local oJson       := JsonObject():New()

    oJson:FromJson(DecodeUtf8(Self:GetContent()))

    retDados(@oResponse, oCoreDash, oJson)

    Self:SetResponse( EncodeUtf8(oResponse:ToJson()))

    oResponse := Nil
    FreeObj( oResponse )

    oCoreDash:Destroy()
    FreeObj( oCoreDash )

Return .T.

//-------------------------------------------------------------------
/*/{Protheus.doc} POST retdados
    Retorna os items utilizado no Drilldown

    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
WSMETHOD POST itemsDetails WSRECEIVE JsonFilter, drillDownFilter WSRESTFUL Exemplo2

    Local aHeader     := {}
    Local aItems      := {}
    Local aRet        := {}
    Local cBody       := DecodeUtf8(Self:GetContent())
    Local cError      := "Erro na Requisição"
    Local cSelect     := ""
    Local cWhere      := ""
    Local lRet        := .T.
    Local oCoreDash  := CoreDash():New()
    Local oBody       := JsonObject():New()
    Local oJsonFilter := JsonObject():New()
    Local oJsonDD     := JsonObject():New()

    If !Empty(cBody)
        oBody:FromJson(cBody)

        If ValType(oBody["chartFilter"]) == "J"
            oJsonFilter := oBody["chartFilter"]
        EndIf

        If ValType(oBody["detailFilter"]) == "A"
            oJsonDD := oBody["detailFilter"]
        EndIf
    EndIf

    Self:SetContentType("application/json")

    If oJsonFilter:GetJsonText("level") == "null" .Or. Len(oJsonFilter["level"]) == 0        
        If Len(oJsonDD) == 0 //Nivel 1 do Drilldown
            aHeader := {;
                {"document"     , "Documento" ,"link"   },;
                {"series"       , "Serie"               },;
                {"state"        , "UF"                  },;
                {"documentType" , "Tipo"                },;
                {"dateOfIssue"  , "Emissão"             };
                }

            aItems := {;
                {"document"     , "F2_DOC"      },;
                {"series"       , "F2_SERIE"    },;
                {"state"        , "F2_EST"      },;
                {"documentType" , "F2_TIPO"     },;
                {"dateOfIssue"  , "F2_EMISSAO"  };
                }

            cSelect := " F2_DOC, F2_SERIE, F2_EST, F2_TIPO, F2_EMISSAO, F2_TIPO "

            aRet := QuerySF2(cSelect)

        Elseif Len(oJsonDD) == 1 //Nivel 2 do Drilldown

            aHeader := {;
                {"D2_ITEM"  , "Item"                            },;
                {"D2_COD"   , "Cod. Produto", "link"            },;
                {"B1_DESC"  , "Desc. Produto "                  },;
                {"D2_PRCVEN", "Vlr.Unitario", "currency","BRL"  },;
                {"D2_QUANT" , "Quantidade","number",'1.2-5'     },;
                {"D2_TOTAL" , "Vlr. Total", "currency","BRL"    },;
                {"D2_LOCAL" , "Armazem"                         };
                }

            aItems := {;
                {"D2_ITEM"      , "D2_ITEM"},;
                {"D2_COD"       , "D2_COD"},;
                {"B1_DESC"      , "B1_DESC"},;
                {"D2_PRCVEN"    , "D2_PRCVEN"},;
                {"D2_QUANT"     , "D2_QUANT"},;
                {"D2_TOTAL"     , "D2_TOTAL"},;
                {"D2_LOCAL"     , "D2_LOCAL"};
                }

            cSelect := " D2_ITEM, D2_COD, B1_DESC, D2_PRCVEN, D2_QUANT, D2_TOTAL, D2_LOCAL "
            cWhere := " D2_DOC = '" + oJsonDD[1]['document'] + "' AND D2_SERIE = '" + oJsonDD[1]['series'] + "' "

            aRet := QuerySD2(cSelect, cWhere)       
        Endif
    Else
        //Monta o Drilldown do grafico nivel 2
        aHeader := {;
            {"document"     , "Documento"   },;
            {"series"       , "Serie"               },;
            {"state"        , "UF"                  },;
            {"documentType" , "Tipo"                },;
            {"dateOfIssue"  , "Emissão"             };
            }

        aItems := {;
            {"document"     , "F2_DOC"      },;
            {"series"       , "F2_SERIE"    },;
            {"state"        , "F2_EST"      },;
            {"documentType" , "F2_TIPO"     },;
            {"dateOfIssue"  , "F2_EMISSAO"  };
            }

        cSelect := " F2_DOC, F2_SERIE, F2_EST, F2_TIPO, F2_EMISSAO, F2_TIPO "

        aRet := QuerySF2(cSelect)
    EndIf

    oCoreDash:SetQuery(aRet[1])
    oCoreDash:SetWhere(aRet[2])    
    oCoreDash:SetFields(aItems)
    oCoreDash:SetApiQstring(Self:aQueryString)
    oCoreDash:BuildJson()

    If lRet
        oCoreDash:SetPOHeader(aHeader)
        Self:SetResponse( oCoreDash:ToObjectJson() )
    Else
        cError := oCoreDash:GetJsonError()
        SetRestFault( 500,  EncodeUtf8(cError) )
    EndIf

    oCoreDash:Destroy()
    FreeObj(oJsonDD)
    FreeObj(oJsonFilter)
    FreeObj(oBody)

    aSize(aRet, 0)
    aSize(aItems, 0)
    aSize(aHeader, 0)

Return lRet
//-------------------------------------------------------------------
/*/{Protheus.doc} retDados
    Retorna os dados que poderão ser apresentados no Grafico

    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
Static Function retDados(oResponse, oCoreDash, oJson)
    Local aData     := {}
    Local aDataFim  := {}
    Local aCab      := {}
    Local nLoop     := 0

    If oJson:GetJsonText("level") == "null" .Or. Len(oJson["level"]) == 0
        aCab := GetUF()

        For nLoop := 1 To Len(aCab)
            aAdd(aData, Randomize(1,999) )
        Next nLoop

        aDataFim := {}
        aAdd(aDataFim, oCoreDash:SetChart(aCab,aData,/*lCurrency*/,,"Nota fiscal por Estado"))
    ElseIf Len(oJson["level"]) == 1
        aCab := GetTipoNF()

        For nLoop := 1 To Len(aCab)
            aAdd(aData, Randomize(1,999) )
        Next nLoop

        aAdd(aDataFim, oCoreDash:SetChart(aCab,aData,/*lCurrency*/,"pie","Quantidade de Notas por Tipos"))

    ElseIf Len(oJson["level"]) == 2

        aCab := GetTopCli()

        For nLoop := 1 To Len(aCab)
            aAdd(aData, Randomize(1, 999) )
        Next nLoop

        oCoreDash:SetGraphInfo( aData, 'Notas', 'bar', "rgba(58,145,231,0.92)" )
        aAdd(aDataFim, oCoreDash:SetChart(aCab,,/*lCurrency*/,"bar","TOP 10 Clientes por Tipo de Nota"))

    Endif

    oResponse["items"] := aDataFim

Return Nil


//-------------------------------------------------------------------
/*/{Protheus.doc} QuerySF2
    Monta a query responsável por trazer os registro da Nota fiscal

    @param cSelect, Caractere, Campos que serão retornados no SELECT
    @param cFilter, Caractere, Filtro complementar utilizado na clausula WHERE
    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
Static Function QuerySF2(cSelect, cFilter )
    Local cQuery
    Local cWhere 

    Default cSelect := " SF2.F2_DOC, SF2.F2_SERIE, SF2.F2_CLIENTE, SF2.F2_LOJA, SF2.F2_TIPO "
    Default cFilter := ""

    cQuery := " SELECT " + cSelect + " FROM " + RetSqlName("SF2") + " SF2 "
    cWhere := " SF2.F2_FILIAL = '" + xFilial("SF2") + "' "
    If !Empty(cFilter)
        cWhere += " AND " + cFilter
    Endif
    cWhere += " AND SF2.D_E_L_E_T_ = ' ' "

Return { cQuery, cWhere }

//-------------------------------------------------------------------
/*/{Protheus.doc} QuerySD2
    Monta a query responsável por trazer os registro da Nota fiscal

    @param cSelect, Caractere, Campos que serão retornados no SELECT
    @param cFilter, Caractere, Filtro complementar utilizado na clausula WHERE
    @author Squad CRM & Faturamento
    @since 28/07/2020
    @version 12.1.27
/*/
//-------------------------------------------------------------------
Static Function QuerySD2(cSelect, cFilter)
    Local cQuery
    Local cWhere

    Default cSelect := " SD2.D2_DOC, SD2.D2_ITEM, SD2.D2_COD "
    Default cFilter := ""

    cQuery := " SELECT " + cSelect + " FROM " + RetSqlName("SD2") + " SD2 "
    cQuery += " INNER JOIN SB1T10 SB1 "
    cQuery += " ON B1_COD = D2_COD AND SB1.D_E_L_E_T_ = ' ' AND B1_FILIAL = '" + xFilial("SB1") + "' "

    cWhere := " SD2.D2_FILIAL = '" + xFilial("SD2") + "' "
    If !Empty(cFilter)
        cWhere += " AND " + cFilter
    Endif
    cWhere += " AND SD2.D_E_L_E_T_ = ' ' "

Return {cQuery, cWhere}




Demais informações

Consultar a documentação do CoreDash.