FiveTech Support Forums

FiveWin / Harbour / xBase community
Board index FiveWin para Harbour/xHarbour DBF - modificar estructura desde aplicaci贸n
Posts: 593
Joined: Sat May 12, 2007 11:47 AM
DBF - modificar estructura desde aplicaci贸n
Posted: Wed Jul 03, 2013 02:19 PM
Buen d铆a,

Por una cuesti贸n de actualizaciones v铆a ftp, necesito lograr cambiar la estructura de una DBF.

Por ej. cambiar el nro. de decimales de un campo num茅rico o agregar un campo a la DBF, pero esto debe hacerse desde la misma aplicaci贸n que acaba de actualizarse.

Estuve buscando funciones xHarbour que me permitan hacerlo pero no doy en el clavo.

Gracias.

Rolando :-)
Posts: 94
Joined: Tue Mar 28, 2006 04:09 PM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Wed Jul 03, 2013 02:49 PM
Luis Fernando Rubio Rubio
Posts: 8523
Joined: Tue Dec 20, 2005 07:36 PM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Wed Jul 03, 2013 07:31 PM
Code (fw): Select all Collapse
            CLOSE EMAILENV

            USE EMAILENV NEW EXCLUSIVE ALIAS EMAILENV

            cAlias := ALIAS()

            lExiste := .F.

            FOR nConta := 1 TO (cAlias)->(fCount())

               IF (cAlias)->(FieldName(nConta)) = "HORAENVIO"  // Nuevo campo ejiste?

                  lExiste := .T.

                  EXIT 

               ENDIF

            NEXT

            //-> Nao existe o campo, HORAENVIO vai criar
            IF .NOT. lExiste

               MsgNoYes ( "USUARIO ADVERTENCIA:                                   " + CRLF +;
                                                                                    + CRLF +;
                          "LA CREACI脫N DEL PROGRAMA necesidad detectada           " + CRLF +;
                          "CAMPO DE LA FECHA DE ENV脥O DEL CORREO ELECTR脫NICO PARA " + CRLF +;
                          "CLIENTE NECESITA AUTORIZACION PARA CREAR               " + CRLF +;
                          "EL CAMPO EN LA BASE DE DATOS DE EMAILS.                " + CRLF +;
                                                                                    + CRLF +;
                          "Para crear el campo, ning煤n otro usuario               " + CRLF +;
                          "PUEDEN UTILIZAR EL PROGRAMA.                           " + CRLF +;
                          "Comprobar y confirmar la operaci贸n.                    " + CRLF +;
                                                                                    + CRLF +;
                          "Elija una de las siguientes opciones:                  " + CRLF +;
                                                                                    + CRLF +;
                          "[Si] -> Crear nuevo campo                              " + CRLF +;
                          "[No] -> no crear nuevo campo                           "         ;
                          "Crear nuevo campo en la base de datos ...") =. F.

               RETURN (. F.)

               DBCLOSEAREA()

               USE EMAILENV NEW EXCLUSIVE ALIAS EMAILENV

               COPY TO EMAILCOP.DBF  // HACER UNA COPIA ANTES

               DBCLOSEAREA()

               DbCreate( "EMAILENV.DBF", { { "CODC",       "N",  10, 00 }, ;
                                           { "CONTATO",    "C", 100, 00 }, ;
                                           { "DATAENVIO",  "D",  08, 00 }, ;
                                           { "HORAENVIO",  "C",  08, 00 } } ) // NUEVO CAMPO

               DBCLOSEAREA()

               USE EMAILENV NEW EXCLUSIVE ALIAS EMAILENV

               APPEND FROM EMAILCOP.DBF

               MsgMeter( { | oMeter, oText, oDlg, lEnd | ;
                         INDEXAR_EMAIL( oMeter, oText, oDlg, @lEnd ) },;
                         "Indexando Emails, Espere..." )

               DBCLOSEAREA()

            ENDIF


Salu2

Jo茫o Santos - S茫o Paulo - Brasil - Phone: +55(11)95150-7341
Posts: 593
Joined: Sat May 12, 2007 11:47 AM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Wed Jul 03, 2013 11:58 PM
Gracias por responder,

Luis, parecen interesantes tus funciones pero lamentablemente no se puede compilar porque faltan dos, la net_use() y la ExisteCampo(). Si las creo y retorno .t. se puede compilar pero ser铆a interesante contar con todas en tu prg.

Karinha, lo que haces es m谩s o menos lo que quiero hacer pero la idea era saber si existen funciones para modificar dentro del xHarbour o FWH.

De nuevo, Gracias.

Rolando :-)
Posts: 1710
Joined: Tue Oct 28, 2008 06:26 PM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Thu Jul 04, 2013 12:35 PM

Rolando

Con el FiveDbu de Antonio se puede modificar la estructura.

Saludos,

Adhemar

Saludos,



Adhemar C.
Posts: 44162
Joined: Thu Oct 06, 2005 05:47 PM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Thu Jul 04, 2013 02:34 PM
Rolando,

Aqui tienes el FiveDBU m谩s reciente con todo su c贸digo fuente por lo que puedes copiar como lo hace :-)
https://code.google.com/p/fivewin-contributions/downloads/detail?name=fivedbu_20130530.zip
regards, saludos

