Page 1 of 1

Como tomar fecha y hora de un archivo en un FTP??

Posted: Sun May 06, 2012 5:11 pm
by gsabattino
Saludos Gente!!!

Luego de haberme dado _ con conectividad de xH+FW con servidores FTP (en buena parte gracias a un post de Enrico Maria Giordano) y tener funcionando todo lo relativo a la admistración de carpetas (directorios) y archivos, me encuentro con otro pequeño problema que me tiene trancado...

Necesito algo muy simple y es obtener fecha y hora de un archivo que se encuentre dentro de una carpeta del servidor FTP

Estoy haciendo esto:
hInternet :=INTERNETOPEN( "CualquierCosa", INTERNET_OPEN_TYPE_DIRECT, 0, 0, 0 )
hConnect :=INTERNETCONNECT( hInternet, cFTP_url, INTERNET_INVALID_PORT_NUMBER, cFTP_Usr, cFTP_Clv, INTERNET_SERVICE_FTP, 0, 0 )

lFTPError :=.f.
do while ( .not. lFTPError ) .and. ( nItem<=len( aFileADW ) )

cADWFile :=oADWin:cDrive+oADWin:cFolder+'\'+aFileADW[ nItem, 1 ]
cFTPFile :=cFTPFldr+'/'+aFileADW[ nItem, 1 ]
lFTPOk :=FTPPUTFILE( hConnect, cADWFile, cFTPFile, 0, 0 )
nCount :=UpdateMeter( oMeter, nCount, nRefresh )
lFTPError :=( .not. lFTPOk )
bMsg :={ || MsgAlert( 'Fallo el envío del archivo '+aFileADW[ nItem, 1 ]+'!!!',;
oMsg():cAtencion ) }
++nItem

enddo

; Hasta aqui todo funciona... los archivos son subidos al servidor FTP

; Ahora viene la parte que me tiene trancado...
; Necesito obtener la fecha y hora de un archivo que se copio al FTP en el Do While anterior y el programa continua asi:
STRUCT oFTPData
MEMBER nFileAttributes AS DWORD // DWORD dwFileAttributes
MEMBER nCreationTime AS STRING LEN 8 // FILETIME ftCreationTime
MEMBER nLastReadAccess AS STRING LEN 8 // FILETIME ftLastAccessTime
MEMBER nLastWriteAccess AS STRING LEN 8 // FILETIME ftLastWriteTime
MEMBER nSizeHight AS DWORD // DWORD nFileSizeHigh
MEMBER nSizeLow AS DWORD // DWORD nFileSizeLow
MEMBER nReserved0 AS DWORD // DWORD dwReserved0
MEMBER nReserved1 AS DWORD // DWORD dwReserved1
MEMBER cFileName AS STRING LEN 260 // TCHAR cFileName[MAX_PATH]
MEMBER cAltName AS STRING LEN 14 // TCHAR cAlternateFileName[14]
ENDSTRUCT

cBuffer :=oFTPData:cBuffer
FtpFindFirstFile( hConnect, cFTPFldr+'/*.dat', @cBuffer, 0, 0 )
oFTPData:cBuffer :=cBuffer

? oFTPData:cFileName,; // ==>> Muestra nombre del 1er archivo: OK
oFTPData:nCreationTime,; // ==>> NO MUESTRA NADA!!!
oFTPData:nFileAttributes // ==>> NO MUESTRA NADA!!!


de acuerdo a la información que está en la página
http://msdn.microsoft.com/en-us/library ... s.85).aspx
nCreationTime, nLastReadAccess, y nLastWriteAccess son subestructuras
typedef struct _FILETIME {
DWORD dwLowDateTime;
DWORD dwHighDateTime;
} FILETIME, *PFILETIME;
de la estructura principal (oFTPData en este caso).

o sea, que no es correcto declarar a nCreationTime, nLastReadAccess, y nLastWriteAccess como String[ 8 ], sino que pareciera que deberia ser algo asi como:
MEMBER nCreationTime AS PTR // FILETIME ftCreationTime
MEMBER nLastReadAccess AS PTR // FILETIME ftLastAccessTime
MEMBER nLastWriteAccess AS PTR // FILETIME ftLastWriteTime

La gran pregunta es como manejo esto con la clase TStruct de FW
porque si lo hago con STRING LEN 8 no muestra nada y al cerrar el díalogo xHarbour me da el mensaje de error "hb_xfree( 00FCB300 ) POINTER OVERFLOW!"...
si declaro la estructura con PTR me sale el mensaje "Member type conversion not implemented yet!", y el programa termina alli.

y todo lo que necesito es la fecha y hora de un archivo .DAT que se copia bien y logro verlo en el servidor con cualquier cliente FTP, y al bajarlo tengo los datos grabados originalmente, que es una de las cosas que necesito.

Ahora... por que necesito la fecha y hora de un archivo que se ha grabado en un servidor FTP???
porque necesito llevar un historial de las veces que un grupo de datos se ha subido al servidor por determinado usuario y validar que los archivos se hayan enviado al servidor dentro de un plazo establecido... Los archivos pueden ser enviados al servidor FTP desde cualquier PC disponible al usuario...
no puedo confiar en la fecha del PC porque la experiencia ha demostrado que dificilmente una PC tiene la fecha y hora correcta, ademas que, dentro de un grupo de PC's (que es lo que se espera manejar con la aplicación) no todos tendran exactamente la misma fecha y hora...
lo mas practico es saber la fecha del servidor, o en su defecto poder obtener fecha y hora conectandome (desde xH+FW) como cliente a un servidor NTP.

Aparentemente haber usado la clase tFTP de FW me hubiese solucionado el problema y tambien hubiese facilitado muchas cosas, pero no hubo manera de hacerla funcionar... nunca paso de mostrar el mensaje de que no podia cargar WinINet.dll... es un problema que veo que muchos compañeros han planteado en el foro sin haber obtenido alguna solución.

Bienvenidos todos los Tips, Ideas, Comentarios, y demas etceteras...
Agradecido de antemano.

Giancarlo J. Sabattino S.
Valencia, Venezuela.

Re: Como tomar fecha y hora de un archivo en un FTP??

Posted: Mon May 07, 2012 5:29 am
by anserkk
I am not sure whether I understood your requirement properly.

Please try the following sample to check the Date, Time and FileSize of a file in a FTP server

Code: Select all

//---------------------//
Function Test()
  Local aFiles:={},dDate,cTime,nSize,oInternet,oFtp
  Local cIp:="xxx.xxx.xxx.xxx", cFtpUserName:="YourFtpUserName", cFtpPassword:="YourFtpPassword"

  oInternet := tInternet():New()
  oFtp      := tFtp():New(cIp,oInternet,cFtpUserName,cFtpPassword)  
  IF !Empty( oFtp:hFtp)
     aFiles:=oFtp:Directory(cFolder+"YourFile.exe" )  // Be careful case sensitive
     IF Len(aFiles)>0         
          //---Date, Time & Size of the File on the FTP Server
          dDate:= aFiles[1,3]
          cTime:= aFiles[1,4]
          nSize:= aFiles[1,2]
     Endif

  ELSE
      MsgInfo("Unable to connect to FTP")
  ENDIF
Return NIL