Problema consumiendo XML Web Service

750 views
Skip to first unread message

romalch

unread,
Aug 19, 2015, 10:18:21 AM8/19/15
to Comunidad de Visual Foxpro en Español
Buen dia, estoy implementado en mi aplicacion la lectura de datos con un WebService.

Al analizar el webservice con SOAPUI este me da varios niveles de metodos que al momento de cargar el webservice en mi VFP no logro llegar a todos los metodos. He tratado de hacerlo en VB segun como me proporciona le proveedor del WebService pero al momento de registrar la refrencia web mi Visual Studio se queda colgado y no logo terminar la referencia web.  Alguno de ustedes puede ayudarme un poco con esto.

a continuacion el codigo que uso para consumir el ws

LOCAL loSCService AS "XML Web Service"
*LOCAL loSCService AS "MSSOAP.SoapClient30"
* Do not remove or alter following line. It is used to support IntelliSense for your XML Web service.
*__VFPWSDef__: loSCService = http://tt.ws.sellercloud.com/scservice.asmx?WSDL , SCService , SCServiceSoap
LOCAL loException, lcErrorMsg, loWSHandler
TRY
loWSHandler = NEWOBJECT("WSHandler",IIF(VERSION(2)=0,"",HOME()+"FFC\")+"_ws3client.vcx")
loSCService = loWSHandler.SetupClient("http://tt.ws.sellercloud.com/scservice.asmx?WSDL", "SCService", "SCServiceSoap")
Local sellercloud as new sc.SCService  && Esto deberia devolver un objeto 
    sellerCloud.timeout =  5*60*1000       && timeout es un metodo al que no consigo acceder desde VFP  (si aparece desde SOAPUI)
    sellerCloud.AuthHeaderValue = SC.authHeader && AuthHeader es un metodo al que no consigo acceder desde VFP  (si aparece desde SOAPUI)
    sellerCloud.AuthHeaderValue.UserName = "te...@test.com"
    sellerCloud.AuthHeaderValue.Password = "test"
CATCH TO loException
lcErrorMsg="Error: "+TRANSFORM(loException.Errorno)+" - "+loException.Message
DO CASE
CASE VARTYPE(loSCService)#"O"
* Handle SOAP error connecting to web service
*lcErrorMsg=lcErrorMsg+CHR(13)+loSCService.Detail+CHR(13)+'Fui Yo'
CASE !EMPTY(loSCService.FaultCode)
* Handle SOAP error calling method
lcErrorMsg=lcErrorMsg+CHR(13)+loSCService.Detail+CHR(13)+'(romalch)'
OTHERWISE
* Handle other error
ENDCASE
* Use for debugging purposes
MESSAGEBOX(lcErrorMsg)
FINALLY
ENDTRY

Desde ya gracias por su apoyo.

Fernando D. Bozzo

unread,
Aug 19, 2015, 11:36:18 AM8/19/15
to Comunidad de Visual Foxpro en Español
Hola:

Intentá configurar tu web-service en Fox siguiendo este ejemplo, a ver si te funciona:

https://groups.google.com/d/msg/publicesvfoxpro/Qax6f4XYjeQ/QjtkD29pAdoJ


Saludos.-

Jorge Kiernan

unread,
Aug 21, 2015, 11:15:58 PM8/21/15
to publicesvfoxpro
Hola, yo tengo un problema similar de lectura de webservice, pero que se origina en que el proveedor no uso tecnología SOAP sino REST ... y se me quemaron las naves. 
Todavía no logré encontrar referencias a como invocar desde vfp estos ws-rest de los cuales me acabo de enterar que existen. 
Si alguno tiene algo al respecto, mil agradecimientos.

Victor Espina

unread,
Aug 22, 2015, 11:26:56 AM8/22/15
to Comunidad de Visual Foxpro en Español
Usa mi libraria JSON:

Usando JSON puedes consumir webservices tipo REST facilmente, tanto usando respuestas XML como JSON.  Por ejemplo:

oResponse = json.httpGet("http://www.thomas-bayer.com/sqlrest/CUSTOMER/18", "xml")
oCustomer
= oResponse.json.customer
?oCustomer.firstName --> "Sylvia"


Saludos

Victor Espina

Victor Espina

unread,
Aug 22, 2015, 11:29:18 AM8/22/15
to Comunidad de Visual Foxpro en Español
La respuesta original de esa llamada REST es esta:

<?xml version="1.0"?>
<CUSTOMER xmlns:xlink="http://www.w3.org/1999/xlink">
   
<ID>18</ID>
   
<FIRSTNAME>Sylvia</FIRSTNAME>
   
<LASTNAME>Fuller</LASTNAME>
   
<STREET>158 - 20th Ave.</STREET>
   
<CITY>Paris</CITY>
</CUSTOMER>



La libreria JSON toma esa respuesta y la convierte en un objeto para facilitar el acceso a los datos.  Lo mismo sucede si el webservice responde con un string JSON en lugar de XML; la libreria toma la respuesta y la convierte en un objeto.

Saludos

Victor Espina

Hugo C.

unread,
Aug 22, 2015, 6:02:14 PM8/22/15
to Comunidad de Visual Foxpro en Español
Que tal Victor, la librería también esta lista para los post, put y delete con JSON ?

Saludos.

Angel Dario Rodriguez

unread,
Aug 23, 2015, 10:37:23 AM8/23/15
to publice...@googlegroups.com
Maestro Victor, como puedo utilizar el ejemplo que usted nos indico mas arriba, me retorna error al ejecutarlo.

Victor Espina

unread,
Aug 23, 2015, 11:23:16 AM8/23/15
to Comunidad de Visual Foxpro en Español
Cual error ?

Victor

Victor Espina

unread,
Aug 23, 2015, 11:24:16 AM8/23/15
to Comunidad de Visual Foxpro en Español
Olvide comentar que antes de ejecutar el codigo, deben cargar la libreria JSON en memoria, haciendo:

<vfp>
DO json
</vfp>

Victor Espina


El sábado, 22 de agosto de 2015, 11:26:56 (UTC-4), Victor Espina escribió:

Victor Espina

unread,
Aug 23, 2015, 11:25:25 AM8/23/15
to Comunidad de Visual Foxpro en Español
Si ejecutaste el codigo tal cual lo escribi, tu problema es que la libreria JSON no esta en memoria.  Aqui va el codigo completo:

do json
oResponse = json.httpGet("http://www.thomas-bayer.com/sqlrest/CUSTOMER/18", "xml")
oCustomer 
= oResponse.json.customer
?oCustomer.firstName --> "Sylvia"


Victor Espina

El domingo, 23 de agosto de 2015, 10:37:23 (UTC-4), angel_darior escribió:

Victor Espina

unread,
Aug 23, 2015, 11:27:56 AM8/23/15
to Comunidad de Visual Foxpro en Español
La verdad no; el metodo httpGet() esta pensado para unicamente consumir metodos con GET.   Probablemente deberia crear una clase distinta para el tema de la comunicacion con webservices tipo REST, por esto de la separacion de responsabilidades.

Dejame meditar un poco sobre esto, porque creo que seria interesante.


Victor Espina

Jorge Kiernan

unread,
Aug 24, 2015, 9:09:11 AM8/24/15
to publicesvfoxpro
Estimado Victor, primero que nada, gracias por el aporte de la rutina json. 
Algo así escapa rotundamente a mis modestas capacidades.
La estoy probando, pero algo se me escapa, como respuesta obtengo que son objetos, pero no logro llegar a sus valores concretos.
El caso se refiere a un seguimiento de movimientos de flota de vehiculos via GPS.
Arme una sencilla prueba con lo que sigue:

WAIT WINDOW NOWAIT 'invocando el web service...'
oResponse = json.httpGet(lcweb, "xml")
WAIT CLEAR 
** hasta aqui todo bien, pero...
WAIT WINDOW oResponse.json.VEHI_TXT
WAIT WINDOW oCustomer.json.hora_inicio
** la respuesta en ambos casos es la palabra OBJECT 
SET STEP ON 
* al pasar al debuguer en la ventana watch, da una estructura anidada en la cual no llego a obtener los valores.

*!* esta es la estructura de los datos esperados, puede verse mas claramente si escribis la url en el explorador
*!* HORA_INICIO / Hora Inicial
*!* HORA_FIN / Hora Final
*!* HORAS_DESVIO / Desvío
*!* HORAS_MANEJO / Horas Manejo
*!* KM_REC / Total Km
*!* VEHI_TXT / Vehículo
*!* EMPR_TXT / Empresa
*!* HORAS_DESCANSO / Horas Descanso
*!* HORAS_TOTAL / Horas Total
*!* ULTIMA_POS / Última Posición
*!* ULTIMA_COM / Última Comunicación
*!* VELOCIDAD / Velocidad
*!* REFERENCIA / Referencia
*!* DIRECCION / Dirección

Desde ya, muchisimas gracias por tu tiempo.
Desde Buenos Aires, Argentina, Mercosur.
Jorge Kiernan

Julián May

unread,
Aug 24, 2015, 10:00:13 AM8/24/15
to Comunidad de Visual Foxpro en Español
Buen día jkiernan accede primero desde la raíz como lo indica Victor en el ejemplo.

-- Estructura de tu XML de respuesta.
    
<REPORTE_VIAJE>
    <ERROR>0</ERROR>
    <VIAJE>
        <HORA_INICIO>04:09:34</HORA_INICIO>
        <HORA_FIN>16:09:19</HORA_FIN>
        <HORAS_DESVIO>02:07</HORAS_DESVIO>
        <HORAS_MANEJO>09:53</HORAS_MANEJO>
        <KM_REC>168.46</KM_REC>
        <VEHI_TXT>U. 122 - FXL 031(FXL 031)</VEHI_TXT>
        <EMPR_TXT>4.6.1.1 TRANSPORTE DON ANTONIO S.R.L. - LIQUIDOS - PETROBRAS</EMPR_TXT>
        <HORAS_DESCANSO>02:15</HORAS_DESCANSO>
        <HORAS_TOTAL>12:07</HORAS_TOTAL>
        <ULTIMA_POS>24/08/2015 10:40:41</ULTIMA_POS>
        <ULTIMA_COM>24/08/2015 10:40:43</ULTIMA_COM>
        <VELOCIDAD>0</VELOCIDAD>
        <REFERENCIA></REFERENCIA>
        <DIRECCION>SGTO PONCE 2006-2400, DOCK SUD, AVELLANEDA, BUENOS AIRES</DIRECCION>
   </VIAJE>
</REPORTE_VIAJE>

-- Consumiendo el servicio tipo REST.


WAIT WINDOW NOWAIT 'invocando el web service...'
oResponse = json.httpGet(lcweb, "xml")

oReporteViaje = oResponse.json.REPORTE_VIAJE

? oReporteViaje.VIAJE.HORA_INICIO 
? oReporteViaje.VIAJE.HORA_FIN

Saludos.

Julián May.

Jorge Kiernan

unread,
Aug 24, 2015, 10:50:33 AM8/24/15
to publicesvfoxpro
Eureka!!
Me faltaba el paso de convertir el resultado a un cursor con
=XMLTOCURSOR(oResponse.raw)
que por defecto genera el cursor XMLRESULT ( con coma y un nombre, nominas el cursor como lo desees)
¡Infinitas gracias a todos! No lo hubiese logrado sin ustedes.
Jorge Kiernan

Victor Espina

unread,
Aug 24, 2015, 11:23:46 AM8/24/15
to Comunidad de Visual Foxpro en Español
La cosa era un poco mas complicada.  Primero, los nodos de datos estaban expresados con ![CDATA, asi que tuve que anadirle soporte a ese tipo de nodos (esta era la razon por la que el valor del nodo terminaba como object).   Pero lo mas complicado fue que el xml no estaba "correctamente" formateado".  Resulta que el nodo REPORTE_VIAJE contiene un nodo ERROR y luego 128 nodos VIAJE.  En estos casos, la estructura del XML que uno espera seria algo asi:

<REPORTE_VIAJE>
 
<ERROR>0</ERROR>
 
<VIAJES>
   
<VIAJE>...</VIAJE>
   
<VIAJE>...</VIAJE>
 
</VIAJES>
</REPORTE_VIAJE>



Pero en este caso el nodo padre VIAJES no existia, asi que todo los nodo VIAJE estaban directamente bajo REPORTE_VIAJE, lo cual no era procesado correcamente por mi rutina. La nueva version 1.12 (http://www.noiqs.com/sos/json.prg) ya maneja este caso directamente, por lo que quedaria asi:

DO json
oResponse
= json.httpGet("http://.....")
oData
= oResponse.json.reporte_viaje
?oData.error --> 0
?oData.viaje.Count --> 128

FOR EACH oViaje IN oData
.viaje
 
?oViaje.vehiculo_txt
ENDFOR



Saludos

Victor Espina
Reply all
Reply to author
Forward
0 new messages