Antonio Linares
www.fivetechsoft.com
Posts: 94
Joined: Tue Mar 28, 2006 04:09 PM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Thu Jul 04, 2013 06:00 PM
Este es el codigo de ModStruct
Code (fw): Select all Collapse
***********************************************************************************
* 聽[ Funciones para hacer modificaciones en estructuras de DBF... ] 聽 聽 聽 聽 聽 聽 聽 *
* 聽1.- Function MsgCopia(cOrigen,cDestino) 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽*
* 聽2.- Function Respaldo(oMeter, oText, oDlg, lend, cOrigen, cDestino) 聽 聽 聽 聽 聽 聽*
* 聽3.- Function ModifyStruct(cRutaLogica,cBaseDatos,aCambios,aNewStruct,lMensaje) *
* 聽4.- function ReemplazaCampos(cDBF,cCAMPO,xVALUE,cCondicion,lMENSAJE) 聽 聽 聽 聽 聽 *
* 聽5.- Function CopiaEstructura(cOrigen,cDestino,aCambios) 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽*
* 聽6.- Function ExisteCampo(cCampo) 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 *
* 聽7.- Function CambiaNombre(cDBF,nField,cNewName) 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽*
* 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 *
* Ultimas modificaci贸nes: 21 de Julio 聽 de 2000 聽Luis Fernando Rubio Rubio 聽 聽 聽 聽*
* 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 24 de Febrero de 2003 聽Bingen Ugaldebere 聽 聽 聽 聽 聽 聽 聽 聽*
***********************************************************************************

#INCLUDE "FIVEWIN.CH"
#include "DBSTRUCT.CH" // Cabeceras de referencia de estructuras de Bases de DATOS
#include "FILEIO.CH" 聽 // Cabeceras de manejo de archivos a bajo nivel

/********************************************************************************************
聽Funci贸n para hacer la modificaci贸n de las estructuras de bases de datos
聽Function ModifyStruct(cRutaLogica,cBaseDatos,aCambios,aNewStruct,lMensaje)
聽 聽 聽 聽 聽 Donde cRutaLogica es el directorio a donde esta la base de datos
聽 聽 聽 聽 聽 Donde cBaseDatos es el nombre de la base de datos a modificar
聽 聽 聽 聽 聽 Donde aCambios es un Array de modificaciones con multiples array 1 por campo a modificar
聽 聽 聽 聽 聽 聽 聽 Donde cTipoMod es el tipo de modificaci贸n + - * (OPCIONAL si no se indica es +)
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 +(A帽adir o cambiar campo) -(Eliminar campo) o *(Cambiar nombre de campo)
聽 聽 聽 聽 聽 聽 聽 Donde cNomCampo es el nombre del campo nuevo
聽 聽 聽 聽 聽 聽 聽 Donde cTipo es el tipo del campo (Numerico,Caracter,Date,Memo)
聽 聽 聽 聽 聽 聽 聽 Donde nTama es el tama帽o del campo nuevo
聽 聽 聽 聽 聽 聽 聽 Donde nDeci es el numero de decimales que tendra el campo (si se requiriera)
聽 聽 聽 聽 聽 聽 聽 Donde xValue es el valor a reemplazar en el campo para todo el archivo
聽 聽 聽 聽 聽 聽 聽 Donde cCondicion es una expresion de tipo caracter que incluye una condici贸n
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 a evaluar antes de hacer el reemplazo anterior
聽 聽 聽 聽 聽 Donde aNewStruct es una estructura nueva completa a crear y es compatible
聽 聽 聽 聽 聽 聽 聽 聽 con aCambios puediendo usarse uno otro o los dos a la vez
聽 聽 聽 聽 聽 Donde lMensaje es si se quiere mensaje mientras se efectua el proceso
********************************************************************************************/

Function ModifyStruct( cRutaLogica, cBaseDatos, aCambios, aNewStruct, plMensaje )
聽 Local cArcResp := "", oData := nil
聽 Local aEstructura := {}, lCopiado := .F.
聽 LOCAL nHandle, cByte := Space(1)

聽 DEFAULT cRutaLogica := cFilePath( GetModuleFileName( GetInstance() ) ),;
聽 聽 聽 聽 聽 cBaseDatos 聽:= cFileNoExt(cBaseDatos),;
聽 聽 聽 聽 聽 aCambios 聽 聽:= ARRAY(0),;
聽 聽 聽 聽 聽 aNewStruct 聽:= ARRAY(0),;
聽 聽 聽 聽 聽 plMensaje 聽 := .T.


