//**************************************************************************** // $Module type: Package // $Module name: SyncFuncs.pkg // $Author : Nils G. Svedmyr // Created : 2001-08-21 @ 14:06 // // COPYRIGHT (c) 2003-2006 RDC Tools International // // This program is free software; you can redistribute it and/or // modify it under the terms of the GNU General Public License // as published by the Free Software Foundation; version 2 // of the License. // This program is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // You should have received a copy of the GNU General Public License // along with this program; (See the GPL.txt file in the Help directory) if not, write to the Free Software // Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. // Description : Functions for the Synchronize project. // // $Rev History: // 2001-08-21 Module header created // //**************************************************************************** Use DFTimer.pkg Use Windows.pkg Use Dll.pkg Use vWin32fh.pkg Use ShellExecute.pkg Use File_Dlg.pkg Use Seq_Chnl.pkg Use ODBC_DRV.pkg Use DB2_DRV.pkg Use DFBTRDRV.pkg Use MSSQLDRV.pkg Use vWin32fh.pkg Use FileVersion.pkg // Function for checking file version of .exe's and dll's. //Use cRDCCrypt.pkg // Contains oCrypt object. Use Working.pkg //Use Mertech.inc Use cSQLBrowseConnect.pkg Use DfAbout.pkg // Network_User_Name //Use SoftwareKey.pkg // Software Key Plus external functions. Use GetSystemInfo.pkg // To get the number of CPU's in the machine Open SncTable Global_Variable Integer giFromDDF Move 100 To giFromDDF // File handle for Source table's File.ddf file. Global_Variable Integer giToDDF Move 110 To giToDDF // File handle for Source table's File.ddf file. Send Ignore_Error Of Error_Info_Object 4103 // "Bad driver name" Send Ignore_Error Of Error_Info_Object 4255 // "Can't load DLL" Send Ignore_Error Of Error_Info_Object 4277 // "Invalid intermediate file keyword" Send Ignore_Error Of Error_Info_Object 4285 // "Attempt to access unsupported attribute" // Propery phoDD is used by function OpenDDFFile. // The function is used by the Builder and Engine. Register_Function phoDD Handle hoDD Returns Integer Register_Function RdsMain_Panel_Id Returns Integer Register_Object oCrypt Define C_CKDrivers For "DB2_DRVMSSQLDRVODBC_DRVDFBTRDRVORA_DRVSQL_DRVMDS_DB2" Define FLEX_DRV_ID For "DATAFLEX" //#REPLACE ODBC_DRV_ID "ODBC_DRV" // DAW driver //#REPLACE MSSQLDRV_ID "MSSQLDRV" // DAW driver //#REPLACE DB2_DRV_ID "DB2_DRV" // DAW driver //#REPLACE DFBTRDRV_ID "DFBTRDRV" // DAW driver Define ORA_DRV_ID For "ORA_DRV" // Mertech driver Define SQL_DRV_ID For "SQL_DRV" // Mertech driver Define MDS_DB2_ID For "MDS_DB2" // Mertech driver Define C_ODBC_DRV_VER For 2.2 Define C_MSSQLDRV_VER For 2.2 Define C_DB2_DRV_VER For 2.2 Define C_DFBTRDRV_VER For 1.3 Define C_ORA_DRV_VER For 3.2 Define C_SQL_DRV_VER For 7.3 Define C_MDS_DB2_VER For 7.0 Object oDrvArray Is A Array Property Boolean pbODBC_DRV False Property Boolean pbMSSQLDRV False Property Boolean pbDB2_DRV False Property Boolean pbDFBTRDRV False Property Boolean pbORA_DRV False Property Boolean pbSQL_DRV False Property Boolean pbMDS_DB2 False End_Object // oDrvArray Object oTempFileListArray Is A Array End_Object // oTempFileListArray //#COMMAND RDC_BEGIN_TRANSACTION // #$ !A [0 0 0] $0C7 |CI0 //#ENDCOMMAND //#COMMAND RDC_END_TRANSACTION // !A [] $0C8 //#ENDCOMMAND // Adds a file temporary to the Filelist.cfg // The next empty slot is used and temporary saved // to the oTempFileListArray. Function AddFileToFileList Global String sPath String sDriver Returns Integer Handle hoArray hStruct Integer iFile String sDisplayName sLogicalName sFileName Get_Attribute DF_FILE_NEXT_EMPTY Of iFile To iFile Get StripPath sPath To sFileName Move sFileName To sDisplayName If (Length(sDisplayName) > 32) ; Move (Pad(sDisplayName, 32)) To sDisplayName If (Length(sDisplayName) > 8) ; Move (Pad(sDisplayName, 8)) To sLogicalName Else ; Move sDisplayName To sLogicalName Set_Attribute DF_FILE_ROOT_NAME Of iFile To sFileName Set_Attribute DF_FILE_LOGICAL_NAME Of iFile To sLogicalName Set_Attribute DF_FILE_DISPLAY_NAME Of iFile To sDisplayName Move (oTempFileListArray(Self)) To hoArray Set Array_Value Of hoArray Item (Item_Count(hoArray) - 1) To iFile Move 0 To hStruct Structure_Start hStruct sDriver Set_Attribute DF_FILE_PHYSICAL_NAME Of hStruct To sPath Structure_End iFile DF_STRUCTEND_OPT_NONE Function_Return iFile End_Function // Add_newfile // Returns the highest used file number in filelist.cfg + 1. // A.k.a. the first available slot after the last used one: Function IsHighFileListNumber Global Returns Integer Handle hFile Integer iRetval Repeat Get_Attribute DF_FILE_NEXT_USED Of hFile To hFile If (hFile > 0) Move hFile To iRetval Until (hFile = 0) Function_Return (iRetval + 1) End_Function // IsHighFileListNumber // Returns the major revision of the currently running VDF version: Function VdfMajorRev Global Returns String String sVersion Move (SysConf(SysConf_DataFlex_Rev)) To sVersion Move (If(Pos(".", sVersion), Left(sVersion, (Pos(".", sVersion) -1)), sVersion)) To sVersion Function_Return sVersion End_Function // VdfMajorRev // Takes a driver name as a parameter. // Returns: * False if the .DLL version is GE the "C_DriverVersion" constant I.e. version is ok. // * The current version if the .DLL version is to old in the format "2.1" I.e. with one decimal. // * -1 if the .DLL couldn't be found in the ..\Bin folder or RDC Programs folder. // * -2 Unkown driver Function IsCurrentDriverVersion Global String sDriver Returns String String sPath sVersion sDLL Integer iRetval iSeparator Number nMinVersion nVersion Move (Trim(sDriver)) To sDriver If (sDriver = FLEX_DRV_ID) Function_Return "0" // This will always be the correct version... Get psProgramPath Of (phoWorkspace(ghoApplication)) To sPath Move (sPath - "\") To sPath Move (sDriver - ".DLL") To sDLL Get vFilePathExists (sPath - sDLL) To iRetval If Not iRetval Begin Function_Return "-1" // .DLL file not found. End // If Not iRetval Begin Get_Attribute DF_DECIMAL_SEPARATOR To iSeparator Set_Attribute DF_DECIMAL_SEPARATOR To (Ascii(".")) Get FileVersionInfo (sPath - sDLL) To sVersion Case Begin Case (sDriver = ODBC_DRV_ID) Move (Remove(sVersion, (Length(C_ODBC_DRV_VER) + 1), 20)) To sVersion Move (Eval(C_ODBC_DRV_VER)) To nMinVersion Case Break Case (sDriver = MSSQLDRV_ID) Move (Remove(sVersion, (Length(C_MSSQLDRV_VER) + 1), 20)) To sVersion Move (Eval(C_MSSQLDRV_VER)) To nMinVersion Case Break Case (sDriver = DB2_DRV_ID) Move (Remove(sVersion, (Length(C_DB2_DRV_VER) + 1), 20)) To sVersion Move (Eval(C_DB2_DRV_VER)) To nMinVersion Case Break Case (sDriver = DFBTRDRV_ID) Move (Remove(sVersion, (Length(C_DFBTRDRV_VER) + 1), 20)) To sVersion Move (Eval(C_DFBTRDRV_VER)) To nMinVersion Case Break Case (sDriver = ORA_DRV_ID) Move (Remove(sVersion, (Length(C_ORA_DRV_VER) + 1), 20)) To sVersion Move (Eval(C_ORA_DRV_VER)) To nMinVersion Case Break Case (sDriver = SQL_DRV_ID) Move (Remove(sVersion, (Length(C_SQL_DRV_VER) + 1), 20)) To sVersion Move (Eval(C_SQL_DRV_VER)) To nMinVersion Case Break Case (sDriver = MDS_DB2_ID) Move (Remove(sVersion, (Length(C_MDS_DB2_VER) + 1), 20)) To sVersion Move (Eval(C_MDS_DB2_VER)) To nMinVersion Case Break Case Else Function_Return "-2" // "Unkown driver" Case End Move (Number(Trim(sVersion))) To nVersion Set_Attribute DF_DECIMAL_SEPARATOR To iSeparator Function_Return (If(nVersion < nMinVersion, String(sVersion), "0")) End_Function // IsCurrentDriverVersion // Loads the specified CK database driver, if not loaded. // Pass True for the bBatch flag to return the error message. (Used by the Synchronize program) // Or pass False to display a stop box with the error message. // Takes a database driver id as parameter and a boolean flag // true to return error text or false to display a stop_box with error text. // Returns: 0 if driver loaded ok or was already loaded. // 1 if driver was found but could not be loaded if not batch. Else error text. // -1 if driver could not be found if not bBatch. Else error text. // -2 if unkown driver if not bBatch. Else error text. // -3 if driver version is to old if not bBatch. Else error text. // Also checks that the driver version is ok. Function SubLoadDriver Global String sDriver Boolean bBatch Returns String String sName sRetval sText sText2 Integer iNumDrivers iCount iFailed iRetval iSeparator Get IsCurrentDriverVersion sDriver To sRetval If (sRetval <> "0") Begin If (sRetval = "-1") Begin Move ("WARNING! Could not find the connectivity kit database driver" * sDriver + ; ". It should reside in the RDC\Programs folder. You need to move/install the driver" * ; sDriver - ".DLL file to the RDC\Programs folder.") To sText If bBatch Function_Return sText Else Begin Send Stop_Box sText Function_Return "-1" End // Else Begin End // If (sRetval = "-1") Begin If (sRetval = "-2") Begin Move ("WARNING! Unkown connectivity kit database driver." * sDriver) To sText If bBatch Function_Return sText Else Begin Send Stop_Box sText Function_Return "-2" End // Else Begin End // If (sRetval = "-2") Begin Else If (sRetval <> "0") Begin Get_Attribute DF_DECIMAL_SEPARATOR To iSeparator Set_Attribute DF_DECIMAL_SEPARATOR To (Ascii(".")) Move ("WARNING! The version of the connectivity kit database driver" * sDriver - ".dll is to old. The version is:" * ; String(sRetval) * "You need to update to at least version") To sText If Not bBatch ; Move "\n\nNote: This warning will not be displayed again but the program will not function properly until you do." To sText2 Case Begin Case (sDriver <> ODBC_DRV_ID) Move (sText * String(Eval(C_ODBC_DRV_VER)) + sText2) To sText Case Break Case (sDriver <> MSSQLDRV_ID) Move (sText * String(Eval(C_MSSQLDRV_VER)) + sText2) To sText Case Break Case (sDriver <> DB2_DRV_ID) Move (sText * String(Eval(C_DB2_DRV_VER)) + sText2) To sText Case Break Case (sDriver = DFBTRDRV_ID) Move (sText * String(Eval(C_DFBTRDRV_VER)) + sText2) To sText Case Break Case (sDriver = ORA_DRV_ID) Move (sText * String(Eval(C_ORA_DRV_VER)) + sText2) To sText Case Break Case (sDriver = SQL_DRV_ID) Move (sText * String(Eval(C_SQL_DRV_VER)) + sText2) To sText Case Break Case (sDriver = MDS_DB2_ID) Move (sText * String(Eval(C_MDS_DB2_VER)) + sText2) To sText Case Break Case Else Move "Case error in function SubLoadDriver (Sysfuncs)" To sText Case End Set_Attribute DF_DECIMAL_SEPARATOR To iSeparator If bBatch Function_Return sText Else Begin Send Stop_Box sText Function_Return "-3" End // Else Begin End // Else If (sRetval > 0) Begin Function_Return "1" End // If sRetval Begin Move 1 To iFailed Get_Attribute DF_NUMBER_DRIVERS To iNumDrivers For iCount From 1 To iNumDrivers Get_Attribute DF_DRIVER_NAME Of iCount To sName If (Uppercase(sName) = Uppercase(sDriver)) Move 0 To iFailed Loop If iFailed Begin Indicate Err False Load_Driver sDriver If Not (Err) Move 0 To iFailed End // If iFailed Begin If (bBatch And iFailed) Function_Return ("WARNING! Could not load database driver" * String(sDriver) + ".dll") Function_Return (String(iFailed)) End_Function // SubLoadDriver // Loads the passed driver name id. // If bBatch returns the error text else returns 0. // Always returns 0 if the loading of the driver has failed on a previous load attempt, // i.e. an error has been reported before while running a program. // Uses the SubLoaddriver function. Function IsLoadCheckDriver Global String sDriver Boolean bBatch Returns String String sRetval Move (Trim(sDriver)) To sDriver Case Begin Case (sDriver = ODBC_DRV_ID) If (Not(bBatch) And pbODBC_DRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval // LoadDriver is a function in SncFuncs.pkg Set pbODBC_DRV Of oDrvArray To True Case Break Case (sDriver = DB2_DRV_ID) If (Not(bBatch) And pbDB2_DRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbDB2_DRV Of oDrvArray To True Case Break Case (sDriver = MDS_DB2_ID) If (Not(bBatch) And pbMDS_DB2(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbMDS_DB2 Of oDrvArray To True Case Break Case (sDriver = MSSQLDRV_ID) If (Not(bBatch) And pbMSSQLDRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbMSSQLDRV Of oDrvArray To True Case Break Case (sDriver = SQL_DRV_ID) If (Not(bBatch) And pbSQL_DRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbSQL_DRV Of oDrvArray To True Case Break Case (sDriver = ORA_DRV_ID) If (Not(bBatch) And pbORA_DRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbORA_DRV Of oDrvArray To True Case Break Case (sDriver = DFBTRDRV_ID) If (Not(bBatch) And pbDFBTRDRV(oDrvArray(Self))) Function_Return "0" Get SubLoadDriver sDriver bBatch To sRetval Set pbDFBTRDRV Of oDrvArray To True Case Break Case Else Move "Case error in function IsLoadCheckDriver (Sysfuncs)" To sRetval Case End If (bBatch And (Length(sRetval) > 2)) Function_Return sRetval Else Function_Return "0" // 0= Ok End_Function // IsLoadCheckDriver Function LoginExtract Global String sLogin String sKeyWord Returns String Integer iStart iEnd String sRetval Move (Trim(sLogin)) To sLogin Move (Pos(Uppercase(sKeyWord), Uppercase(sLogin))) To iStart If Not iStart Function_Return "" Move (Left(sLogin, (iStart -1))) To sRetval Move (Replace(sRetval, sLogin, '')) To sLogin Move (Pos(";", sLogin)) To iEnd If iEnd ; Move (Mid(sLogin, (iEnd - Length(sKeyWord) -1) ,(Length(sKeyWord) +1))) To sRetval Else ; Move (Mid(sLogin, 255 ,(Length(sKeyWord) +1))) To sRetval // Assume enf of string Function_Return sRetval End_Function // LoginExtract Function FieldType Global Integer iType Returns String If (iType = DF_ASCII) Function_Return "ASCII" If (iType = DF_BCD) Function_Return "Numeric" If (iType = DF_DATE) Function_Return "Date" If (iType = DF_TEXT) Function_Return "Text" If (iType = DF_BINARY) Function_Return "Binary" If (iType = DF_OVERLAP) Function_Return "Overlap" Function_Return "UNKNOWN" End_Function // FieldType Function ExtractValue Global String sText String sDelimit Returns String Integer iPos Move (String(sText) - String(sDelimit)) To sText Move (Pos(sDelimit, sText)) To iPos Function_Return (Left(sText, (iPos - 1))) End_Function // ExtractValue // 0=LT 1=LE 2=EQ 3=GE 4=GT 5=NE 6=Matches 7=Contains Function ExtractMode Global String sText Returns String String sMode sChar Integer iPos iMode Move (Pos(" ", sText)) To iPos If Not iPos Function_Return "" Move (Left(sText, (iPos - 1))) To sMode If ("01234567" Contains sMode) Begin Move sMode To iMode If (iMode = 0) Function_Return "<" If (iMode = 1) Function_Return "<=" If (iMode = 2) Function_Return "=" If (iMode = 3) Function_Return ">=" If (iMode = 4) Function_Return ">" If (iMode = 5) Function_Return "<>" If (iMode = 6) Function_Return "Matches" If (iMode = 7) Function_Return "Contains" Function_Return "" End // If ("01234567" contains sChar) Begin Else Begin If (sMode = "<") Function_Return "0" If (sMode = "<=") Function_Return "1" If (sMode = "=") Function_Return "2" If (sMode = ">=") Function_Return "3" If (sMode = ">") Function_Return "4" If (sMode = "<>") Function_Return "5" If (sMode = "Matches") Function_Return "6" If (sMode = "Contains") Function_Return "7" Function_Return "" End // Else Begin End_Function // ExtractMode //*** Function: Find_file //*** Purpose : Find the given name in DFPATH. If it exists, return the full //*** name. Function Find_File Global String sFileName Returns String String sFullName sPath sPath_sep sDir Integer iSeparator iSeppos bFileExist //*** Only check if there are no directory separators in the name. Move "" To sFullName Move 0 To iSeparator If (SysConf(SYSCONF_DIR_SEPARATOR)) in sFileName Move 1 To iSeparator If (Not(iSeparator)) Begin Move 0 To bFileExist Move (SysConf(SYSCONF_PATH_SEPARATOR)) To sPath_sep Get_Attribute DF_OPEN_PATH To sPath If (Length(sPath)) Begin Repeat Pos sPath_sep In sPath To iSeppos If iSeppos Begin Left sPath To sDir (iSeppos - 1) Right sPath To sPath (Length(sPath) - iSeppos) If (Length(sDir)) Begin Append sDir (SysConf(SYSCONF_DIR_SEPARATOR)) sFileName Get Get_file_exists sDir To bFileExist // Function in Func.pkg (DAW package file) If bFileExist Move sDir To sFullName End // If (Length(sDir)) Begin End // If iSeppos Begin Until ((Not(iSeppos)) Or bFileExist) If (Not(bFileExist)) Begin If (Length(sPath)) Begin Move sPath To sDir Append sDir (SysConf(SYSCONF_DIR_SEPARATOR)) sFileName Get Get_file_exists sDir To bFileExist If bFileExist ; Move sDir To sFullName End // If (Length(sPath)) Begin End // If (Not(bFileExist)) Begin End // If (Length(sPath)) Begin Else Begin Move "." To sDir Append sDir (SysConf(SYSCONF_DIR_SEPARATOR)) sFileName Get Get_file_exists sDir To bFileExist If bFileExist Move sDir To sFullName End // Else Begin End // If (Not(iSeparator)) Begin Else Move sFileName To sFullName Function_Return (Trim(sFullName)) End_Function // Find_file //***************************************************************************** //*** Function: StripPath *** //*** Purpose : Strip the path of a file path. Returns only the last name *** //*** in the path. *** //*** *** //*** Arguments: *** //*** sFilePath The path to the file. *** //*** *** //*** Returns: *** //*** The file name only. *** //***************************************************************************** Function StripPath Global String sFilePath Returns String String sFileName sChar sDirSep Integer iCount iReady Move (SysConf(SYSCONF_DIR_SEPARATOR)) To sDirSep Move (Length(sFilePath)) To iCount Move DFFALSE To iReady While ((iCount > 0) And (Not(iReady))) Move (Mid(sFilePath, 1, iCount)) To sChar If (sChar = sDirSep) Move DFTRUE To iReady Else Decrement iCount End // While... Move (Right(sFilePath, (Length(sFilePath) - iCount))) To sFileName Function_Return sFileName End_Function // StripPath //***************************************************************************** //*** Function: StripFile *** //*** Purpose : Strip the file name of a file path. Returns only the *** //*** the path. *** //*** *** //*** Arguments: *** //*** sFilePath The path to the file. *** //*** *** //*** Returns: *** //*** The path only. *** //***************************************************************************** Function StripFile Global String sFilePath Returns String String sPathName sChar sDirSep Integer iCount iReady Move (SysConf(SYSCONF_DIR_SEPARATOR)) To sDirSep Move (Length(sFilePath)) To iCount Move DFFALSE To iReady While ((iCount > 0) And (Not(iReady))) Move (Mid(sFilePath, 1, iCount)) To sChar If (sChar = sDirSep) Move DFTRUE To iReady Else Decrement iCount End // While... Move "" To sPathName If iCount ; Move (Left(sFilePath, iCount - 1)) To sPathName Function_Return sPathName End_Function // StripFile //***************************************************************************** //*** Function: StripExt *** //*** Purpose : Strip the extension of a filename. *** //*** *** //*** Arguments: *** //*** sFilePath The path to the file. *** //*** *** //*** Returns: *** //*** The filename without the extension. *** //***************************************************************************** Function StripExt Global String sFilePath Returns String String sFileName sChar Integer iCount iReady Move (Trim(sFilePath)) To sFilePath Move (Length(sFilePath)) To iCount Move DFFALSE To iReady While ((iCount > 0) And (Not(iReady))) Move (Mid(sFilePath, 1, iCount)) To sChar Decrement iCount If (sChar = ".") Move DFTRUE To iReady End // While... If iReady Move (Left(sFilePath, iCount)) To sFileName Else Move sFilePath To sFileName Function_Return sFileName End_Function // StripExt Function DataflexNameOnly Global String sFullPath Returns String String sPath sTable sRetval Get StripFile sFullPath To sPath Get StripPath sFullPath To sTable Get StripExt sTable To sRetval Function_Return sRetval End_Function // DataflexNameOnly // Returns a string with the first character capitalized, and // the rest of the string in lowercase: Function UpperFirstChar Global String sValue Returns String String sChar Move (Uppercase(Left(sValue, 1))) To sChar Move (sChar + Right(Lowercase(sValue), (Length(sValue) -1))) To sValue Function_Return sValue End_Function // UpperFirstChar // Parameters: File handle and field number // Returns : A formatted field string including type, length and precision. E.g. "Customerno (ASCII 8,2)" Function FieldSpecs Global Integer iFile Integer iField Returns String String sSep sFieldName sRetval sType sLength Integer iType iLength iPrec Send Ignore_Error Of Error_Info_Object 54 Send Ignore_Error Of Error_Info_Object 77 Get_Attribute DF_DECIMAL_SEPARATOR To sSep Move (Character(sSep)) To sSep Get_Attribute DF_FIELD_NAME Of iFile iField To sFieldname Get UpperFirstChar sFieldName To sFieldName Get_Attribute DF_FIELD_TYPE Of iFile iField To iType Get FieldType iType To sType Get_Attribute DF_FIELD_LENGTH Of iFile iField To iLength Get_Attribute DF_FIELD_PRECISION Of iFile iField To iPrec If (iType = DF_BCD) Move (iLength - iPrec) To iLength Else Move 0 To iPrec Send Trap_Error Of Error_Info_Object 54 Send Trap_Error Of Error_Info_Object 77 Function_Return (String(sFieldName) * "(" + String(sType) * String(iLength) + sSep + String(iPrec) + ")") End_Function // FieldSpecs Procedure ReDisplayWindow Global Handle hWnd hVoid hoMain Get RdsMain_Panel_Id To hoMain Get Window_Handle Of hoMain To hWnd If hWnd Move (UpdateWindow(hWnd)) To hVoid End_Procedure Function DDObjectId Global Handle hoDD Integer iFile String sField Returns Handle Handle ho Integer iField iCount iItems iSearchField Field_Map iFile (Trim(sField)) To iSearchField Get Data_Set_User_Interface_Count Of hoDD To iItems For iCount From 1 To iItems Get Data_Set_User_Interface Of hoDD iCount To ho If ho Get Data_Field Of ho To iField If (iField = iSearchField) Break Loop // For iCount from 1 to iItems Function_Return ho End_Function // DDObjectId // On Successful open of the DDF file returns the file handle: // Else returns 0 Function OpenDDFFile Global Boolean bFrom String sPath String sDriver Boolean bSilent Returns Integer Integer iFile iOpen iRetval iDataFile String sOrgPath sPassword If bFrom Move giFromDDF To iFile // Global variable in Syncfuncs.pkg Else Move giToDDF To iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If iOpen Begin If bFrom Get Field_Current_Value Of (phoDD(Self)) Field SncTable.FromFile To iDataFile Else Get Field_Current_Value Of (phoDD(Self)) Field SncTable.ToFile To iDataFile Get_Attribute DF_FILE_OPENED Of iDataFile To iOpen If iOpen Close iDataFile End // If iOpen Begin // 2004-06-23 ------------------------------------ Start Nils G. Svedmyr // IMPORTANT: // Until the P.SQL driver can handle both a Source and a Target table, we need to make sure // that both meta files are closed before attempting to do an open. Close giFromDDF Close giToDDF Get CreateX$Files sPath To iRetval // Global function in syncfuncs.pkg If Not iRetval Begin If Not bSilent Send Stop_Box ("The files X$File.int, X$Field.int and X$Index.int were missing in the folder" * sPath * "CrossMerge tried to create them but failed. Check your rights for creating files in that folder. Cannot continue.") Function_Return 0 End // If Not iRetval Begin DFBTR_REMOVE_ALL_OWNERS DFBTR_ADD_OWNER "..SC...." // 2003-05-14 ------------------------------------ Start Nils G. Svedmyr If bFrom Get Field_Current_Value Of (phoDD(Self)) Field SncTable.FromPv To sPassword Else Get Field_Current_Value Of (phoDD(Self)) Field SncTable.ToPv To sPassword Move (Trim(sPassword)) To sPassword If (Length(sPassword) > 0) DFBTR_DDF_OWNER sPassword // 2003-05-14 ------------------------------------ Stop Nils G. Svedmyr Get_Attribute DF_OPEN_PATH To sOrgPath Set_Attribute DF_OPEN_PATH To sPath //(sPath - ";" - sOrgPath) Send Ignore_Error Of Error_Info_Object 75 // 'Can't open data file' Open (sDriver - ":" - sPath - "\X$FILE") as iFile Set_Attribute DF_OPEN_PATH To sOrgPath // RESET DF_OPEN_PATH! Send Trap_Error Of Error_Info_Object 75 Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bSilent Send Stop_Box ("Could not open Pervasive.SQL Meta Data file:" * sPath - "\File.ddf. Is it password protected?") Function_Return 0 End // If Not iOpen Begin Function_Return iFile End_Function // OpenDDFFile // Returns: Filenumber if the file was successfully opened. // 0 if it could not be opened. Function RDSOpenAsFile Global Handle hoDD Boolean bFrom Boolean bBatch Returns Integer String sDriver sPath sOrgPath sTable sServer sUser sPassword sOwner sConnect sDataBase Integer iFile iOpen iNTAuth iType iRetval iDSNType iCount Integer iFileOemToAnsi If (Not(bBatch) And Active_State(Self)) Send StartWorkingMessage "Opening Database Table..." If bFrom Begin Get Field_Current_Value Of hoDD Field SncTable.FromFile To iFile Get Field_Current_Value Of hoDD Field SncTable.FromDriver To sDriver Get Field_Current_Value Of hoDD Field SncTable.FromFilePath To sPath Get Field_Current_Value Of hoDD Field SncTable.FromDataTable To sTable Get Field_Current_Value Of hoDD Field SncTable.FromDataBase To sDatabase Get Field_Current_Value Of hoDD Field SncTable.FromNTAuth To iNTAuth Get Field_Current_Value Of hoDD Field SncTable.FromdbType To iType Get Field_Current_Value Of hoDD Field SncTable.FromServer To sServer Get Field_Current_Value Of hoDD Field SncTable.FromUser To sUser Get Field_Current_Value Of hoDD Field SncTable.FromOwner To sOwner Get Field_Current_Value Of hoDD Field SncTable.FromPv To sPassword Get Field_Current_Value Of hoDD Field SncTable.FromDSNType To iDSNType Get Field_Current_Value Of hoDD Field SncTable.FrFileOemToAnsi To iFileOemToAnsi End // If bFrom Begin Else Begin Get Field_Current_Value Of hoDD Field SncTable.ToFile To iFile Get Field_Current_Value Of hoDD Field SncTable.ToDriver To sDriver Get Field_Current_Value Of hoDD Field SncTable.ToFilePath To sPath Get Field_Current_Value Of hoDD Field SncTable.ToDataTable To sTable Get Field_Current_Value Of hoDD Field SncTable.ToDataBase To sDatabase Get Field_Current_Value Of hoDD Field SncTable.ToNTAuth To iNTAuth Get Field_Current_Value Of hoDD Field SncTable.TodbType To iType Get Field_Current_Value Of hoDD Field SncTable.ToServer To sServer Get Field_Current_Value Of hoDD Field SncTable.ToUser To sUser Get Field_Current_Value Of hoDD Field SncTable.ToOwner To sOwner Get Field_Current_Value Of hoDD Field SncTable.ToPv To sPassword Get Field_Current_Value Of hoDD Field SncTable.ToDSNType To iDSNType Get Field_Current_Value Of hoDD Field SncTable.ToFileOemToAnsi To iFileOemToAnsi End // Else Begin If Not iFile Begin If Not bBatch Send StopWorkingMessage Function_Return 0 // Nothing to do yet... End // If Not iFile Begin Get_Attribute DF_FILE_OPENED Of iFile To iOpen If iOpen Begin Close iFile End // If iOpen Begin If (Not(iType) And Not(bBatch)) Send Info_Box "Program Error. The database type has not been set." If (Not(iFile) Or Not(iType)) Begin If Not bBatch Send StopWorkingMessage Function_Return 0 End // If (Not(iFile) Or Not(iType)) Begin Move (Trim(sDriver)) To sDriver Move (Trim(sPath)) To sPath Move (Trim(sTable)) To sTable // Move (Uppercase(sTable)) To sTable Move (Trim(sServer)) To sServer Move (Trim(sUser)) To sUser Move (Trim(sOwner)) To sOwner Move (Trim(sPassword)) To sPassword If (sTable Contains "") Move "" To sTable If (sServer Contains "") Move "" To sServer If (Length(sTable) = 0) Begin If Not bBatch Send StopWorkingMessage Function_Return 0 End // If (Length(sTable) = 0) Begin If (iType > 1 And iType < 6 And (Length(sServer) = 0)) Begin If Not bBatch Send StopWorkingMessage Function_Return 0 // Nothing to do... End // If (iType > 1 And iType < 6 And (Length(sServer) = 0)) Begin Send Ignore_Error Of Error_Info_Object 72 // 'File not open' Send Ignore_Error Of Error_Info_Object 75 // 'Can't open data file' Send Ignore_Error Of Error_Info_Object 4271 // 'Unable to open intermediate file' Send Ignore_Error Of Error_Info_Object 12293 // 'Login unsuccessful' Send Ignore_Error Of Error_Info_Object 12295 // 'Table not in connection' Send Ignore_Error Of Error_Info_Object 12289 // General MS SQL Error Get IsLoadCheckDriver sDriver False To iRetval Case Begin Case (iType = 1) // DataFlex Open (sPath - "\" - sTable) as iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send Info_Box ("Could not open DataFlex data table:" * sPath - "\" - sTable) Move 0 To iFile End // If Not iOpen Begin Case Break Case (iType = 2) // IBM DB2 UDB Move ("DSN=" + String(sServer) + ";UID=" + sUser + ";PWD=" + sPassword) To sConnect If (Length(sOwner) > 0) Move (sDriver + ":" + sOwner + "#" + sTable + "@" + sConnect) To sConnect Else Move (sDriver + ":" + sTable + "@" + sConnect) To sConnect Send Ignore_Error Of Error_Info_Object 12293 Open sConnect as iFile Send Trap_Error Of Error_Info_Object 12293 Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open IBM DB2 Universal Database data table:" * sTable) Move 0 To iFile Open SncTable // For some odd reason we need this if login fails and the cancel button is pressed. End // If Not iOpen Begin Case Break Case (iType = 3) // MS SQL If iNTAuth Begin Login (sServer + ";Trusted_Connection=Yes") sUser "" sDriver End // If iNTAuth Begin Move ("SERVER=" + String(sServer) + ";DATABASE=" + sDataBase + ";UID=" + sUser + ";PWD=" + sPassword) To sConnect If (Length(sOwner) > 0) Move (sDriver + ":" + sOwner + "#" + sTable + "@" + sConnect) To sConnect Else Move (sDriver + ":" + sTable + "@" + sConnect) To sConnect Open sConnect as iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open Microsoft SQL data table:" * sTable) Move 0 To iFile Open SncTable // For some odd reason we need this if login fails and the cancel button is pressed. End // If Not iOpen Begin Case Break Case (iType = 4) // ODBC If (iDSNType = 2) Begin Get StripExt sServer To sServer Move ("FILEDSN=" + sPath - "\" - sServer) To sServer Move "" To sOwner // Can't be used with FILEDSN. Move sServer To sConnect End // If (iDSNType = 2) Begin Else Begin Move ("DSN=" + sServer) To sServer Move (String(sServer) + ";UID=" + sUser + ";PWD=" + sPassword) To sConnect End // Else Begin If (Length(sOwner) > 0) Move (sDriver + ":" + sOwner + "#" + sTable + "@" + sConnect) To sConnect Else Move (sDriver + ":" + sTable + "@" + sConnect) To sConnect Open sConnect as iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin // Get IsRetryOpenFileUpperUserName sConnect iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open ODBC data table:" * sTable + ". You could try to press the Login button to check that the login info is correct.") Move 0 To iFile Open SncTable // For some odd reason we need this if login fails and the cancel button is pressed. End // If Not iOpen Begin End // If Not iOpen Begin Case Break Case (iType = 5) // Oracle Send DoCreateIntFile sDriver sServer sTable sOwner 1 // *** TEMP *** If (Length(sUser) > 0 Or Length(sPassword) > 0) Login sServer sUser sPassword sDriver Open (sTable + ".INT") as iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open Oracle data table:" * sTable) Move 0 To iFile End // If Not iOpen Begin Else Get IsChangedPrimaryIndex sDriver sServer sTable 1 iFile To iRetval If iRetval Begin Open (sTable + ".INT") as iFile Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open Oracle Database data table:" * sTable * "after primary index check.") Move 0 To iFile End // If Not iOpen Begin End // If iRetval Begin Case Break Case (iType = 6) // Pervasive.SQL // 2004-06-21 ------------------------------------ Start Nils G. Svedmyr Get OpenDDFFile bFrom sPath sDriver False To iOpen If (iOpen = 0) Function_Return // 2004-06-21 ------------------------------------ Stop Nils G. Svedmyr // If (Length(sPassword) > 0) Begin // DFBTR_REMOVE_ALL_OWNERS // DFBTR_ADD_OWNER sPassword // "..SC...." // End // If (Length(sPassword) > 0) Begin Send Ignore_Error Of Error_Info_Object 72 // 'File not open' Send Ignore_Error Of Error_Info_Object 75 // 'Can't open data file' Send Ignore_Error Of Error_Info_Object 4271 // 'Unable to open intermediate file' Send Ignore_Error Of Error_Info_Object 12293 // 'Login unsuccessful' Send Ignore_Error Of Error_Info_Object 12295 // 'Table not in connection' Send Ignore_Error Of Error_Info_Object 12289 // General MS SQL Error Get_Attribute DF_OPEN_PATH To sOrgPath Set_Attribute DF_OPEN_PATH To sPath //(sPath - ";" - sOrgPath) Open (sDriver - ":" - sPath - "\" - sTable) as iFile Set_Attribute DF_OPEN_PATH To sOrgPath // RESET DF_OPEN_PATH! Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin If Not bBatch Send StopWorkingMessage If Not bBatch Send Info_Box ("Could not open Pervasive data table:" * sPath - "\" - sTable - ".") Move 0 To iFile End // If Not (Found) Begin Case Break Case Else Send StopWorkingMessage Function_Return 0 Case End If iFile Set_Attribute DF_REPORT_UNSUPPORTED_ATTRIBUTES Of iFile To False If (iFile And bBatch And (iType > 1 And iType < 6)) Begin Set_Attribute DF_FILE_TABLE_CHARACTER_FORMAT Of iFile To (If(iFileOemToAnsi = 1, "ANSI", "OEM")) Set_Attribute DF_FILE_GET_RID_AFTER_CREATE Of iFile To True Set_Attribute DF_FILE_MAX_ROWS_FETCHED Of iFile To 0 //1 Set_Attribute DF_FILE_REFIND_AFTER_SAVE Of iFile To False End // If (iFile And bBatch And (iType > 1 And iType < 6)) Begin Indicate Err False Send Trap_Error Of Error_Info_Object 72 Send Trap_Error Of Error_Info_Object 75 Send Trap_Error Of Error_Info_Object 4271 Send Trap_Error Of Error_Info_Object 12293 Send Trap_Error Of Error_Info_Object 12295 Send Trap_Error Of Error_Info_Object 12289 Send StopWorkingMessage Function_Return iFile End_Function // RDSOpenAsFile // Will try to uppercase the UserID in the connect string and retry to open the file Function IsRetryOpenFileUpperUserName Global String sConnect Integer iFile Returns Integer Integer iRetval iStart iEnd iCount String sChar Move (Pos("UID=", sConnect)) To iStart If Not iStart Function_Return 0 Move (iStart + 4) To iStart Move (Pos(";PWD=", sConnect)) To iEnd For iCount From iStart To (iEnd - 1) Move (Mid(sConnect, 1, iCount)) To sChar Move (Uppercase(sChar)) To sChar Move (Overstrike(sChar, sConnect, iCount)) To sConnect Loop // For iCount from iStart to iEnd Open sConnect as iFile Get_Attribute DF_FILE_OPENED Of iFile To iRetval Function_Return iRetval End_Function // IsRetryOpenFileUpperUserName // Returns True if exist or successfully created. Else False: Function CreateX$Files Global String sPath Returns Integer Integer iRetval iCh iExist Get Seq_New_Channel To iCh If Not iCh Begin Send Stop_Box ("No available output channel. Could not create X_File.int in folder:" * String(sPath)) Function_Return 0 End // If Not iCh Begin Move 1 To iExist Get vFilePathExists (sPath - "\X_File.int") To iRetval If Not iRetval Begin Direct_Output Channel iCh (sPath - "\X_File.int") Writeln Channel iCh "Driver_Name DFBTRDRV" Writeln Channel iCh "" Writeln Channel iCh "DDF_Name X$FILE" Writeln Channel iCh "" Writeln Channel iCh 'Owner "..SC...."' Writeln Channel iCh "" Close_Output Channel iCh If iExist Get vFilePathExists (sPath - "\X_File.int") To iExist End // If Not iRetval Begin Get vFilePathExists (sPath - "\X_Field.int") To iRetval If Not iRetval Begin Direct_Output Channel iCh (sPath - "\X_Field.int") Writeln Channel iCh "Driver_Name DFBTRDRV" Writeln Channel iCh "" Writeln Channel iCh "DDF_Name X$FIELD" Writeln Channel iCh "" Writeln Channel iCh 'Owner "..SC...."' Writeln Channel iCh "" Close_Output Channel iCh If iExist Get vFilePathExists (sPath - "\X_Field.int") To iExist End // If Not iRetval Begin Get vFilePathExists (sPath - "\X_Index.int") To iRetval If Not iRetval Begin Direct_Output Channel iCh (sPath - "\X_Index.int") Writeln Channel iCh "Driver_Name DFBTRDRV" Writeln Channel iCh "" Writeln Channel iCh "DDF_Name X$INDEX" Writeln Channel iCh "" Writeln Channel iCh 'Owner "..SC...."' Writeln Channel iCh "" Close_Output Channel iCh If iExist Get vFilePathExists (sPath - "\X_Index.int") To iExist End // If Not iRetval Begin Send Seq_Release_Channel iCh Function_Return iExist End_Function // CreateX$Files sPath Returns Integer Procedure DoCreateIntFile Global String sDriver String sServer String sTable String sOwner Integer iRecordIdentity String sPath Integer iRetval iChnl Get psDataPath Of (phoWorkspace(ghoApplication)) To sPath Get vFilePathExists (sPath - "\" - sTable - ".INT") To iRetval If iRetval Begin // If the file already exists. // Procedure_Return // *** TEMP *** Do not re-create. Get vDeleteFile (sPath - "\" - sTable - ".INT") To iRetval Get vDeleteFile (sPath - "\" - sTable - ".CCH") To iRetval End // If iRetval Begin Get Seq_New_Channel To iChnl If (iChnl < 0) Procedure_Return Direct_Output Channel iChnl (sPath - "\" - sTable - ".Int") Writeln Channel iChnl "DRIVER_NAME " sDriver If (Length(sServer) > 0) ; Writeln Channel iChnl "SERVER_NAME " sServer If (sDriver <> DFBTRDRV_ID) ; Writeln Channel iChnl "DATABASE_NAME " sTable If (Length(sOwner) > 0) ; Writeln Channel iChnl "SCHEMA_NAME " sOwner Writeln Channel iChnl "" Writeln Channel iChnl "PRIMARY_INDEX 1" Writeln Channel iChnl "USE_DUMMY_ZERO_DATE YES" Writeln Channel iChnl "" Writeln Channel iChnl "" Writeln Channel iChnl "INDEX_NUMBER 1" Writeln Channel iChnl "INDEX_NUMBER_SEGMENTS 1" Writeln Channel iChnl ("INDEX_SEGMENT_FIELD " + String(iRecordIdentity)) Close_Output Channel iChnl Send Seq_Release_Channel iChnl End_Procedure // DoCreateIntFile Function IsChangedPrimaryIndex Global String sDriver String sServer String sTable Integer iIdentity Integer iFile Returns Integer String sPath Integer iRetval iRecordIdentity iOpen Get psDataPath Of (phoWorkspace(ghoApplication)) To sPath Get vFilePathExists (sPath - "\" - sTable - ".INT") To iRetval If Not iRetval Begin Send Stop_Box ("Could not find the" * sPath - "\" - sTable - ".INT file.") Function_Return False End // If Not iRetval Begin Get_Attribute DF_FILE_OPENED Of iFile To iOpen If Not iOpen Begin Send Stop_Box ("The table" * sTable * "is not open. Could not check primary index.") Function_Return False End // If Not iOpen Begin Get_Attribute DF_FILE_RECORD_IDENTITY Of iFile To iRecordIdentity If (iRecordIdentity <> iIdentity) Begin Close iFile Send DoCreateIntFile sDriver sServer sTable iRecordIdentity Function_Return True End // If (iRecordIdentity <> 1) Begin Function_Return False End_Function // IsChangedPrimaryIndex Procedure DoChangeRecordIdentity Global Handle hoDD Boolean bFrom Integer iRecordIdentity String sDriver sServer sTable Integer iFile iRetval If bFrom Begin Get Field_Current_Value Of hoDD Field SncTable.FromFile To iFile Get Field_Current_Value Of hoDD Field SncTable.FromDriver To sDriver Get Field_Current_Value Of hoDD Field SncTable.FromDataTable To sTable Get Field_Current_Value Of hoDD Field SncTable.FromServer To sServer End // If bFrom Begin Else Begin Get Field_Current_Value Of hoDD Field SncTable.ToFile To iFile Get Field_Current_Value Of hoDD Field SncTable.ToDriver To sDriver Get Field_Current_Value Of hoDD Field SncTable.ToDataTable To sTable Get Field_Current_Value Of hoDD Field SncTable.ToServer To sServer End // Else Begin Send DoCreateIntFile sDriver sServer sTable iRecordIdentity Get RDSOpenAsFile hoDD bFrom False To iRetval End_Procedure // DoChangeRecordIdentity