聽 if len( aCambios ) = 0 .and. len( aNewStruct ) = 0
聽 聽MsgStop("Los par谩metros de cambios en la estructura son incorrectos","Modificaci贸n de estructura", "Error de Estructura..."); return( .F. )
聽 elseif ! file( cRutaLogica + cBaseDatos + ".DBF") .and. len( aNewStruct ) = 0
聽 聽 MsgInfo("No se proceso el archivo: " + upper(cRutaLogica) + upper(cBaseDatos) + ", NO EXISTE y es necesario que al finalizar se contacte con su Asesor de Sistemas..." )
聽 聽 return(.F.)
聽 elseif file( cRutaLogica + cBaseDatos + ".DBF") .and. len( aNewStruct ) <> 0
聽 聽 MsgInfo("No se proceso el archivo: " + upper(cRutaLogica) + upper(cBaseDatos) + ", YA EXISTE y es necesario que al finalizar se contacte con su Asesor de Sistemas..." )
聽 聽 return(.F.)
聽 endif

聽 cRutaLogica := STRTRAN( cRutaLogica + "\", "\\", "\" ) 聽//cRutaLogica SIEMPRE TERMINAR脕 EN \

* 聽oApp:settext('Modificando: ' + UPPER(cRutaLogica+cBaseDatos)+ '...')

聽 //Buscar el DBF y su DBT/FPT para si existen, hacer copia de seguridad
聽 if File( cRutaLogica + cBaseDatos + ".DBF")

聽 聽 聽//Si no la hay crear carpeta de BACKUP
聽 聽 聽if ! lIsDir( cRutaLogica+"BACKUP" )
聽 聽 聽 聽 lMkDir( cRutaLogica+"BACKUP" )
聽 聽 聽endif

聽 聽 聽// Se crea un archivo de respaldo Consecutivo
聽 聽 聽cArcResp 聽:= ArcProv( '.DBF', cRutaLogica+"BACKUP\", 0, LEFT( cBaseDatos, 3 ) )
聽 聽 聽MsgCopia(cRutaLogica+cBaseDatos+'.DBF', cArcResp)
聽 聽 聽lCopiado:=.T.

聽 聽 聽//Comprobar existencia de archivos de campos memo NTX/CDX y hacer copia de seguridad
聽 聽 聽if File( cRutaLogica + cBaseDatos + '.DBT' )
聽 聽 聽 聽 MsgCopia( cRutaLogica + cBaseDatos + '.DBT', STRTRAN( cArcResp, ".DBF", ".DBT" ) )
聽 聽 聽endif

聽 聽 聽if File(cRutaLogica+cBaseDatos+'.FPT')
聽 聽 聽 聽 MsgCopia(cRutaLogica+cBaseDatos+'.FPT',STRTRAN(cArcResp,".DBF",".FPT"))
聽 聽 聽endif
聽 endif

聽 //Procesar aCambios que es la tabla que lleva la informacion de los cambios a efectuar
聽 CURSORWAIT()

聽 if len( aNewStruct ) > 0 聽//Nueva estructura completa
聽 聽Dbcreate( cRutaLogica+cBaseDatos, aNewStruct )
聽 endif

聽 if len( aCambios ) > 0 聽 //Modificaciones sobre la estructura actual
聽 聽for nITEM :=1 TO len( aCambios )
聽 聽 if ! aCambios[ nITEM, 1 ]$"+-*"
聽 聽 聽asize( aCambios[ nITEM ], len( aCambios[ nITEM ] ) + 1 )
聽 聽 聽AINS( aCambios[ nITEM], 1 )
聽 聽 聽aCambios[ nITEM, 1 ] := "+"
聽 聽 endif
聽 聽next

聽 聽if ! CopiaEstructura( cArcResp, cRutaLogica+cBaseDatos, aCambios )
聽 聽 Return .F.
聽 聽endif
聽 endif

聽 //Abre archivo modificado y carga en el los datos de la copia de seguridad
聽 if ! net_use(cBaseDatos,,,cRutaLogica) // 14/05/2007 01:44p. LFRR
聽 *DBUSEAREA(.T.,,cRutaLogica+cBaseDatos,,.T.)
聽 *if NETERR() 聽//Error de apertura
聽 聽*MsgStop("Problema al abrir el archivo: "+cRutaLogica+cBaseDatos,"Modificaci贸n de estructura")
聽 聽Return .F.
聽 endif
聽 DATABASE oData


聽 /*if lCopiado
聽 聽if plMensaje
聽 聽 *WAITON( "Realizando cambios en la estructura de " + cRutaLogica+cBaseDatos )
聽 聽 MsgWait( "Realizando cambios en la estructura de " + cRutaLogica+cBaseDatos,"", 0 )
聽 聽Else
聽 聽 CURSORWAIT()
聽 聽endif

聽 聽Append From (cArcResp)

聽 聽if plMensaje
聽 聽 *WAITOFF()
聽 聽endif
聽 endif*/

聽 if lCopiado
聽 聽 if plMensaje
聽 聽 聽 MsgWait( "Realizando cambios en la estructura de " + cRutaLogica+cBaseDatos,"", 0 )
聽 聽 endif
聽 聽 Append From (cArcResp)
聽 endif

聽 oData:CLOSE()

聽 //Cargar estructura nueva
聽 aEstructura = DBStruct()

聽 //Modificar nombres de campos de la estructura Bingen
聽 for nItem = 1 To len(aCambios)
聽 聽 if aCambios[nItem,1]="*"
聽 聽 聽 for nCampo:=1 TO len(aEstructura)
聽 聽 聽 聽 if aEstructura[nCampo,DBS_NAME] == UPPER(aCambios[nItem,DBS_NAME+1])
聽 聽 聽 聽 聽 CAMBIANOMBRE( cRutaLogica+cBaseDatos, nCampo, UPPER(aCambios[nItem,DBS_NAME+2]) )
聽 聽 聽 聽 聽 EXIT
聽 聽 聽 聽 endif
聽 聽 聽 next
聽 聽 endif
聽 next

聽 if len(aCambios)>0 聽 //Modificacion de contenidos de campos
聽 聽 for nITEM:=1 TO len(aCambios)
聽 聽 聽 if len(aCambios[nITEM])>5
聽 聽 聽 聽 ReemplazaCampos( cRutaLogica + cBaseDatos, upper( aCambios[ nItem, DBS_NAME + 1 ] ) , aCambios[ nItem, 6 ], if( len( aCambios[nITEM])=7,aCambios[nItem,7],".T."))
聽 聽 聽 endif
聽 聽 next
聽 endif

聽 CURSORARROW()

Return .T.


// --- 聽08.07.2000 LFRR 聽 Ahora compara si existe el campo y su estructura si es igual asi lo deja y si no lo modifica 聽LRRR RMN
Function CopiaEstructura( cOrigen, cDestino, aCambios )
聽 Local aEstructura:={}, nITEM:=0, oORIGEN

聽 //Abre archivo modificado y carga en el los datos de la copia de seguridad
聽 if ! net_use( cFileNoPath(cOrigen),,,cFilePath(cOrigen) )
// 聽DBUSEAREA(.T.,,cORIGEN,,.T.)
// 聽if NETERR() 聽//Error de apertura
聽 聽Return .F.
聽 endif

聽 DATABASE oORIGEN

聽 *if NetErr()
聽 * 聽MsgStop("Problema al abrir el archivo de origen: "+cOrigen,"Modificaci贸n de estructura")
聽 * 聽Return .F.
聽 *endif

聽 //Cargar estructura antigua
聽 aEstructura = DBStruct()

聽 //A帽adir campos Adicionales
聽 for nItem = 1 To len(aCambios)
聽 聽 do case
聽 聽 聽 /*agregar campos adicionales o modificarlos, ya se en su nombre, */
聽 聽 聽 case aCambios[nItem,1]="+" //A帽adir campos Adicionales o modificarlos
聽 聽 聽 聽 if ! ExisteCampo( aCambios[nItem,DBS_NAME+1] ) 聽//Si no existe agregar a la estructura
聽 聽 聽 聽 聽 aAdd( aEstructura, { aCambios[nItem,DBS_NAME+1], aCambios[nItem,DBS_TYPE+1], aCambios[nItem,DBS_LEN+1], aCambios[nItem,DBS_DEC+1] } )
聽 聽 聽 聽 else 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 //Si existe modificarlo
聽 聽 聽 聽 聽 if aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_TYPE ] != aCambios[ nItem, DBS_TYPE + 1 ] .or.;
聽 聽 聽 聽 聽 聽 聽aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_LEN ] 聽!= aCambios[ nItem, DBS_LEN 聽+ 1 ] .or.;
聽 聽 聽 聽 聽 聽 聽aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_DEC ] 聽!= aCambios[ nItem, DBS_DEC 聽+ 1 ]

聽 聽 聽 聽 聽 聽 聽aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_TYPE ] := aCambios[ nItem, DBS_TYPE + 1 ]
聽 聽 聽 聽 聽 聽 聽aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_LEN ] 聽:= aCambios[ nItem, DBS_LEN 聽+ 1 ]
聽 聽 聽 聽 聽 聽 聽aEstructura[ fieldpos( aCambios[ nItem, DBS_NAME + 1 ] ), DBS_DEC ] 聽:= aCambios[ nItem, DBS_DEC 聽+ 1 ]
聽 聽 聽 聽 聽 endif
聽 聽 聽 聽 endif

聽 聽 聽 case aCambios[nItem,1]="-" //Eliminar campos de la estructura Bingen
聽 聽 聽 聽 for nCampo :=1 to len( aEstructura )
聽 聽 聽 聽 聽 if aEstructura[nCampo,DBS_NAME] == UPPER(aCambios[nItem,DBS_NAME+1])
聽 聽 聽 聽 聽 聽 adel(aEstructura,Ncampo)
聽 聽 聽 聽 聽 聽 asize(aEstructura,len(aEstructura)-1)
聽 聽 聽 聽 聽 聽 EXIT
聽 聽 聽 聽 聽 endif
聽 聽 聽 聽 next
聽 聽 endcase
聽 next

聽 oORIGEN:CLOSE()

聽 //Crear archivo de destino con nueva estructura
聽 Dbcreate(cDestino,aEstructura)
Return .T.

// Reemplaza los campos del area especificada
Function ReemplazaCampos( cDBF, cCAMPO, xVALUE, cCondicion, plMensaje )
聽 local oData
聽 default cCondicion := ".T.", plMensaje := .T.

聽 if ! net_use( cDbf )
聽 聽 *DBUSEAREA(.T.,,cDBF,,.T.)
聽 *if NETERR() 聽//Error de apertura
聽 * MsgStop("Imposible abrir archivo: "+cRutaLogica+cBaseDatos+" en modo exclusivo.","Error de Reemplazo de campos")
聽 聽Return .F.
聽 endif
聽 DATABASE oData
聽 oData:={|| NIL }

聽 for nITEM = 1 To oData:fCount()
聽 聽 if Upper( oData:FieldName( nITEM ) )== Upper( cCAMPO )
聽 聽 聽 聽if VALTYPE( oData:FIELDGET( nITEM ) ) == VALTYPE(xVALUE)
聽 聽 聽 聽 聽if plMensaje
聽 聽 聽 聽 聽 聽 *WAITON("Reemplazando campo "+cCampo+" en "+cDBF)
聽 聽 聽 聽 聽 聽 MsgWait("Reemplazando campo "+cCampo+" en "+cDBF,"",0)
聽 聽 聽 聽 聽endif

聽 聽 聽 聽 聽DO WHILE ! oData:EOF()
聽 聽 聽 聽 聽 if &cCONDICION
聽 聽 聽 聽 聽 聽oData:FIELDPUT(nITEM,xVALUE)
聽 聽 聽 聽 聽 聽oData:SAVE()
聽 聽 聽 聽 聽 endif
聽 聽 聽 聽 聽 oData:SKIP()
聽 聽 聽 聽 聽ENDDO
聽 聽 聽 聽 聽if plMensaje
聽 聽 聽 聽 聽 聽 *WAITOFF()
聽 聽 聽 聽 聽endif
聽 聽 聽 聽ELSE
聽 聽 聽 聽 聽MSGSTOP("Imposible modificar campo "+oData:FieldName( nITEM )+;
聽 聽 聽 聽 聽 聽 聽 聽 聽"con "+cVALTOCHAR(xValue)+" Tipo de dato incorrecto ","Error de Reemplazo de campos")
聽 聽 聽 聽endif
聽 聽 endif
聽 next

聽 oData:CLOSE()

return(nil)

//Cambia el nombre del campo n潞 nField por el nuevo nombre cNewName
STATIC Function CAMBIANOMBRE( cDBF, nField, cNewName )
LOCAL nHandle,nPos 聽 聽:= ( nField * 32 聽)
聽CURSORWAIT()
聽if ( nHandle := fopen( cDBF+".DBF", FO_READWRITE ) ) <> - 1
聽 聽 fseek( nHandle, nPos, FS_SET )
聽 聽 fwrite( nHandle, padr( cNewName, 10 ) + chr( 0 ), 11 )
聽 聽 fclose( nHandle )
聽 聽 Return .T.
聽endif
聽CURSORARROW()
Return .F.

//****************************************************************************************************************************//
// Esta funcion crea un nombre de archivo consecutivo..
// modo de uso:
// ArcProv('.DBF',pcRutaLogica,0,LEFT(pcBaseDatos,3))
//****************************************************************************************************************************//

STATIC FUNCTION ArcProv(pcExtension,pcRuta,pIncrementar,pcPrefijo) 聽 //Devuelve el nombre de un archivo provisional
聽 聽 LOCAL i := 0,;
聽 聽 聽 聽 聽 m := 0,;
聽 聽 聽 聽 聽 cRuta := '',;
聽 聽 聽 聽 聽 cNombre := '',;
聽 聽 聽 聽 聽 nInc := 0

聽 聽 if pcount()>=3 聽//Se dio el parametro pIncrementar
聽 聽 聽 聽nInc := pIncrementar
聽 聽 endif

聽 聽 if pcPrefijo = Nil
聽 聽 聽 聽 pcPrefijo :='TMP'
聽 聽 endif

聽 聽 if pcount()=1
聽 聽 聽 聽if !empty(gete("TMP"))
聽 聽 聽 聽 聽 cRuta=gete("TMP")
聽 聽 聽 聽ELSEif !empty(gete("TEMP"))
聽 聽 聽 聽 聽 cRuta=gete("TEMP")
聽 聽 聽 聽endif

聽 聽 聽 聽if !empty(cRuta)
聽 聽 聽 聽 聽 if subst(cRuta,len(cRuta),1)!="\"
聽 聽 聽 聽 聽 聽 聽cRuta+='\'
聽 聽 聽 聽 聽 endif
聽 聽 聽 聽endif
聽 聽 ELSE
聽 聽 聽 聽cRuta := pcRuta
聽 聽 endif

聽 聽 for i := 1 to 99999
聽 聽 聽 聽 cNombre := cRuta+;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽pcPrefijo+;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽strzero(i+nInc,5)+;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽pcExtension
聽 聽 聽 聽 if !file(cNombre)
聽 聽 聽 聽 聽 聽m := fcreate(cNombre,0)
聽 聽 聽 聽 聽 聽fclose(m)
聽 聽 聽 聽 聽 聽RETURN cNombre
聽 聽 聽 聽 endif
聽 聽 next
RETURN('')



//----------------------------------------------------------------------------//
*******************************************************************
* 聽MENSAJE CON ESPERA PERMANENTE HASTA QUE SE EJECUTE 聽WAITOFF() 聽*
*******************************************************************

FUNCTION WAITON( cTEXT, cTitle)

聽 聽 聽LOCAL nWidth
聽 聽 聽LOCAL 聽 bAction 聽:= { || .t. }
聽 聽 聽private ODLGWAIT := nil

聽 聽 聽DEFAULT cTitle := "Espere un momento..."

聽 聽/*
聽 聽 聽 if VALTYPE( oDLGWAIT ) <> 'U'
聽 聽 聽 聽 聽RETURN NIL
聽 聽 聽 endif
聽 聽*/

聽 聽 聽if cTEXT == NIL
聽 聽 聽 聽 聽 DEFINE DIALOG oDLGWAIT ;
聽 聽 聽 聽 聽 聽 聽 聽FROM 0,0 TO 3, len( cTitle ) + 4 ;
聽 聽 聽 聽 聽 聽 聽 聽STYLE nOr( DS_MODALFRAME, WS_POPUP )
聽 聽 聽ELSE
聽 聽 聽 聽 聽 DEFINE DIALOG oDLGWAIT ;
聽 聽 聽 聽 聽 聽 聽 聽FROM 0,0 TO 4, Max( len( cTEXT ), len( cTitle ) ) + 4 ;
聽 聽 聽 聽 聽 聽 聽 聽TITLE cTitle ;
聽 聽 聽 聽 聽 聽 聽 聽STYLE DS_MODALFRAME
聽 聽 聽endif

** 聽 oDLGWAIT:bStart := { || .t. }
聽 聽 聽oDLGWAIT:cMsg 聽 := cTEXT

聽 聽 聽nWidth := oDLGWAIT:nRight - oDLGWAIT:nLeft

聽 聽 聽oDlgWait:lHelpIcon:=.F.

聽 聽 聽ACTIVATE DIALOG oDLGWAIT CENTER ;
聽 聽 聽 聽 聽 ON PAINT oDLGWAIT:Say( 1, 0, xPadC( oDLGWAIT:cMsg, nWidth ) ) NOWAIT

聽 聽 聽SYSREFRESH()
聽 聽 聽CURSORWAIT()

RETURN NIL

FUNCTION WAITOFF() 聽 // PARA CERRAR EL WAITON()

聽 聽if valtype(oDLGWAIT) <> 'U' 聽/* waiton has to be called first! */
聽 聽 聽 oDLGWAIT:end()
聽 聽 聽 oDLGWAIT := NIL
聽 聽endif
聽 聽oWND:SETFOCUS()
聽 聽SYSREFRESH()
聽 聽CURSORARROW()
RETURN NIL
//----------------------------------------------------------------------------//

// COPIA DE ARCHIVOS
Function MsgCopia( cOrigen, cDestino )
// 聽 MsgProgress( { | oMeter, oText, oDlg, lEnd | Respaldo( oMeter, oText, oDlg, @lEnd, cOrigen, cDestino ) }, "Copiando a: " + cDestino, "Respaldando: " + cOrigen )
聽 聽MsgMeter( { | oMeter, oText, oDlg, lEnd | Respaldo( oMeter, oText, oDlg, @lEnd, cOrigen, cDestino ) }, "Copiando a: " + cDestino, "Respaldando: " + cOrigen )

Return(.t.)

// FUNCION QUE HACE LA ACCION DE COPIA DE ARCHIVOS
Function Respaldo(oMeter, oText, oDlg, lEnd, cOrigen, cDestino)
聽 Local forigen, fDestino
聽 Local nBuffer 聽 聽:= 8192 聽 聽 聽 聽// Tama帽o del Buffer en Bytes
聽 Local cBuffer := SPACE(nBuffer)
聽 Local Tamano := fsize(cOrigen), nLeido := 0, nEscrito := 0, nCopiados := 0

聽 ? cOrigen, cDestino

聽 oMeter:nTotal = Tamano

聽 forigen = fOpen(cOrigen)
聽 if fError() != 0
聽 聽 MsgStop('No se Pudo Abrir el archivo '+cOrigen,'Error de Apertura')
聽 聽 lEnd := .t.
聽 聽 Return(Nil)
聽 endif

聽 fDestino = fCreate(cDestino)
聽 if fError() != 0
聽 聽 MsgStop('No se Pudo crear el archivo '+cDestino,'Error de Creaci贸n')
聽 聽 lEnd := .t.
聽 聽 Return(Nil)
聽 endif

聽 DO While nCopiados < Tamano
聽 聽 CURSORWAIT()
聽 聽 nLeido = fRead(forigen, @cBuffer, nBuffer)

聽 聽 if fError() != 0
聽 聽 聽 MsgStop('No se Pudo leer el archivo '+cOrigen,'Error de Lectura')
聽 聽 聽 lEnd := .t.
聽 聽 聽 fclose(forigen)
聽 聽 聽 fclose(fDestino)
聽 聽 聽 Return(Nil)
聽 聽 endif

聽 聽 nEscrito = fwrite(fDestino, cBuffer, nLeido)

聽 聽 if fError() != 0
聽 聽 聽 MsgStop('No se Pudo escribir en el archivo '+cDestino,'Error de Escritura')
聽 聽 聽 lEnd := .t.
聽 聽 聽 fclose(forigen)
聽 聽 聽 fclose(fDestino)
聽 聽 聽 Return(Nil)
聽 聽 endif

聽 聽 nCopiados+=nLeido // Incrementa la cantidad de Bytes copiados hasta el momento...
聽 聽 oMeter:Set( nCopiados )
聽 聽 oMETER:Refresh()

聽 EndDo
聽 lEnd = .t.
聽 fclose(forigen)
聽 fclose(fDestino)

聽 CURSORARROW()
Return(Nil)

Este es el codigo de ExisteCampo
Code (fw): Select all Collapse
//Determinar si existe el campo en el area indicada, Rafael Morf隆n 聽1998
function ExisteCampo( pCampo)
聽 local i:=0, mArea:=0, lExiste := .F.

聽 for i=1 to fcount()
聽 聽 if upper(fieldname(i)) == upper(pCampo)
聽 聽 聽 lExiste := .T.
聽 聽 endif
聽 next

return(lExiste)


y este es el codigo del Net_Use
Code (fw): Select all Collapse
// *********************************************************************************************
// Fecha de Inicio del Proyecto: 17/01/2006 01:28p.
// Programador: Luis Fernando Rubio Rubio
// Empresa:
// Lenguaje de Desarrollo:
// Comentarios:
// *********************************************************************************************

#include "fivewin.ch"
#INCLUDE "fileio.ch"

function net_use( pcBaseDatos, plExclusivo, pcAlias, pcRuta, plOkDbf, plMensaje )
聽 Local lContinuar := .F.
聽 local oError
聽 local cTabla := iif( valtype( pcRuta )$"U", ".\", pcRuta ) + pcBaseDatos
聽 local nInicio := seconds()
聽 local cAlias := iif( empty(pcAlias), cFileNoExt(pcBaseDatos), pcAlias )

聽 default plExclusivo := .F., pcRuta := "", plOkDbf := .F., plMensaje := .T.//, pcAlias := cAlias //, pcBaseDatos := cFileNoExt(pcBaseDatos)

聽 //? pcBaseDatos, pcAlias, pcRuta

聽 if plOkDbf
聽 聽 if ! lOkDbf( pcRuta + pcBaseDatos )
聽 聽 聽 return(lContinuar)
聽 聽 endif
聽 endif

// 聽? pcRuta, pcBaseDatos, pcAlias, plExclusivo

// 聽DBUSEAREA( .T., , pcRuta + pcBaseDatos, pcAlias, plExclusivo, .T.)

聽 if plExclusivo
聽 聽 if empty(pcAlias)
聽 聽 聽 use (pcRuta + pcBaseDatos) exclusive new
聽 聽 else
聽 聽 聽 use (pcRuta + pcBaseDatos) alias (pcAlias) exclusive new
聽 聽 endif

聽 else
聽 聽 if empty(pcAlias)
聽 聽 聽 //use (pcRuta + pcBaseDatos) shared new
聽 聽 聽 dbUseArea( .T., /*"DBFCDX"*/, pcRuta + pcBaseDatos, pcAlias, .T., .F. )
聽 聽 else
聽 聽 聽 //use (pcRuta + pcBaseDatos) alias (pcAlias) shared new
聽 聽 聽 dbUseArea( .T., /*"DBFCDX"*/, pcRuta + pcBaseDatos, pcAlias, .T., .F. )
聽 聽 endif

// 聽 聽 聽use (cTabla) alias (cAlias) shared new
// 聽 聽 聽DBUSEAREA(.T.,,cTabla,,.T.)

聽 endif


聽 if ! netErr()
聽 聽 lContinuar := .T.
聽 聽 (cAlias)->(ordSetFocus(1))
聽 else
聽 聽 if plMensaje
聽 聽 聽 MsgStop("La base de datos: " + Upper(pcBaseDatos) + ".DBF, no puede ser procesada" + CRLF +;
聽 聽 聽 聽 聽 聽 聽 "llame a su asesor de Informatica..." , oApp:cEmpresa)
聽 聽 endif
聽 endif

return(lContinuar)

FUNCTION DbProtect(cDbf,nAction)
聽 聽LOCAL nHandle:=0
聽 聽LOCAL cBuffer:=Space(32)
聽 聽nHandle:=FOpen(cDbf,FO_READWRITE+FO_SHARED)
聽 聽DEFAULT nAction:=1

聽 聽IF nHandle!=-1
聽 聽 聽 IF FRead(nHandle,@cBuffer,32)==32
聽 聽 聽 聽 聽IF nAction==0 聽 聽 聽 // Proteger
聽 聽 聽 聽 聽 聽 IF SubStr(cBuffer,1,1)<>Chr(26)
聽 聽 聽 聽 聽 聽 聽 聽cBuffer:=Chr(26)+SubStr(cBuffer,1,31)
聽 聽 聽 聽 聽 聽 ENDIF
聽 聽 聽 聽 聽ELSE 聽 聽 聽 聽 聽 聽 聽 聽// Desproteger
聽 聽 聽 聽 聽 聽 IF SubStr(cBuffer,1,1)==Chr(26)
聽 聽 聽 聽 聽 聽 聽 聽cBuffer:=SubStr(cBuffer,2,31)+ Chr(0)
聽 聽 聽 聽 聽 聽 ENDIF
聽 聽 聽 聽 聽ENDIF
聽 聽 聽 聽 聽FSeek(nHandle,0)
聽 聽 聽 聽 聽FWrite(nHandle,cBuffer,32)
聽 聽 聽 ENDIF
聽 聽 聽 FClose(nHandle)
聽 聽ENDIF
RETURN (FError())

FUNCTION lProtect(cDbf)
聽 聽 LOCAL nHandle :=0
聽 聽 LOCAL cBuffer :=Space(32)
聽 聽 LOCAL lRet 聽 :=.F.
聽 聽 IF (nHandle:=FOpen(cDbf,FO_READWRITE+FO_SHARED))!=-1
聽 聽 聽 聽IF FRead(nHandle,@cBuffer,32)==32
聽 聽 聽 聽 聽 lRet:=IF(SubStr(cBuffer,1,1)==Chr(26),.T.,.F.)
聽 聽 聽 聽ENDIF
聽 聽 聽 聽FClose(nHandle)
聽 聽 ELSE
聽 聽 聽 聽 MsgInfo("No puede abrirse la tabla "+cDbf,"Verifique!")
聽 聽 ENDIF
RETURN (lRet)

FUNCTION lOkDbf( cNameExt, cPath )
聽 LOCAL lReturn := .T.
聽 LOCAL nHnd, cBytes, nNumRecs, nHdrSize, nRecSize, nFileSize, nRecs
聽 LOCAL cError, cErrorLog
聽 default cPath := ".\"


聽 // Abrimos en exclusiva. Si no es posible, alguien lo esta usando (NO da帽ado)
聽 IF (nHnd := FOpen(cPath + '\' + cNameExt, FO_READWRITE + FO_EXCLUSIVE)) > 0
聽 聽 FSeek(nHnd,4,FS_SET)
聽 聽 // Numero registros segun tabla
聽 聽 cBytes := '0000'
聽 聽 FRead(nHnd,@cBytes,4)
聽 聽 nNumRecs := Bin2L(cBytes)
聽 聽 // Tama帽o Header
聽 聽 cBytes := '00'
聽 聽 FRead(nHnd,@cBytes,2)
聽 聽 nHdrSize := Bin2I(cBytes)
聽 聽 // Tama帽o Registro
聽 聽 cBytes := '00'
聽 聽 FRead(nHnd,@cBytes,2)
聽 聽 nRecSize := Bin2I(cBytes)
聽 聽 // Tama帽o Tabla
聽 聽 nFileSize := FSeek(nHnd,0,FS_END)
聽 聽 // Numero de registros real
聽 聽 nRecs := (nFileSize - nHdrSize) / nRecSize
聽 聽 // Si el archivo se manipulo con dBase, Fox ... tiene 1 byte mas
聽 聽 IF nRecs != Round(nRecs,0)
聽 聽 聽 聽 nRecs := (nFileSize - nHdrSize - 1) / nRecSize
聽 聽 ENDIF
聽 聽 // Si los registros segun la tabla y los calculados no coinciden
聽 聽 IF nRecs != nNumRecs
聽 聽 聽 聽 cError 聽 聽:= "N煤mero de registros incorrecto en Base de Datos " + cNameExt
聽 聽 聽 聽 cErrorLog := cError + " en" + CRLF + Trim(cPath) + ' :' + CRLF + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 " 聽 Registros iniciales 聽" + strzero(nNumRecs,7) + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 " 聽 Registros detectados " + strzero(nRecs,7) 聽 聽+ CRLF + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 "Aseg煤rese de guardar la 煤ltima copia de 聽seguridad y" + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 "realice una copia suplementaria ANTES DE corregir el" + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 "problema."
聽 聽 聽 聽 IF MsgNoYes( cErrorLog + CRLF + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 聽 "驴 Desea corregir el problema ?", "Error de apertura")
聽 聽 聽 聽 聽 FSeek(nHnd,4,FS_SET)
聽 聽 聽 聽 聽 FWrite(nHnd,L2Bin(Round(nRecs,0)),4)
聽 聽 聽 聽 聽 MsgInfo('El problema ha sido corregido.' + CRLF + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 'Antes de continuar el 聽uso normal del programa' + CRLF +;
聽 聽 聽 聽 聽 聽 聽 聽 聽 'debe realizarse una "Indexaci贸n de ficheros".','Aviso Importante')
聽 聽 聽 聽 ENDIF
聽 聽 ENDIF
聽 聽 FClose(nHnd)
聽 ENDIF

RETURN lReturn
Luis Fernando Rubio Rubio
Posts: 593
Joined: Sat May 12, 2007 11:47 AM
Re: DBF - modificar estructura desde aplicaci贸n
Posted: Thu Jul 04, 2013 10:38 PM

Muchas Gracias a todos,

Ya tengo bastante madera para tallar.

Saludos.

Rolando :D

Continue the discussion