// DBUtils.cpp : implementation file // #include "stdafx.h" #include "sp.h" #include "DBUtils.h" #include "Defaultsdlg.h" #include "TED.h"//tiny editor #include "kd.h" #include "SimpleDate.h" #include "gzCurrencyFormatter.h" #include "xferdlg.h" #ifdef _DEBUG #define new DEBUG_NEW #undef THIS_FILE static char THIS_FILE[] = __FILE__; #endif #define CUTOFF 100 //cutoff indexing after this many records for testing purposes used in suckwords #define TRACING 0//1=enable runtime tracing, 0=don't ///////////////////////////////////////////////////////////////////////////// // CDBUtils IMPLEMENT_DYNCREATE(CDBUtils, CFormView) CDBUtils::CDBUtils() : CFormView(CDBUtils::IDD) { //{{AFX_DATA_INIT(CDBUtils) //}}AFX_DATA_INIT m_pApp = (CSpApp*)AfxGetApp(); //Initialize recordset pointer rs=m_pApp->rsPool->GetRS("CDBUtils (RS)"); rs2=m_pApp->rsPool->GetRS("CDBUtils (RS2)"); rs3=m_pApp->rsPool->GetRS("CDBUtils (RS3)"); m_bBootScanDone=false; } CDBUtils::~CDBUtils() { DeActivate(); } void CDBUtils::DoDataExchange(CDataExchange* pDX) { CFormView::DoDataExchange(pDX); //{{AFX_DATA_MAP(CDBUtils) DDX_Control(pDX, IDC_STAT11, m_st11); DDX_Control(pDX, IDC_PROGRESS11, m_pg11); DDX_Control(pDX, IDC_BTNTEST, m_btnTest); DDX_Control(pDX, IDC_STAT99, m_st9); DDX_Control(pDX, IDC_STAT88, m_st8); DDX_Control(pDX, IDC_STAT77, m_st7); DDX_Control(pDX, IDC_STAT66, m_st6); DDX_Control(pDX, IDC_STAT1010, m_st10); DDX_Control(pDX, IDC_PROGRESS99, m_pg9); DDX_Control(pDX, IDC_PROGRESS88, m_pg8); DDX_Control(pDX, IDC_PROGRESS77, m_pg7); DDX_Control(pDX, IDC_PROGRESS66, m_pg6); DDX_Control(pDX, IDC_PROGRESS1010, m_pg10); DDX_Control(pDX, IDC_BTNDELETEALL, m_btnDelAll); DDX_Control(pDX, IDC_BTNQUICKINDEX, m_btnQuickIndex); DDX_Control(pDX, IDC_BTNINDEXALL, m_btnIndexAll); DDX_Control(pDX, IDC_BTNDEFAULTS, m_btnDefaults); DDX_Control(pDX, IDC_BTNCOMPACT, m_btnCompact); DDX_Control(pDX, IDC_BTNCM3, m_btnCM3); DDX_Control(pDX, IDC_LBLWORDCOUNT, m_lblWordCount); DDX_Control(pDX, IDC_LBLPARTIALINFO, m_lblPartialInfo); DDX_Control(pDX, IDC_LBLFULLINFO, m_lblFullInfo); DDX_Control(pDX, IDC_STAT5, m_st5); DDX_Control(pDX, IDC_STAT4, m_st4); DDX_Control(pDX, IDC_STAT3, m_st3); DDX_Control(pDX, IDC_STAT2, m_st2); DDX_Control(pDX, IDC_STAT1, m_st1); DDX_Control(pDX, IDC_PROGRESS5, m_pg5); DDX_Control(pDX, IDC_PROGRESS4, m_pg4); DDX_Control(pDX, IDC_PROGRESS3, m_pg3); DDX_Control(pDX, IDC_PROGRESS2, m_pg2); DDX_Control(pDX, IDC_PROGRESS1, m_pg1); //}}AFX_DATA_MAP } BEGIN_MESSAGE_MAP(CDBUtils, CFormView) //{{AFX_MSG_MAP(CDBUtils) ON_BN_CLICKED(IDC_BTNCOMPACT, OnBtncompact) ON_BN_CLICKED(IDC_BTNDEFAULTS, OnBtndefaults) ON_BN_CLICKED(IDC_BTNINDEXALL, OnBtnindexall) ON_BN_CLICKED(IDC_BTNQUICKINDEX, OnBtnquickindex) ON_WM_RBUTTONDBLCLK() ON_BN_CLICKED(IDC_BTNCM3, OnBtncm3) ON_BN_CLICKED(IDC_BTNDELETEALL, OnBtndeleteall) ON_BN_CLICKED(IDC_BTNTEST, OnBtntest) ON_BN_CLICKED(IDC_BTNEXPORT, OnBtnexport) ON_BN_CLICKED(IDC_BTNIMPORT, OnBtnimport) //}}AFX_MSG_MAP ON_WM_HELPINFO() END_MESSAGE_MAP() ///////////////////////////////////////////////////////////////////////////// // CDBUtils diagnostics #ifdef _DEBUG void CDBUtils::AssertValid() const { CFormView::AssertValid(); } void CDBUtils::Dump(CDumpContext& dc) const { CFormView::Dump(dc); } #endif //_DEBUG ///////////////////////////////////////////////////////////////////////////// // CDBUtils message handlers void CDBUtils::OnInitialUpdate() { CFormView::OnInitialUpdate(); if(m_pApp->m_lusrID==1) m_btnDelAll.ShowWindow(TRUE); //registered? if(m_pApp->m_uiFeatures&LICENSE_REGISTERED) ; else m_btnDelAll.ShowWindow(FALSE); ppg[0]=&m_pg1; ppg[1]=&m_pg2; ppg[2]=&m_pg3; ppg[3]=&m_pg4; ppg[4]=&m_pg5; ppg[5]=&m_pg6; ppg[6]=&m_pg7; ppg[7]=&m_pg11; ppg[8]=&m_pg9; ppg[9]=&m_pg10; ppg[10]=&m_pg8; //display index information ShowIndexInfo(); SetRights(); #ifdef _DEBUG m_btnTest.ShowWindow(TRUE); #endif //_DEBUG } void CDBUtils::Activate() { #ifdef _WTF_ AfxMessageBox("dbutils activate"); #endif //Process database updates if any. if(m_pApp->m_bBadDatabaseVersion) UpdateDatabaseSchema(); //daily maintenance if(!m_bBootScanDone) BootScan(); } void CDBUtils::DeActivate() { #ifdef _WTF_ AfxMessageBox("dbutils De-activate"); #endif m_pApp->rsPool->ReleaseRS(&rs->m_nID); m_pApp->rsPool->ReleaseRS(&rs2->m_nID); m_pApp->rsPool->ReleaseRS(&rs3->m_nID); } CSpDoc* CDBUtils::GetDocument() { return (CSpDoc*)m_pDocument; } void CDBUtils::OnBtncompact() { ShowProgressControls(false); if(!m_pApp->rsPool->GoExclusive()) { AfxMessageBox("All other users need to exit first\r\n" "You need exclusive access in order to proceed."); rs->m_bExclusiveConnection=false; //back to shared mode m_pApp->rsPool->GoShared(); return ; } m_pApp->rsPool->Disconnect(); GetDocument()->Compact(true);//compact and keep backup copy rs->m_bExclusiveConnection=false; //rs->Close(); //Ok, everyone is out, go shared m_pApp->rsPool->GoShared(); AfxMessageBox("Finsihed"); } void CDBUtils::OnBtndefaults() { ShowProgressControls(false); CDefaultsDlg d; d.DoModal(); } void CDBUtils::OnBtnindexall() { if(ExclusiveAccess()) Index(true); } void CDBUtils::OnBtnquickindex() { if(ExclusiveAccess()) Index(false); } bool CDBUtils::ExclusiveAccess() { rs->m_bExclusiveConnection=true; if(!m_pApp->rsPool->GoExclusive()) { AfxMessageBox("All other users need to exit first\r\n" "You need exclusive access in order to proceed."); rs->m_bExclusiveConnection=false; //back to shared mode m_pApp->rsPool->GoShared(); return false; } rs->m_bExclusiveConnection=false; rs->Close(); //Ok, everyone is out, go shared m_pApp->rsPool->GoShared(); return true; } void CDBUtils::Index(bool bFullIndex) { CString str,strText,strWord,lchar,q,strData; long lData,lRecs,lUniqueWords; COleDateTime dtStart,dtEnd; COleDateTimeSpan dtsDuration; float fData; dtStart=COleDateTime::GetCurrentTime(); //Open exclusive CWaitCursor wait; m_strErrorLog.Empty(); ShowProgressControls(true); PeekAndPump(); wait.Restore(); //Empty temporary dictionary (should be empty anyway) rs->Close(); rs->Ex("DELETE srchtempdict.* FROM srchtempdict;"); //If re-indexing *ALL* then if(bFullIndex) { //Flag all tables with an indexed field to no rs->Ex("UPDATE probs SET probs.indexed = False;"); rs->Ex("UPDATE labor SET labor.indexed = False;"); rs->Ex("UPDATE subrepair SET subrepair.indexed = False;"); rs->Ex("UPDATE rentals SET rentals.indexed = False;"); rs->Ex("UPDATE clients SET clients.indexed = False;"); //Added 8/29/00 rs->Ex("UPDATE contacts SET contacts.indexed = False;"); rs->Ex("UPDATE units SET units.indexed = False;"); //Added 05/09/2001 rs->Ex("UPDATE wo SET wo.indexed = False;"); //ADD NEW ITEM HERE //Empty search keys and dictionary tables rs->Ex("DELETE srchkey.* FROM srchkey;"); rs->Ex("DELETE srchdict.* FROM srchdict;"); } else { //REMOVE STALE DATA ASSOCIATED WITH RECORDS THAT WERE INDEXED BUT ARE NOW //NOT DUE TO EDITS ETC //flag stale search keys //CLIENTS rs->Ex("UPDATE clients INNER JOIN srchkey ON clients.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=4) AND ((clients.indexed)=False));"); //LABOR rs->Ex("UPDATE srchkey INNER JOIN labor ON [srchkey].[tableid]=[labor].[id] SET srchkey.remove = True " "WHERE ((([srchkey].[tabletype])=1) And (([labor].[indexed])=False));"); //PROBS rs->Ex("UPDATE srchkey INNER JOIN probs ON srchkey.tableid = probs.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=0) AND ((probs.indexed)=False));"); //RENTALS rs->Ex("UPDATE rentals INNER JOIN srchkey ON rentals.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=3) AND ((rentals.indexed)=False));"); //SUBREPAIRS rs->Ex("UPDATE srchkey INNER JOIN subrepair ON srchkey.tableid = subrepair.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=2) AND ((subrepair.indexed)=False));"); //CONTACTS rs->Ex("UPDATE contacts INNER JOIN srchkey ON contacts.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=5) AND ((contacts.indexed)=False));"); //UNITS rs->Ex("UPDATE srchkey INNER JOIN subrepair ON srchkey.tableid = subrepair.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=6) AND ((subrepair.indexed)=False));"); //Added 05/09/2001 new table workorder header is table type 7 //WORKORDER HEADERS rs->Ex("UPDATE srchkey INNER JOIN wo ON srchkey.tableid = wo.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=7) AND ((wo.indexed)=False));"); //ADD NEW ITEM HERE AS TABLE TYPE 8 //REMOVE previous search results here rs->Ex("DELETE srch.* FROM srch;"); //remove stale search keys rs->Ex("DELETE srchkey.*, srchkey.remove " "FROM srchkey " "WHERE (((srchkey.remove)=True));"); //flag stale dictionary words rs->Ex("UPDATE srchkey RIGHT JOIN srchdict ON srchkey.wordid = srchdict.ID SET srchdict.remove = True " "WHERE (((srchkey.wordid) Is Null));"); //Remove stale dictionary words not used anymore rs->Ex("DELETE srchdict.*, srchdict.remove " "FROM srchdict " "WHERE (((srchdict.remove)=True));"); } //Loop through each table //pull out words and add each word to the temporary dictionary //with the word and the record it came from //srchkey.type: 0=probs,1labour,2subrepair,3rentals,4clients //5-contacts (client notebook) 6=units, 7=workorder headers (wo) //********************************************************* //********************************************************* //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' //zTrace("index C",false); //PROBS (table 0)* //v1.9.4.5 added slight variation on query for performance gain if(bFullIndex) rs2->QueryReadOnly("SELECT probs.id, [brief], [probs].[notes], probs.created AS idate, wo.client AS iclient " "FROM probs LEFT JOIN wo ON probs.wolink = wo.id;"); else rs2->QueryReadOnly("SELECT probs.id, [brief], [probs].[notes], probs.created AS idate, wo.client AS iclient " "FROM probs LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((probs.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(0); } ppg[0]->SetPos(100); PeekAndPump(); wait.Restore(); //zTrace("index D",false); //LABOUR (table 1)* //v1.9.4.5 added slight variation on query for performance gain if(bFullIndex) rs2->QueryReadOnly("SELECT labor.id, labor.details , labor.stop AS idate, wo.client AS iclient " "FROM (labor LEFT JOIN probs ON labor.link = probs.id) LEFT JOIN wo ON probs.wolink = wo.id;"); else rs2->QueryReadOnly("SELECT labor.id, labor.details, labor.stop AS idate, wo.client AS iclient " "FROM (labor LEFT JOIN probs ON labor.link = probs.id) LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((labor.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(1); } //AfxMessageBox("Done labour starting subrepair"); ppg[1]->SetPos(100); PeekAndPump(); wait.Restore(); //zTrace("index E",false); //SUBREPAIR (table2)* rs2->QueryReadOnly("SELECT subrepair.id, subrepair.notes, subrepair.created AS idate, wo.client AS iclient " "FROM (subrepair LEFT JOIN probs ON subrepair.link = probs.id) LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((subrepair.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(2); } //AfxMessageBox("Done subrepair, starting rentals"); ppg[2]->SetPos(100); PeekAndPump(); wait.Restore(); //RENTALS (table 3)* rs2->QueryReadOnly("SELECT rentals.id, [notes], [loanedto], [description], rentals.dateout AS idate, rentals.clientlink AS iclient " "FROM rentals " "WHERE (((rentals.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(3); } ppg[3]->SetPos(100); PeekAndPump(); wait.Restore(); //CLIENTS (table 4)* rs2->QueryReadOnly("SELECT clients.id, clients.id AS iclient, clients.created AS idate, [generalnotes] , " "[technotes] , [alert] , " "[first] , [last] , [company] " " , [mailaddress] , " "[streetaddress] , [city] , " "[stateprov] , [postal] , " "[country] , [bizphone] , " "[fax] , [email] , [acctnumber] , [phone2] , [phone3] " "FROM clients WHERE (((clients.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(4); } ppg[4]->SetPos(100); PeekAndPump(); wait.Restore(); //CONTACTS (table 5)* rs2->QueryReadOnly( "SELECT contacts.id, contacts.notes, contacts.date AS idate, " "contacts.clientlink AS iclient FROM contacts " "WHERE (((contacts.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(5); } ppg[5]->SetPos(100); PeekAndPump(); wait.Restore(); //UNITS (table 6)* rs2->QueryReadOnly("SELECT units.id, [units].[receipt] , [units].[sn] , [units].[id1] , " "[units].[id2] , [units].[id3] , [units].[notes] , " "[units].[description], units.client AS iclient, " "IIf(IsNull([units].[purchasedate]),IIf(IsNull([units].[created]), " "IIf(IsNull([units].[modified]),#1/1/2000#,[units].[modified]),[units].[created]), " "[units].[purchasedate]) AS idate " "FROM units " "WHERE (((units.indexed)=False) AND ((units.client)<>0));"); if(!rs2->IsEmpty()) { SuckWords(6); } ppg[6]->SetPos(100); PeekAndPump(); wait.Restore(); //WORKORDER HEADER (TABLE 7) added 05/09/2001 //v1.9.4.5 added slight variation on query for performance gain if(bFullIndex) rs2->QueryReadOnly("SELECT wo.id, [wo].[notes], [wo].[invoice], [wo].[clientrefnum], " "[wo].[clientcontact], [wo].[ourref], wo.created AS idate, wo.client AS iclient " "FROM wo;"); else rs2->QueryReadOnly("SELECT wo.id, [wo].[notes], [wo].[invoice], [wo].[clientrefnum], " "[wo].[clientcontact], [wo].[ourref], wo.created AS idate, wo.client AS iclient " "FROM wo " "WHERE (((wo.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(7); } ppg[7]->SetPos(100); PeekAndPump(); wait.Restore(); //================================= //ADD new indexed items here. //To do: add wo header and woparts //================================= //Make the dictionary: Stage 6 //Pull out all the unique words from the temporary dictionary //that do *not* appear in the stop words table of words to ignore //and insert each one into the SearchDictionary, assigning //each one an id number (new method now will do this automatically?) //05/09/2001 changed progress control to 10 as 7 is now wo table //see initial update for more info rs2->QueryReadOnly("SELECT srchtempdict.word " "FROM (srchtempdict LEFT JOIN srchstopwords ON srchtempdict.word = " "srchstopwords.word) LEFT JOIN srchdict ON srchtempdict.word = srchdict.word " "WHERE (((srchstopwords.word) Is Null)) " "GROUP BY srchtempdict.word, srchdict.word;"); if(rs2->IsEmpty()) { AfxMessageBox("No data to index"); rs->Close(); rs2->Close(); return; } wait.Restore(); lUniqueWords=lRecs=rs2->FetchRecordCount(); rs2->MoveFirst(); lData=0; ppg[10]->SetRange32(0,(int)lRecs); //pConnection->BeginTrans(); rs2->pTheConnection->BeginTrans(); do{ rs2->FetchField("word",&strData); lData++; q.Format("INSERT INTO srchdict ( ID, word ) SELECT %u , \"%s\";",lData,strData); rs->Ex(q); }while(rs2->MoveForward()); rs2->pTheConnection->CommitTrans(); //pConnection->CommitTrans(); ppg[10]->SetPos((int)lData); PeekAndPump(); wait.Restore(); //Make keys: //match up the words and tempdictionary and insert a single match from //each record into the keys so that if the same word appears more //than once in a record, it actually only causes one entry since at //this point we don't care where in the actual record each repetition //appears, only that there is at least one in record X. //srchkey.type: 0=probs,1labour,2subrepair,3rentals,4clients ppg[8]->SetPos(50); rs->Ex("INSERT INTO srchkey ( [tableid], wordid, tabletype, client, [date] ) " "SELECT DISTINCT srchtempdict.id, srchdict.ID, srchtempdict.type, srchtempdict.client, [srchtempdict].[date] " "FROM srchdict RIGHT JOIN srchtempdict ON srchdict.word = srchtempdict.word " "WHERE (((srchdict.word) Is Not Null));"); ppg[8]->SetPos(100); PeekAndPump(); //AfxMessageBox("passed stage 6"); wait.Restore(); //final cleanup********************* ppg[9]->SetPos(1); PeekAndPump(); wait.Restore(); //Clean out the tempdict //************************************************ // TEST TO RESOLVE LOCK PROBLEM //03/09/2004 rs->Close(); rs2->Close(); //Empty temporary dictionary (should be empty anyway) rs3->Ex("DELETE srchtempdict.* FROM srchtempdict;"); ppg[9]->SetPos(12); PeekAndPump(); wait.Restore(); //Flag all indexed tables as being indexed rs->Ex("UPDATE clients SET clients.indexed = True;"); ppg[9]->SetPos(24); PeekAndPump(); wait.Restore(); rs->Ex("UPDATE probs SET probs.indexed = True;"); ppg[9]->SetPos(36); PeekAndPump(); wait.Restore(); rs->Ex("UPDATE labor SET labor.indexed = True;"); ppg[9]->SetPos(48); PeekAndPump(); wait.Restore(); //AfxMessageBox("48% done..."); rs->Ex("UPDATE subrepair SET subrepair.indexed = True;"); ppg[9]->SetPos(60); PeekAndPump(); wait.Restore(); //AfxMessageBox("60% done..."); rs->Ex("UPDATE rentals SET rentals.indexed = True;"); ppg[9]->SetPos(72); PeekAndPump(); wait.Restore(); //added may 9th 2001 for wo table rs->Ex("UPDATE wo SET wo.indexed = True;"); ppg[9]->SetPos(75); PeekAndPump(); wait.Restore(); //compact the database //close the recordsets first rs->Close(); rs2->Close(); //pConnection->Close(); //pConnection->Release(); m_pApp->rsPool->Disconnect(); GetDocument()->Compact(false);//compact and dump old copy m_pApp->rsPool->GoShared(); ppg[9]->SetPos(90); PeekAndPump(); wait.Restore(); //AfxMessageBox("90% done..."); //mark index date in the global defaults table //nice touch would be to also indicate how many unique words are //indexed //re-open the recordset to update the defaults table dtEnd=COleDateTime::GetCurrentTime(); dtsDuration=dtEnd-dtStart; fData=(float)(dtsDuration.GetTotalSeconds()/60); if(bFullIndex) { q.Format("UPDATE defaults SET defaults.lastfullindex = " "#%s#, defaults.dictsize = %u, defaults.fullindextime = %f;",dtEnd.Format(_T("%m/%d/%Y %H:%M:%S")),lUniqueWords,fData); } else { q.Format("UPDATE defaults SET defaults.lastpartindex = " "#%s#, defaults.dictsize = %u, defaults.partindextime = %f;",dtEnd.Format(_T("%m/%d/%Y %H:%M:%S")),lUniqueWords,fData); } rs->Ex(q); ppg[9]->SetPos(100); PeekAndPump(); wait.Restore(); rs->Close(); ShowIndexInfo(); wait.Restore(); CString strTemp; strTemp.Format("Index complete!\r\n%u:%u:%u (HH:MM:SS).", dtsDuration.GetHours(),dtsDuration.GetMinutes(),dtsDuration.GetSeconds()); AfxMessageBox(strTemp); } /* void CDBUtils::Index(bool bFullIndex) { CString str,strText,strWord,lchar,q,strData; long lData,lRecs,lUniqueWords; COleDateTime dtStart,dtEnd; COleDateTimeSpan dtsDuration; float fData; dtStart=COleDateTime::GetCurrentTime(); //Open exclusive CWaitCursor wait; m_strErrorLog.Empty(); ShowProgressControls(true); PeekAndPump(); wait.Restore(); //connection stuff here to avoid overhead //of using one in gzrset //create a pointer to a connection _bstr_t strSQL; //_ConnectionPtr pConnection = NULL; //instantiate it: pConnection.CreateInstance(__uuidof(Connection)); //get connect string _bstr_t strCnn(m_pApp->strConnectString); //open the connection pConnection->Open (strCnn, "", "", adConnectUnspecified); //zTrace("Start of index",false); //Empty temporary dictionary (should be empty anyway) rs->Close(); rs->Ex("DELETE srchtempdict.* FROM srchtempdict;"); //If re-indexing *ALL* then if(bFullIndex) { //Flag all tables with an indexed field to no rs->Ex("UPDATE probs SET probs.indexed = False;"); rs->Ex("UPDATE labor SET labor.indexed = False;"); rs->Ex("UPDATE subrepair SET subrepair.indexed = False;"); rs->Ex("UPDATE rentals SET rentals.indexed = False;"); rs->Ex("UPDATE clients SET clients.indexed = False;"); //Added 8/29/00 rs->Ex("UPDATE contacts SET contacts.indexed = False;"); rs->Ex("UPDATE units SET units.indexed = False;"); //Added 05/09/2001 rs->Ex("UPDATE wo SET wo.indexed = False;"); //ADD NEW ITEM HERE //Empty search keys and dictionary tables rs->Ex("DELETE srchkey.* FROM srchkey;"); rs->Ex("DELETE srchdict.* FROM srchdict;"); } else { //REMOVE STALE DATA ASSOCIATED WITH RECORDS THAT WERE INDEXED BUT ARE NOW //NOT DUE TO EDITS ETC //flag stale search keys //CLIENTS rs->Ex("UPDATE clients INNER JOIN srchkey ON clients.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=4) AND ((clients.indexed)=False));"); //LABOR rs->Ex("UPDATE srchkey INNER JOIN labor ON [srchkey].[tableid]=[labor].[id] SET srchkey.remove = True " "WHERE ((([srchkey].[tabletype])=1) And (([labor].[indexed])=False));"); //PROBS rs->Ex("UPDATE srchkey INNER JOIN probs ON srchkey.tableid = probs.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=0) AND ((probs.indexed)=False));"); //RENTALS rs->Ex("UPDATE rentals INNER JOIN srchkey ON rentals.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=3) AND ((rentals.indexed)=False));"); //SUBREPAIRS rs->Ex("UPDATE srchkey INNER JOIN subrepair ON srchkey.tableid = subrepair.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=2) AND ((subrepair.indexed)=False));"); //CONTACTS rs->Ex("UPDATE contacts INNER JOIN srchkey ON contacts.id = srchkey.tableid SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=5) AND ((contacts.indexed)=False));"); //UNITS rs->Ex("UPDATE srchkey INNER JOIN subrepair ON srchkey.tableid = subrepair.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=6) AND ((subrepair.indexed)=False));"); //Added 05/09/2001 new table workorder header is table type 7 //WORKORDER HEADERS rs->Ex("UPDATE srchkey INNER JOIN wo ON srchkey.tableid = wo.id SET srchkey.remove = True " "WHERE (((srchkey.tabletype)=7) AND ((wo.indexed)=False));"); //ADD NEW ITEM HERE AS TABLE TYPE 8 //REMOVE previous search results here rs->Ex("DELETE srch.* FROM srch;"); //remove stale search keys rs->Ex("DELETE srchkey.*, srchkey.remove " "FROM srchkey " "WHERE (((srchkey.remove)=True));"); //flag stale dictionary words rs->Ex("UPDATE srchkey RIGHT JOIN srchdict ON srchkey.wordid = srchdict.ID SET srchdict.remove = True " "WHERE (((srchkey.wordid) Is Null));"); //Remove stale dictionary words not used anymore rs->Ex("DELETE srchdict.*, srchdict.remove " "FROM srchdict " "WHERE (((srchdict.remove)=True));"); } //Loop through each table //pull out words and add each word to the temporary dictionary //with the word and the record it came from //srchkey.type: 0=probs,1labour,2subrepair,3rentals,4clients //5-contacts (client notebook) 6=units, 7=workorder headers (wo) //********************************************************* //********************************************************* //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ //'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' //zTrace("index C",false); //PROBS (table 0)* rs2->QueryReadOnly("SELECT probs.id, [brief] & \" \" & [probs].[notes] AS [text], probs.created AS idate, wo.client AS iclient " "FROM probs LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((probs.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(0); } ppg[0]->SetPos(100); PeekAndPump(); wait.Restore(); //zTrace("index D",false); //LABOUR (table 1)* rs2->QueryReadOnly("SELECT labor.id, labor.details AS [text], labor.stop AS idate, wo.client AS iclient " "FROM (labor LEFT JOIN probs ON labor.link = probs.id) LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((labor.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(1); } //AfxMessageBox("Done labour starting subrepair"); ppg[1]->SetPos(100); PeekAndPump(); wait.Restore(); //zTrace("index E",false); //SUBREPAIR (table2)* rs2->QueryReadOnly("SELECT subrepair.id, subrepair.notes AS [text], subrepair.created AS idate, wo.client AS iclient " "FROM (subrepair LEFT JOIN probs ON subrepair.link = probs.id) LEFT JOIN wo ON probs.wolink = wo.id " "WHERE (((subrepair.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(2); } //AfxMessageBox("Done subrepair, starting rentals"); ppg[2]->SetPos(100); PeekAndPump(); wait.Restore(); //RENTALS (table 3)* rs2->QueryReadOnly("SELECT rentals.id, [notes] & \" \" & [loanedto] & \" \" & [description] AS [text], rentals.dateout AS idate, rentals.clientlink AS iclient " "FROM rentals " "WHERE (((rentals.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(3); } ppg[3]->SetPos(100); PeekAndPump(); wait.Restore(); //CLIENTS (table 4)* rs2->QueryReadOnly("SELECT clients.id, clients.id AS iclient, clients.created AS idate, [generalnotes] & \" \" & " "[technotes] & \" \" & [alert] & \" \" & " "[first] & \" \" & [last] & \" \" & [company] " "& \" \" & [mailaddress] & \" \" & " "[streetaddress] & \" \" & [city] & \" \" & " "[stateprov] & \" \" & [postal] & \" \" & " "[country] & \" \" & [bizphone] & \" \" & " "[fax] & \" \" & [email] & \" \" & [acctnumber] AS [text] " "FROM clients WHERE (((clients.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(4); } ppg[4]->SetPos(100); PeekAndPump(); wait.Restore(); //CONTACTS (table 5)* rs2->QueryReadOnly( "SELECT contacts.id, contacts.notes AS [text], contacts.date AS idate, " "contacts.clientlink AS iclient FROM contacts " "WHERE (((contacts.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(5); } ppg[5]->SetPos(100); PeekAndPump(); wait.Restore(); //UNITS (table 6)* rs2->QueryReadOnly("SELECT units.id, [units].[receipt] & \" \" & [units].[sn] & \" \" & [units].[id1] & \" \" & " "[units].[id2] & \" \" & [units].[id3] & \" \" & [units].[notes] & \" \" & " "[units].[description] AS [text], units.client AS iclient, " "IIf(IsNull([units].[purchasedate]),IIf(IsNull([units].[created]), " "IIf(IsNull([units].[modified]),#1/1/2000#,[units].[modified]),[units].[created]), " "[units].[purchasedate]) AS idate " "FROM units " "WHERE (((units.indexed)=False) AND ((units.client)<>0));"); if(!rs2->IsEmpty()) { SuckWords(6); } ppg[6]->SetPos(100); PeekAndPump(); wait.Restore(); //WORKORDER HEADER (TABLE 7) added 05/09/2001 rs2->QueryReadOnly("SELECT wo.id, [wo].[notes] & \" \" & [wo].[invoice] & \" \" & [wo].[clientrefnum] & \" \" & " "[wo].[clientcontact] & \" \" & [wo].[ourref] AS [text], wo.created AS idate, wo.client AS iclient " "FROM wo " "WHERE (((wo.indexed)=False));"); if(!rs2->IsEmpty()) { SuckWords(7); } ppg[7]->SetPos(100); PeekAndPump(); wait.Restore(); //================================= //ADD new indexed items here. //To do: add wo header and woparts //================================= //Make the dictionary: Stage 6 //Pull out all the unique words from the temporary dictionary //that do *not* appear in the stop words table of words to ignore //and insert each one into the SearchDictionary, assigning //each one an id number (new method now will do this automatically?) //05/09/2001 changed progress control to 10 as 7 is now wo table //see initial update for more info rs2->QueryReadOnly("SELECT srchtempdict.word " "FROM (srchtempdict LEFT JOIN srchstopwords ON srchtempdict.word = " "srchstopwords.word) LEFT JOIN srchdict ON srchtempdict.word = srchdict.word " "WHERE (((srchstopwords.word) Is Null)) " "GROUP BY srchtempdict.word, srchdict.word;"); if(rs2->IsEmpty()) { AfxMessageBox("No data to index"); rs->Close(); rs2->Close(); return; } wait.Restore(); lUniqueWords=lRecs=rs2->FetchRecordCount(); rs2->MoveFirst(); lData=0; ppg[10]->SetRange32(0,(int)lRecs); pConnection->BeginTrans(); do{ rs2->FetchField("word",&strData); lData++; q.Format("INSERT INTO srchdict ( ID, word ) SELECT %u , \"%s\";",lData,strData); //convert the string to a bstr strSQL=q; //execute the query pConnection->Execute(strSQL, NULL, adExecuteNoRecords); }while(rs2->MoveForward()); pConnection->CommitTrans(); ppg[10]->SetPos((int)lData); PeekAndPump(); wait.Restore(); //Make keys: //match up the words and tempdictionary and insert a single match from //each record into the keys so that if the same word appears more //than once in a record, it actually only causes one entry since at //this point we don't care where in the actual record each repetition //appears, only that there is at least one in record X. //srchkey.type: 0=probs,1labour,2subrepair,3rentals,4clients ppg[8]->SetPos(50); rs->Ex("INSERT INTO srchkey ( [tableid], wordid, tabletype, client, [date] ) " "SELECT DISTINCT srchtempdict.id, srchdict.ID, srchtempdict.type, srchtempdict.client, [srchtempdict].[date] " "FROM srchdict RIGHT JOIN srchtempdict ON srchdict.word = srchtempdict.word " "WHERE (((srchdict.word) Is Not Null));"); ppg[8]->SetPos(100); PeekAndPump(); //AfxMessageBox("passed stage 6"); wait.Restore(); //final cleanup********************* ppg[9]->SetPos(1); PeekAndPump(); wait.Restore(); //Clean out the tempdict //Empty temporary dictionary (should be empty anyway) rs->Ex("DELETE srchtempdict.* FROM srchtempdict;"); ppg[9]->SetPos(12); PeekAndPump(); wait.Restore(); //Flag all indexed tables as being indexed rs->Ex("UPDATE clients SET clients.indexed = True;"); ppg[9]->SetPos(24); PeekAndPump(); wait.Restore(); rs->Ex("UPDATE probs SET probs.indexed = True;"); ppg[9]->SetPos(36); PeekAndPump(); wait.Restore(); rs->Ex("UPDATE labor SET labor.indexed = True;"); ppg[9]->SetPos(48); PeekAndPump(); wait.Restore(); //AfxMessageBox("48% done..."); rs->Ex("UPDATE subrepair SET subrepair.indexed = True;"); ppg[9]->SetPos(60); PeekAndPump(); wait.Restore(); //AfxMessageBox("60% done..."); rs->Ex("UPDATE rentals SET rentals.indexed = True;"); ppg[9]->SetPos(72); PeekAndPump(); wait.Restore(); //added may 9th 2001 for wo table rs->Ex("UPDATE wo SET wo.indexed = True;"); ppg[9]->SetPos(75); PeekAndPump(); wait.Restore(); //compact the database //close the recordsets first rs->Close(); rs2->Close(); pConnection->Close(); //pConnection->Release(); m_pApp->rsPool->Disconnect(); GetDocument()->Compact(false);//compact and dump old copy m_pApp->rsPool->GoShared(); ppg[9]->SetPos(90); PeekAndPump(); wait.Restore(); //AfxMessageBox("90% done..."); //mark index date in the global defaults table //nice touch would be to also indicate how many unique words are //indexed //re-open the recordset to update the defaults table dtEnd=COleDateTime::GetCurrentTime(); dtsDuration=dtEnd-dtStart; fData=(float)(dtsDuration.GetTotalSeconds()/60); if(bFullIndex) { q.Format("UPDATE defaults SET defaults.lastfullindex = " "#%s#, defaults.dictsize = %u, defaults.fullindextime = %f;",dtEnd.Format(_T("%m/%d/%Y %H:%M:%S")),lUniqueWords,fData); } else { q.Format("UPDATE defaults SET defaults.lastpartindex = " "#%s#, defaults.dictsize = %u, defaults.partindextime = %f;",dtEnd.Format(_T("%m/%d/%Y %H:%M:%S")),lUniqueWords,fData); } rs->Ex(q); ppg[9]->SetPos(100); PeekAndPump(); wait.Restore(); rs->Close(); ShowIndexInfo(); wait.Restore(); AfxMessageBox("Index complete!"); } */ void CDBUtils::ShowProgressControls(bool bShow) { BOOL show = bShow ? TRUE : FALSE; m_pg1.ShowWindow(show); m_st1.ShowWindow(show); m_pg2.ShowWindow(show); m_st2.ShowWindow(show); m_pg3.ShowWindow(show); m_st3.ShowWindow(show); m_pg4.ShowWindow(show); m_st4.ShowWindow(show); m_pg5.ShowWindow(show); m_st5.ShowWindow(show); m_pg6.ShowWindow(show); m_st6.ShowWindow(show); m_pg7.ShowWindow(show); m_st7.ShowWindow(show); m_st8.ShowWindow(show); m_pg8.ShowWindow(show); m_st9.ShowWindow(show); m_pg9.ShowWindow(show); m_st10.ShowWindow(show); m_pg10.ShowWindow(show); m_st11.ShowWindow(show); m_pg11.ShowWindow(show); for(int x=0;x<11;x++) ppg[x]->SetPos(0); } BOOL CDBUtils::PeekAndPump() { static MSG msg; while (::PeekMessage(&msg,NULL,0,0,PM_NOREMOVE)) { if (!AfxGetApp()->PumpMessage()) { ::PostQuitMessage(0); return FALSE; } } return TRUE; } long CDBUtils::FindMaxChar() { long lBiggest=0; int x; CString strData; rs2->MoveFirst(); do{ rs2->FetchField("text",&strData); x=strData.GetLength(); if(x>lBiggest) lBiggest=x; }while(rs2->MoveForward()); rs2->MoveFirst(); return lBiggest; } //suck the words out of the table in rs2 bool CDBUtils::SuckWords(int nTable) { CString str,strText,strWord,q,strDate,temp; //register int lchar; int nPos; long lID; //long lBiggest; long lClient; COleDateTime dtData; //Aug 6 2004 changes //char ch; TCHAR ch; //progress variables //float currec,recs; long currec,recs; //v1.9.4.5 re-wrote much of the code below //Aug 6th 2004 Replaced CStringList with CMapStringToString to //aid in ensuring no duplicates here and no stop words //as the real bottleneck is the insert sql command, not //anything here CMapStringToString ssWords; CMapStringToString StopWords; StopWords.SetAt("about",0); StopWords.SetAt("after",0); StopWords.SetAt("all",0); StopWords.SetAt("also",0); StopWords.SetAt("an",0); StopWords.SetAt("and",0); StopWords.SetAt("another",0); StopWords.SetAt("any",0); StopWords.SetAt("are",0); StopWords.SetAt("as",0); StopWords.SetAt("at",0); StopWords.SetAt("be",0); StopWords.SetAt("because",0); StopWords.SetAt("been",0); StopWords.SetAt("before",0); StopWords.SetAt("being",0); StopWords.SetAt("between",0); StopWords.SetAt("both",0); StopWords.SetAt("but",0); StopWords.SetAt("by",0); StopWords.SetAt("came",0); StopWords.SetAt("can",0); StopWords.SetAt("come",0); StopWords.SetAt("could",0); StopWords.SetAt("did",0); StopWords.SetAt("do",0); StopWords.SetAt("does",0); StopWords.SetAt("each",0); StopWords.SetAt("else",0); StopWords.SetAt("for",0); StopWords.SetAt("from",0); StopWords.SetAt("get",0); StopWords.SetAt("got",0); StopWords.SetAt("had",0); StopWords.SetAt("has",0); StopWords.SetAt("have",0); StopWords.SetAt("he",0); StopWords.SetAt("her",0); StopWords.SetAt("here",0); StopWords.SetAt("him",0); StopWords.SetAt("himself",0); StopWords.SetAt("his",0); StopWords.SetAt("how",0); StopWords.SetAt("if",0); StopWords.SetAt("in",0); StopWords.SetAt("into",0); StopWords.SetAt("is",0); StopWords.SetAt("it",0); StopWords.SetAt("its",0); StopWords.SetAt("just",0); StopWords.SetAt("like",0); StopWords.SetAt("make",0); StopWords.SetAt("many",0); StopWords.SetAt("me",0); StopWords.SetAt("might",0); StopWords.SetAt("more",0); StopWords.SetAt("most",0); StopWords.SetAt("much",0); StopWords.SetAt("must",0); StopWords.SetAt("my",0); StopWords.SetAt("never",0); StopWords.SetAt("now",0); StopWords.SetAt("of",0); StopWords.SetAt("on",0); StopWords.SetAt("only",0); StopWords.SetAt("or",0); StopWords.SetAt("other",0); StopWords.SetAt("our",0); StopWords.SetAt("out",0); StopWords.SetAt("over",0); StopWords.SetAt("re",0); StopWords.SetAt("said",0); StopWords.SetAt("same",0); StopWords.SetAt("see",0); StopWords.SetAt("should",0); StopWords.SetAt("since",0); StopWords.SetAt("so",0); StopWords.SetAt("some",0); StopWords.SetAt("still",0); StopWords.SetAt("such",0); StopWords.SetAt("take",0); StopWords.SetAt("than",0); StopWords.SetAt("that",0); StopWords.SetAt("the",0); StopWords.SetAt("their",0); StopWords.SetAt("them",0); StopWords.SetAt("then",0); StopWords.SetAt("there",0); StopWords.SetAt("these",0); StopWords.SetAt("they",0); StopWords.SetAt("this",0); StopWords.SetAt("those",0); StopWords.SetAt("through",0); StopWords.SetAt("to",0); StopWords.SetAt("too",0); StopWords.SetAt("under",0); StopWords.SetAt("up",0); StopWords.SetAt("use",0); StopWords.SetAt("very",0); StopWords.SetAt("want",0); StopWords.SetAt("was",0); StopWords.SetAt("way",0); StopWords.SetAt("we",0); StopWords.SetAt("well",0); StopWords.SetAt("were",0); StopWords.SetAt("what",0); StopWords.SetAt("when",0); StopWords.SetAt("where",0); StopWords.SetAt("which",0); StopWords.SetAt("while",0); StopWords.SetAt("who",0); StopWords.SetAt("will",0); StopWords.SetAt("with",0); StopWords.SetAt("would",0); StopWords.SetAt("you",0); StopWords.SetAt("your",0); //hand chosen items StopWords.SetAt("ll",0); int nWords; _bstr_t strSQL; int nLength; CWaitCursor wait; //Commented out Aug 4th 2004, //what's the point really? //lBiggest=FindMaxChar(); ////zTrace("Suck C",false); ////don't waste time on an empty table //if(lBiggest< 3) //{ // // return true; // //} //pnTable is actually supposed to be an unsigned char //but there doesn't seem to be a good CString::Format() //for that ASSERT(nTable>-1 && nTable < 256); recs=rs2->FetchRecordCount(); currec=0; strText.Empty(); strWord.Empty(); nPos=0; nLength=0; //03/09/2003 changed to 100 //to fix problem where it would show as incomplete when done ppg[nTable]->SetRange32(0,100);//(int)recs); ppg[nTable]->SetPos(0); do { currec++; //TEST 03/09/2004 to put back user feedback /*if(currec % 500 == 0) { ppg[nTable]->SetPos(int(currec/recs*100)); PeekAndPump(); wait.Restore(); }*/ //rs2->FetchField("text",&strText); //Updated 1.9.4.6 09-May-2005 to fix problem with //total amount of text exceeding 255 characters rs2->FetchAllTextFieldsAsOneString(&strText); strText.MakeLower(); //make all lower case rs2->FetchField("id",&lID); rs2->FetchField("iclient",&lClient); rs2->FetchField("idate",&dtData); strDate=dtData.Format(_T("%m/%d/%Y")); if(strDate.IsEmpty()) { dtData=COleDateTime::GetCurrentTime(); switch(nTable) { case 0: temp="PROBLEMS"; break; case 1: temp="LABOUR"; break; case 2: temp="SUBREPAIRS"; break; case 3: temp="RENTALS"; break; case 4: temp="CLIENTS"; break; case 5: temp="CONTACTS"; break; case 6: temp="UNITS"; break; } strDate.Format( "During indexing on %s while parsing records an error occured:\r\n" "An internal date is missing from the following record\r\n" "Table:%s, Record:%u\r\n" "To keep things rolling, todays date was substituted instead\r\n" "Consequences: This record will show as being created today in a search\r\n" "although it was probably created at an earlier date. \r\n" "Otherwise, you should be able to work as normal.\r\n" "Please inform tech support with the details of this message.\r\n" "=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-\r\n" ,dtData.Format(_T("%m/%d/%Y %H:%M:%S")),temp,lID); LogError(strDate); //strDate=dtData.Format(VAR_DATEVALUEONLY); strDate=dtData.Format(_T("%m/%d/%Y")); } //zTrace("Suck G",false); //make sure there is something to parse nLength=strText.GetLength(); //PROCESS BLOCK OF TEXT int nWordLength=0; if (nLength > 1) { strWord.Empty(); ssWords.RemoveAll(); nWords=0; //loop through all characters in strText for(nPos=0;nPos < nLength;nPos++) { ch=strText.GetAt(nPos); if( (/*IsAlpha*/ch>=97 && ch<=122) || (/*IsDigit*/ ch >='0' && ch<='9') ) { strWord+=ch; nWordLength++; } else if(strWord!="")//is a non-regular text character { if(nWordLength>1)//greater than one character { if(!StopWords.Lookup(strWord,temp)) ssWords.SetAt(strWord,0); } strWord.Empty(); nWordLength=0; }//end of else for a non regular character }//lPos loop //Manually add last word if(strWord!="") { if(nWordLength>50) strWord=strWord.Left(50); if(nWordLength>1) { if(!StopWords.Lookup(strWord,temp)) ssWords.SetAt(strWord,"0"); } } //SAVE all Words rs->pTheConnection->BeginTrans(); POSITION pos = ssWords.GetStartPosition( ); while( pos != NULL ) { ssWords.GetNextAssoc( pos, strWord, temp ); q.Format("INSERT INTO srchtempdict ( word, id, type, client, [date] ) " "SELECT '%s' , %u , %i, %u, #%s#;",strWord,lID,nTable,lClient, strDate); rs->Ex(q); } rs->pTheConnection->CommitTrans(); }//END PROCESS BLOCK OF TEXT /* ORIGINAL (PRE AUG 6 2004) PROCESS BEFORE ATTEMPTED OPTIMIZATION //PROCESS BLOCK OF TEXT if (nLength > 1) { strWord.Empty(); slWords.RemoveAll(); nWords=0; slWords.AddHead(".");//to save overhead of checking if first inside loop //zTrace("Suck H",false); //loop through all characters in strText for(nPos=0;nPos < nLength;nPos++) { ch=strText.GetAt(nPos); if(isalnum(ch)) strWord+=ch; else//is a non-regular text character { slWords.AddTail(strWord); nWords++; strWord.Empty(); }//end of else for a non regular character }//lPos loop //have to add the very last strWord in manually, this may not really be necessary //but does not hurt as all duplicates are purged anyway later on in the process slWords.AddTail(strWord); nWords++; //zTrace("Suck I",false); //SAVE all Words rs->pTheConnection->BeginTrans(); for(int x=1;x 1 )//changed 12/19/00 from 2 letters to 1 letters { if(strWord.GetLength()>50) strWord=strWord.Left(50);//added 07/06/2001 because db wordsize is only 50 q.Format("INSERT INTO srchtempdict ( word, id, type, client, [date] ) " "SELECT \"%s\" , %u , %i, %u, #%s#;",strWord,lID,nTable,lClient,dtData.Format(_T("%m/%d/%Y"))); //_T("%m/%d/%Y %H:%M:%S") rs->Ex(q); } } rs->pTheConnection->CommitTrans(); //zTrace("Suck J",false); }//END PROCESS BLOCK OF TEXT */ }while(rs2->MoveForward());// && currec < CUTOFF); //ppg[nTable]->SetPos(100); //PeekAndPump(); //wait.Restore(); return true; } void CDBUtils::ShowIndexInfo() { CString strData,txt; long lData; float fData; COleDateTime dtData; rs->Query("SELECT defaults.* FROM defaults;"); rs->FetchField("lastpartindex",&dtData); rs->FetchField("partindextime",&fData); if(dtData.GetYear()==1968)//no record yet { txt="Partial index has not yet been run."; } else { txt.Format("Last partial index: %s took %.2f minutes to complete.",dtData.Format(_T("%m/%d/%Y %H:%M:%S")),fData); } m_lblPartialInfo.SetWindowText(txt); txt.Empty(); rs->FetchField("lastfullindex",&dtData); rs->FetchField("fullindextime",&fData); if(dtData.GetYear()==1968)//no record yet { txt="Full index has not yet been run."; } else { txt.Format("Last full index: %s took %.2f minutes to complete.",dtData.Format(_T("%m/%d/%Y %H:%M:%S")),fData); } m_lblFullInfo.SetWindowText(txt); txt.Empty(); rs->FetchField("dictsize",&lData); txt.Format("Total unique searchable words: %u",lData); m_lblWordCount.SetWindowText(txt); rs->Close(); } void CDBUtils::OnRButtonDblClk(UINT nFlags, CPoint point) { bool PreEval; CString strData; //check if going from unregistered to registered //if so, erase all data now automatically if(m_pApp->m_uiFeatures&LICENSE_REGISTERED) PreEval=false; else PreEval=true; if(m_pApp->m_lusrID!=1) { AfxMessageBox("You must log in using the manager account\r\n" "to perform this action"); return;//only the manager! } CKD d; d.DoModal(); //check and see if were now unregistered if(PreEval) { //lookup regto name //if not "Evaluation" then erase data rs->Query("SELECT regto FROM defaults;"); rs->FetchField("regto",&strData); rs->Close(); if(strData!="Evaluation" && strData!="AyaNova Evaluation") { if(AfxMessageBox("*** READ CAREFULLY ***\r\n\r\n" "All data in the AyaNova database is about to be erased.\r\n" "This will remove all the sample data and any data you have entered\r\n" "while evaluating AyaNova so that you can start with a fresh database.\r\n\r\n" "It is recommended that you answer yes to erase the data.\r\n\r\n" "Erase the AyaNova database?",MB_YESNO)==IDYES) { EraseAll(); AfxMessageBox("Close and restart AyaNova now"); } else { AfxMessageBox("The data will not be erased.\r\n\r\n" "You can erase it later using the\r\n" "erase all data button on the database utilities screen.\r\n\r\n" "All technicians in the trial database will now be set to inactive\r\n" "to ensure that you will not be locked out of the program when you restart it.\r\n"); GZK k; CString a,b,strTemp; bool bValue=false; /* SELECT users.active, users.a, users.b FROM users WHERE (((users.id)<>1) AND ((users.tech)=True) AND ((users.active)=True)); */ if(!rs->Query(k.InLineDecrypt("A38sl+nbfd//IE2wby+SBMb8KnIh47GwGTMGXdofhDKwwdw2ui69FDkyDMaJsKxSKAPJ00vU" "KPXl4BOk4qFk+7lURE/y7g/NVRVb1TgRUGLFdtnAPyaQa26Q882oAkJnmZCQ9b5jBm1W4TUy" "5lmFLCDBYrQke0n9yeSogzoeLHdHvfntlbYwBAds6gckYs/M"))) { /* Unable to set technicians to inactive Contact tech support */ AfxMessageBox(k.InLineDecrypt("O5i0JrVLzlAwwEkvQIYCzr3YiwN0XqwuAu2j5geep7lPwJxQ0J1Jv7V/gy6XNK9N4LwHMUqC" "c6cijWvlEjdYXA==")); } do{ //LOOP through all active tech users who are not manager account //read in 'a' field rs->FetchField(k.InLineDecrypt("zpiZm0o4SPSHizSP27V8lg"),&a); //decrypt k.GZDecrypt(&a,false); //replace rightmost string "TRUE" with "FALSE" //"TRUETRUE", "TRUEFALSE" a.Replace(k.InLineDecrypt("nOmVnvypPUdu0dKmUO4Zuw"),k.InLineDecrypt("bMctUK0utAKMdgo8T9s4bQ")); //calc a hash of it, b=a; k.GZHash(&b); //re-encrypt a field k.GZEncrypt(&a,false); //write 'a' back, write hash to b field, set active to false rs->UpdateField(k.InLineDecrypt("zpiZm0o4SPSHizSP27V8lg"),&a); rs->UpdateField(k.InLineDecrypt("lIgbn+v0h55FcZSl6rhR4A"),&b); rs->UpdateField(k.InLineDecrypt("67gzOWhzGhgW7mlFH6aQfA"),&bValue); //LOOP }while(rs->MoveForward()); AfxMessageBox("Close and restart AyaNova now"); } } } } //************************************************************* //************************************************************* //************************************************************* //************************************************************* //************************************************************* //************************************************************* //************************************************************* void CDBUtils::OnBtncm3() { CString q,strData,strWOID,strOriginalID,str; long lData,lLink,lTechID,recs,currec; COleDateTime dtData,dtTime,dtDate,dtStart,dtStop; float fData; bool bData,bMissingClient=false; int pct=0; m_pg1.ShowWindow(TRUE); m_pg1.SetPos(0); AfxMessageBox("Before proceeding ensure you have\r\n" "the following tables linked in from CM3:\r\n" "Calls, Customers, Techs, Type of call"); if(AfxMessageBox("Ready?",MB_YESNO)==IDNO) return; CWaitCursor wait; //********* IMPORT TABLES FIRST ************** //These will only import records that do not exist //not duplicates will be created //CLIENTS rs->Ex("INSERT INTO clients ( company ) " "SELECT Customers.[Customer Name] " "FROM Customers LEFT JOIN clients ON Customers.[Customer Name] = clients.company " "WHERE (((clients.company) Is Null));"); //TECHS rs->Ex("INSERT INTO users ( [first], [last], initials, active, login, pass, tech ) " "SELECT \"IMPORTED\" AS Expr4, Techs.Technician, Techs.[Tech Code Abbreviation], False AS Expr1, \"IMPORTED\" AS Expr2, \"IMPORTED\" AS Expr3, True AS Expr5 " "FROM Techs LEFT JOIN users ON Techs.[Tech Code Abbreviation] = users.initials " "WHERE (((users.initials) Is Null));"); //RATES rs->Ex("INSERT INTO rates ( name, rate, active, travelrate ) " "SELECT [Type of Call].Description, [Type of Call].HourlyWork, [Type of Call].Active, False AS typerate " "FROM [Type of Call] LEFT JOIN rates ON [Type of Call].Description = rates.name " "WHERE (((rates.name) Is Null));"); //************** import workorders ************** //trickier operation, can only be done once? rs->Query("SELECT Calls.[Master Invoice Number], Calls.Customer, Calls.Description, Calls.[Billable Hours], Calls.Date, clients.id AS clientid, users.id AS techid, Calls.[Arrival Time], Calls.[Departure Time], Calls.[Billing Invoice Number], Calls.[Travel hours], rates.id AS rateid " "FROM rates RIGHT JOIN (((Calls LEFT JOIN clients ON Calls.Customer = clients.company) LEFT JOIN users ON Calls.Technician = users.last) LEFT JOIN [Type of Call] ON Calls.[Call type] = [Type of Call].ID) ON rates.name = [Type of Call].Description;"); if(!rs->IsEmpty()) { currec=0; recs=rs->FetchRecordCount(); m_pg1.SetRange32(0,(int)recs); rs->MoveFirst(); do{//************ SEE SIMPLE WO TO SAVE TIME THIS MORNING!! //create a workorder header record flagged as quick wo //keep message queue flowing currec++; //pct=(int)((float)(currec/recs)*100); //pct=(int)(((float)currec/(float)recs)*100); m_pg1.SetPos(currec); PeekAndPump(); wait.Restore(); /* if(currec== 150) if(AfxMessageBox("150 - Stop now?",MB_YESNO)==IDYES) return; if(currec== 300) if(AfxMessageBox("300 - Stop now?",MB_YESNO)==IDYES) return; */ bMissingClient=false; //FETCH AND SET VALUES FOR LATER USAGE //GET TECH FOR LATER*********************************************** rs->FetchField("techid",&lTechID); //keep the date for later on processing rs->FetchField("Date",&dtDate); //GET START DATE/TIME rs->FetchField("Arrival Time",&dtTime); rs->FetchField("Date",&dtDate); dtStart.SetDateTime(dtDate.GetYear(),dtDate.GetMonth(),dtDate.GetDay(),dtTime.GetHour(),dtTime.GetMinute(),dtTime.GetSecond()); //GET STOP DATE TIME rs->FetchField("Departure Time",&dtTime); dtStop.SetDateTime(dtDate.GetYear(),dtDate.GetMonth(),dtDate.GetDay(),dtTime.GetHour(),dtTime.GetMinute(),dtTime.GetSecond()); //start a new workorder: //open the workorder table with a query guaranteed to //return no records as this is probably better performance rs2->Query("SELECT wo.* FROM wo WHERE (((wo.id)=0));");// //now add the new record rs2->AddNewRecord(); rs2->UpdateField("creator",&lTechID); COleDateTime dtData; dtData=COleDateTime::GetCurrentTime(); rs2->UpdateField("created",&dtDate); rs2->SaveRecord(); //now go back and find the record just created to get the id number //by using some unique variables for the query q.Format("SELECT wo.* FROM wo WHERE (((wo.creator)=%u) " "AND ((wo.created)=#%s#) AND ((wo.client)=0));",lTechID,dtDate.Format(_T("%m/%d/%Y"))); rs2->Query(q); rs2->FetchField("id",&lData); //save the workorder ID number strWOID.Format("%u",lData); //CLIENT rs->FetchField("clientid",&lData); if(lData==0) bMissingClient=true; rs2->UpdateField("client",&lData); //CATEGORY lData=0; rs2->UpdateField("type",&lData); //CLOSED - time workorder closed (now) rs2->UpdateField("closed",&dtDate); //ONSITE bData= true;//TREAT all as onsite regardless rs2->UpdateField("onsite",&bData); //STARTTIME rs->FetchField("Arrival Time",&dtData); rs2->UpdateField("starttime",&dtData); //STOPTIME rs->FetchField("Departure Time",&dtData); rs2->UpdateField("stoptime",&dtData); //QUICK - flag this as a quickie workorder //so that it gets displayed on this screen //when selected to view bData=true; rs2->UpdateField("quick",&bData); //INVOICE # rs->FetchField("Billing Invoice Number",&strData); rs2->UpdateField("invoice",&strData); rs2->SaveRecord(); //Create a problem record //open the probs table, return no records rs2->Query("SELECT probs.* FROM probs WHERE (((probs.id)=0));"); rs2->AddNewRecord(); //SAVE THE WORKORDER ID NUMBER rs2->UpdateField("wolink",&strWOID); //STATUS to zero lData=0; rs2->UpdateField("status",&lData); //CREATOR rs2->UpdateField("creator",&lTechID); //Save problem record rs2->SaveRecord(); //get id of problem record q.Format("SELECT probs.id FROM probs " "WHERE (((probs.wolink)=%s) AND " "((probs.status)=0) AND " "((probs.creator)=%u));",strWOID,lTechID); rs2->Query(q); lLink=0; rs2->FetchField("id",&lLink); ASSERT(lLink!=0); //************************************ //************************************ //Use id to create a labour table record //firstly open the labor table in a way that returns no records rs2->Query("SELECT labor.* FROM labor WHERE (((labor.link)=0));"); rs2->AddNewRecord(); //set labour record fields //LINK TO PROBLEM RECORD rs2->UpdateField("link",&lLink); //TECH rs2->UpdateField("tech",&lTechID); //HOURS rs->FetchField("Billable Hours",&fData); rs2->UpdateField("hours",&fData); //NOCHARGE HOURS fData=0; rs2->UpdateField("nchours",&fData); //TRAVEL HOURS rs->FetchField("Travel hours",&fData); rs2->UpdateField("travhours",&fData); //RATE rs->FetchField("rateid",&lData); rs2->UpdateField("rate",&lData); //TRAVEL RATE rs->FetchField("rateid",&lData);//BUG BUG CHANGE FOR OTHERS WE DONT USE TRAVEL //this is a lazy avoidance of figuring out the travel rate. rs2->UpdateField("travrate",&lData); //START rs2->UpdateField("start",&dtStart); //STOP rs2->UpdateField("stop",&dtStop); //DETAILS rs->FetchField("Master Invoice Number",&strOriginalID); rs->FetchField("Description",&strData); strData="< Original workorder #: " + strOriginalID + " >\r\n" + strData; if(bMissingClient) { rs->FetchField("Customer",&str); strData+="MISSING CUSTOMER DURING IMPORT! - WAS:" + str + "\r\n"; } rs2->UpdateField("details",&strData); rs2->SaveRecord(); }while(rs->MoveForward()); AfxMessageBox("Finished"); }//not rs empty rs->Close(); rs2->Close(); } void CDBUtils::ShowMe(CString txt) { CTED d; d.m_strText=txt; d.DoModal(); } void CDBUtils::zTrace(CString msg,bool bShow) { if(TRACING==1) { if(bShow) ShowMe(msg); else AfxMessageBox(msg); } } void CDBUtils::LogError(CString strError) { m_strErrorLog+=strError+"\r\n"; } void CDBUtils::SetRights() { int x=m_pApp->Allowed(RDBUTIL,true); if(x==1) return;//full access //default is read only m_btnCM3.ShowWindow(FALSE); m_btnCompact.ShowWindow(FALSE); m_btnDefaults.ShowWindow(FALSE); m_btnIndexAll.ShowWindow(FALSE); m_btnQuickIndex.ShowWindow(FALSE); } void CDBUtils::OnBtndeleteall() { if(AfxMessageBox( "Warning: you are about to completely erase\r\n" "ALL data. This operation can *not* be undone.\r\n" "If you want to keep the current data \r\n" "make a backup outside AyaNova first.\r\n\r\n" "Do you wish to proceed?",MB_YESNO)==IDYES) { if(AfxMessageBox("Are you certain you want to completely erase all data?",MB_YESNO)==IDYES) EraseAll(); } } void CDBUtils::EraseAll() { //Attempt to go Exclusive if(!m_pApp->rsPool->GoExclusive()) { AfxMessageBox("In order to protect the integrity of your data\r\n" "you need exclusive access to the database to access this function.\r\n" "\r\nAll other users must exit before proceeding."); //back to shared mode m_pApp->rsPool->GoShared(); return; } //Ok, everyone is out, go shared m_pApp->rsPool->GoShared(); rs->Close(); rs->Ex("DELETE clients.* FROM clients;"); rs->Ex("DELETE contacts.* FROM contacts;"); rs->Ex("DELETE contracts.* FROM contracts;"); rs->Ex("DELETE groups.*, groups.id FROM groups WHERE (((groups.id)<>1));"); rs->Ex("DELETE labor.* FROM labor;"); rs->Ex("DELETE mail.* FROM mail;"); rs->Ex("DELETE mailroute.* FROM mailroute;"); rs->Ex("DELETE nonclients.* FROM nonclients;"); rs->Ex("DELETE parts.* FROM parts;"); rs->Ex("DELETE pmparts.* FROM pmparts;"); rs->Ex("DELETE pmhead.* FROM pmhead;"); rs->Ex("DELETE pmitems.* FROM pmitems;"); rs->Ex("DELETE probs.* FROM probs;"); //rs->Ex("DELETE probstat.* FROM probstat;"); rs->Ex("DELETE projects.* FROM projects;"); rs->Ex("DELETE rentals.* FROM rentals;"); rs->Ex("DELETE rates.* FROM rates;"); rs->Ex("DELETE rptsusers.* FROM rptsusers;"); rs->Ex("DELETE labor.* FROM labor;"); rs->Ex("DELETE srch.* FROM srch;"); rs->Ex("DELETE srchdict.* FROM srchdict;"); rs->Ex("DELETE srchkey.* FROM srchkey;"); rs->Ex("DELETE srchtempdict.* FROM srchtempdict;"); rs->Ex("DELETE statusviews.*, statusviews.viewname FROM statusviews WHERE (((statusviews.viewname)<>\"< default >\"));"); rs->Ex("DELETE subrepair.* FROM subrepair;"); rs->Ex("DELETE tasks.* FROM tasks;"); rs->Ex("DELETE unitmodelcats.* FROM unitmodelcats;"); rs->Ex("DELETE unitmodels.* FROM unitmodels;"); rs->Ex("DELETE units.* FROM units;"); rs->Ex("DELETE users.*, users.id FROM users WHERE (((users.id)<>1));"); rs->Ex("DELETE wo.* FROM wo;"); rs->Ex("DELETE woparts.* FROM woparts;"); rs->Ex("DELETE wotypes.* FROM wotypes;"); rs->Ex("DELETE zones.* FROM zones;"); //Added 09/18/2001 rs->Ex("DELETE schdets.* FROM schdets;"); rs->Ex("DELETE schdgrps.* FROM schdgrps;"); rs->Ex("DELETE schedmarkers.* FROM schedmarkers;"); //------------------------------------------------- //reset manager password to login manager pw: letmein rs->Ex("UPDATE users SET users.login = \"3029163104\", users.pass = \"1901781427\" " "WHERE (((users.id)=1));"); //Added 08/27/2001 rs->Ex("INSERT INTO zones ( name ) SELECT \"Default zone\";"); rs->Ex("INSERT INTO clients ( company ) SELECT \"Default client\";"); rs->Ex("INSERT INTO rates ( name, rate, cost, expires, travelrate, partnum ) " "SELECT \"Default rate\", 1,1, #1/1/3000#, False, 1;"); rs->Ex("INSERT INTO rates ( name, rate, cost, expires, travelrate, partnum ) " "SELECT \"Default travel rate\", 1,1, #1/1/3000#,True, 1;"); rs->Close(); m_pApp->rsPool->GoExclusive(); m_pApp->rsPool->Disconnect(); GetDocument()->Compact(false);//compact and keep backup copy rs->m_bExclusiveConnection=false; //rs->Close(); //Ok, everyone is out, go shared m_pApp->rsPool->GoShared(); /*AfxMessageBox("Finished"); //compact GetDocument()->Compact(false);//compact and dont keep backup copy */ AfxMessageBox("Erase complete.\r\nNote: the manager account was set back to the default\r\n" "login name which is: \"manager\"\r\nand the default password which is: \"letmein\"\r\n\r\nAyaNova will now close."); PostQuitMessage(-1); } //FUTURE READER keywords to find this method //update database schema 171 1.9 scdata.sc ayanova ce //etc etc etc void CDBUtils::UpdateDatabaseSchema() { int nVersion; CString msg,strTemp,strData; //long lData; CString q,q2; COleDateTime dtDefault; dtDefault.SetDate(1968,03,12); nVersion=atoi(m_pApp->m_strDataVersion); bool buptodate=false; m_bBootScanDone=true;//dont try to do both at once bool bUpdateRanOK; //do whatever updates are necessary. while (!buptodate) { switch (nVersion) { //================================================== case 126://changed to 127 on 8/22/00 { //Added a record to the rptsmaster table for the //workorder dispatch report //Not a schema update only an added record //see if the record is here already so it's not done twice: rs->Query("SELECT rptsmaster.virtualname " "FROM rptsmaster WHERE (((rptsmaster.virtualname)=\"Workorder dispatch\"));"); if(rs->IsEmpty()) { rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Workorder dispatch\", \"wodispst.rpt\", \"wodispatch\", False, 32767, 21;"); } //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"127\";"); nVersion=127; } break; //====================================================== case 127://changed to 128 on 8/24/00 { //Added a record to the rptsmaster table for the //QUICK workorder dispatch report //Not a schema update only an added record //see if the record is here already so it's not done twice: rs->Query("SELECT rptsmaster.virtualname " "FROM rptsmaster WHERE (((rptsmaster.virtualname)=\"Workorder dispatch (Quick)\"));"); if(rs->IsEmpty()) { rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Workorder dispatch (Quick)\", \"wodispqu.rpt\", \"wodispatch\", False, 32767, 22;"); } //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"128\";"); nVersion=128; } break; //===================================================== case 128://changed to 129 on 8/28/00 { //Dropped contacts table fields: wolink, problink //added fields: clientlink rs->Ex("ALTER TABLE contacts DROP COLUMN wolink;"); rs->Ex("ALTER TABLE contacts DROP COLUMN problink;"); rs->Ex("ALTER TABLE contacts ADD COLUMN clientlink LONG;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"129\";"); nVersion=129; } break; case 129://changed to 130 on 8/29/00 - 8/31/00 { //contacts table added field:indexed //units table added field:indexed rs->Ex("ALTER TABLE contacts ADD COLUMN indexed YESNO;"); rs->Ex("UPDATE contacts SET contacts.indexed = False;"); rs->Ex("ALTER TABLE units ADD COLUMN indexed YESNO;"); rs->Ex("UPDATE units SET units.indexed = False;"); //add the unit history to reports screen q2="SELECT \"user\" AS zCurrentUser, probs.id, Format([start],\"Short Date\") AS " "servdate, labor.details, IIf(IsNull([company]),[clients]![last] & \", \" & [clients]![first],[company]) " "AS clientcompany, units.sn, unitmodels.model, users.initials, probs.meter, ztotalparts.totalparts, " "ztotallabor.totallabor " "FROM [SELECT Sum((labor.hours*rates.rate)+(labor.travhours*travrates.rate)) AS totallabor, " "probs.id FROM probs INNER JOIN (rates INNER JOIN (rates AS travrates INNER JOIN labor ON " "travrates.id = labor.rate) ON rates.id = labor.rate) ON probs.id = labor.link GROUP BY probs.id]. AS " "ztotallabor RIGHT JOIN ([SELECT IIf(IsNull(Sum(woparts.quantity*woparts.price)),0, " "Sum(woparts.quantity*woparts.price)) AS totalparts, probs.id FROM probs LEFT JOIN woparts " "ON probs.id = woparts.link GROUP BY probs.id]. AS ztotalparts RIGHT JOIN (users RIGHT JOIN " "((labor RIGHT JOIN (((wo RIGHT JOIN probs ON wo.id = probs.wolink) LEFT JOIN units ON " "probs.unit = units.id) LEFT JOIN unitmodels ON units.model = unitmodels.id) ON labor.link = " "probs.id) LEFT JOIN clients ON wo.client = clients.id) ON users.id = labor.tech) ON ztotalparts.id " "= probs.id) ON ztotallabor.id = probs.id " "WHERE (((probs.unit)~UNIT) AND ((units.sn) Is Not Null) AND ((labor.start) Between #~STRT# And #~END_#)) " "ORDER BY labor.start DESC;"; q.Format("UPDATE rptsmaster SET rptsmaster.x = True, rptsmaster.criteriafields = 400, rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=7));",q2); rs->Ex(q); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"130\";"); nVersion=130; } break; //===================================================== case 130://changed to 131 on 9/12/00 { //PM module additions rs->Ex("ALTER TABLE pmschedules ADD COLUMN autoworkorder YESNO;"); rs->Ex("UPDATE pmschedules SET pmschedules.autoworkorder = False;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"131\";"); nVersion=131; } break; //*************************************************************************** case 131://changed to 132 on 9/22/00 and now 133 on 10/02/00 { //since it's unreleased, decided to bump up one more. //PM module additions //Add a last meter reading column to the units table //this is updated when someone enters a workorder unit count. //to make pm easier to deal with. rs->Ex("ALTER TABLE units ADD COLUMN lastmeter INTEGER;"); //NOTE: CANT SET TO DEFAULT OF ZERO WITHOUT IT CRASHING OUT //Delete the pmschedules, superseded by pmhead table below rs->Ex("DROP TABLE pmschedules;"); //new pm header table q.Format("CREATE TABLE pmhead (" "id COUNTER CONSTRAINT PK_pmhead PRIMARY KEY, " "description TEXT(50), " "notes MEMO, " "link INTEGER DEFAULT 0, "//link to client or unit id number "type INTEGER DEFAULT 0, " //0-timebased,1-meter,2-agebased "isclient YESNO DEFAULT False, " //true = client false=unitbased "ismodel YESNO DEFAULT False, " //true = MODEL false=units or clients "autowo YESNO DEFAULT False, " "autorpt YESNO DEFAULT False, " "dow INTEGER DEFAULT 0," //autoschedule day of week 0any 1-monday 2-tuesd etc "tech INTEGER DEFAULT 0, " //HEREpreferred technician "woconvert INTEGER DEFAULT 0, " //convert to workorder days / meter counts in advance "nextsrvdate DATETIME DEFAULT #%s#, " "nextsrvmeter INTEGER DEFAULT 0, "//next meter count to service on "repeatevery INTEGER DEFAULT 0, "//repeat every meter / months "agemonths INTEGER DEFAULT 0, "//Age based: months old to schedule "ageyears INTEGER DEFAULT 0, "//Age based: years old to schedule "active YESNO DEFAULT True, "//on hold or active? "series INTEGER DEFAULT 0, "//schedule this many series at a time "creator INTEGER DEFAULT 0, "//user who created record "created DATETIME DEFAULT #%s#, " //date created "modifier INTEGER DEFAULT 0, "//date modified who cares?? probably no one "modified DATETIME DEFAULT #%s#, " "wotype INTEGER DEFAULT 0, " "woquick YESNO DEFAULT False, " "woproject INTEGER DEFAULT 0, " "woonsite YESNO DEFAULT False);" ,dtDefault.Format(_T("%m/%d/%Y")),dtDefault.Format(_T("%m/%d/%Y")),dtDefault.Format(_T("%m/%d/%Y"))); rs->Ex(q); //new table to hold preventative maintenance items //in schedule viewer q.Format("CREATE TABLE pmitems (" "id COUNTER CONSTRAINT PK_pmitem PRIMARY KEY, " "pmschedlink INTEGER DEFAULT 0, " "clientlink INTEGER DEFAULT 0, " "schedate DATETIME DEFAULT #%s#, " "schedmeter INTEGER DEFAULT 0, " "autowo YESNO DEFAULT True, " "hold YESNO DEFAULT False, " "schedtech INTEGER DEFAULT 0, " "link INTEGER DEFAULT 0, "//link to client or unit id number "isclient YESNO DEFAULT False);",dtDefault.Format(_T("%m/%d/%Y"))); //true = client false=unitbased rs->Ex(q); //clear out the pmparts table rs->Ex("DELETE pmparts.* FROM pmparts;"); //set correct report control profile for PM check screen now 8 columns was 7 rs->Ex("UPDATE users SET users.pmprofile = \"(8,8) 111 70 91 93 67 67 258 0 0 1 2 3 4 5 6 7\";"); //Add the lastmaintdate column to the defaults table //this is used for maintenance to ensure that only one station //tries to do it at a time: When SC is run, it checks to see if //this date is older than the current date, if so, it "locks" it by //updating to today's date, thereby effectively locking out any latecomers //then runs any required maintenance. rs->Ex("ALTER TABLE defaults ADD COLUMN lastmaintdate DATETIME;"); q.Format("UPDATE defaults SET defaults.lastmaintdate = #%s#;",dtDefault.Format(_T("%m/%d/%Y"))); rs->Ex(q); //Add the woestimate column to the defaults table, this is to //flag whether to use estimates on dispatch workorders or not. //this is in response to TCCSI client that needs this and it //will now be available to all users. This flag is settable under the //defaults screen, program, not users rs->Ex("ALTER TABLE defaults ADD COLUMN woestimate YESNO;"); rs->Ex("UPDATE defaults SET defaults.woestimate = False;"); //Customer reference number and contact //as suggested by Rob MacKay in Australia rs->Ex("ALTER TABLE wo ADD COLUMN clientrefnum TEXT(50);"); rs->Ex("ALTER TABLE wo ADD COLUMN clientcontact TEXT(50);"); //Add a first boot field to detect new evaluation versions //this will be used to show a friendly welcome to message and //to fixup the dates in the demo data. //set to false because if this field isn't in the table already, //it means user has older version so it just needs to be there //not actually used rs->Ex("ALTER TABLE defaults ADD COLUMN firstboot YESNO;"); rs->Ex("UPDATE defaults SET defaults.firstboot = False;"); //refdate is used in an eval to fixup all the dates //in the evaluation database. //so that the evaluator sees the demo data as current rs->Ex("ALTER TABLE defaults ADD COLUMN refdate DATETIME;"); //DROP the pm columns no longer required in the units table rs->Ex("ALTER TABLE units DROP COLUMN lastpmmetric;"); rs->Ex("ALTER TABLE units DROP COLUMN lastpmdate;"); rs->Ex("ALTER TABLE units DROP COLUMN nextpmmetric;"); rs->Ex("ALTER TABLE units DROP COLUMN nextpmdate;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"133\";"); nVersion=133; } break; //===================================================== case 133://changed to 134 for schedule view { CString strID,strName,strRights,strHash; long lData; GZK k; //Add new right: //loop through all the group records rs->Query("SELECT groups.* FROM groups;"); do{ rs->FetchField("id",&lData); rs->FetchField("a",&strName); rs->FetchField("b",&strRights); //decrypt the original rights string k.GZDecrypt(&strRights,false); strRights=strRights+"1";//add on the extra right for schedule view //re-'crypt' k.GZEncrypt(&strRights,false); //HASH strHash.Format("%u%s%s",lData,strName,strRights); k.GZHash(&strHash); //save the rights rs->UpdateField("b",&strRights); //save the hash rs->UpdateField("c",&strHash); //save the record if(!rs->SaveRecord()) AfxMessageBox("Error trying to save record"); }while(rs->MoveForward()); rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Parts\", \"parts.rpt\", \".\", False, 32767, 23;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"134\";"); nVersion=134; } break; //*************************************************************************** //===================================================== case 134://changed to 135 on 12/19/00 { rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Search results\", \"srch.rpt\", \".\", False, 32767, 24;"); rs->Ex("ALTER TABLE users ADD COLUMN rpttext1 MEMO;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"135\";"); nVersion=135; } break; //===================================================== case 135://changed to 136 on Jan 15 2001 { bUpdateRanOK=true; //USER RECORD CHANGES rs->Ex("ALTER TABLE users ADD COLUMN defschedstarthour INTEGER;"); rs->Ex("ALTER TABLE users ADD COLUMN defschedstophour INTEGER;"); rs->Ex("ALTER TABLE users ALTER defschedstarthour SET DEFAULT '0';"); rs->Ex("ALTER TABLE users ALTER defschedstophour SET DEFAULT '0';"); if(!rs->Ex("UPDATE users SET users.defschedstarthour = 0, users.defschedstophour = 0;")) bUpdateRanOK=false; //WORKORDER COLUMN CHANGES rs->Ex("ALTER TABLE wo ADD COLUMN status INTEGER;"); rs->Ex("ALTER TABLE wo ALTER status SET DEFAULT '0';"); rs->Ex("UPDATE wo SET wo.status = 0;"); rs->Ex("ALTER TABLE wo ADD COLUMN ourref TEXT(80);"); rs->Ex("ALTER TABLE wo ADD COLUMN esthours REAL;"); rs->Ex("ALTER TABLE wo ADD COLUMN estrate INTEGER;"); rs->Ex("ALTER TABLE wo ALTER notes TEXT(110)"); //STATUS VIEW SCREEN CHANGE rs->Ex("UPDATE statusviews SET statusviews.viewprofile = \"(17,17) 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16\";"); //fix the version number up as long as updates seem ok if(bUpdateRanOK) rs->Ex("UPDATE defaults SET defaults.versioninfo = \"136\";"); AfxMessageBox("Part of this update modifies the main workorder list view screen.\r\n\r\n" "You will need to re-order the columns in the main view to your preferences and re-save the views.\r\n\r\n" "This update affects the column order only, not the underlying restriction settings."); nVersion=136; } break; //===================================================== case 136://changed to 137 on Jan 18 2001 { //NEW FIELDS TO ADD TO STATUS VIEW TABLE rs->Ex("ALTER TABLE statusviews ADD COLUMN ourref INTEGER;"); rs->Ex("ALTER TABLE statusviews ADD COLUMN status INTEGER;"); rs->Ex("ALTER TABLE statusviews ALTER ourref SET DEFAULT '0';"); rs->Ex("ALTER TABLE statusviews ALTER status SET DEFAULT '0';"); rs->Ex("UPDATE statusviews SET statusviews.status = 1;"); rs->Ex("UPDATE statusviews SET statusviews.ourref = 1;"); rs->Ex("ALTER TABLE woparts ADD COLUMN sn TEXT(255);"); //client account number rs->Ex("ALTER TABLE clients ADD COLUMN acctnumber TEXT(40);"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"137\";"); nVersion=137; } break; case 137://changed to 138 on Jan 29 2001 -bug in tech billing summary { q2="SELECT [users].[last] & \", \" & [users].[first] AS name, Sum(techsubq.hours) AS SumOfhours, Sum(techsubq.nchours) AS SumOfnchours, Sum(techsubq.travhours) AS SumOftravhours, Sum(techsubq.wototal) AS SumOfwototal " "FROM [SELECT labor.tech, labor.hours, labor.nchours, labor.travhours, (rates.rate*labor.hours)+(travelrates.rate*labor.travhours) AS wototal " "FROM rates AS travelrates RIGHT JOIN (((labor LEFT JOIN (probs LEFT JOIN wo ON probs.wolink = wo.id) ON labor.link = probs.id) LEFT JOIN rates ON labor.rate = rates.id) LEFT JOIN clients ON wo.client = clients.id) ON travelrates.id = labor.travrate " "WHERE (((labor.tech)<>-1) AND ((labor.stop) Between #~STRT# And #~END_#) AND ((clients.czone)<>-1) AND ((wo.type)<>-1) AND ((wo.project)<>-1) AND ((wo.client)<>-1))]. AS techsubq INNER JOIN users ON techsubq.tech = users.id " "GROUP BY techsubq.tech, [users].[last] & \", \" & [users].[first] " "ORDER BY [users].[last] & \", \" & [users].[first];"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=17));",q2); rs->Ex(q); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"138\";"); nVersion=138; } break; case 138://changed to 139 on Jan 29 2001 -bug in tech billing summary and didn't fix it the first time { q2="SELECT [users].[last] & \", \" & [users].[first] AS name, Sum(techsubq.hours) AS SumOfhours, Sum(techsubq.nchours) AS SumOfnchours, Sum(techsubq.travhours) AS SumOftravhours, Sum(techsubq.wototal) AS SumOfwototal " "FROM [SELECT labor.tech, labor.hours, labor.nchours, labor.travhours, (rates.rate*labor.hours)+(travelrates.rate*labor.travhours) AS wototal " "FROM rates AS travelrates RIGHT JOIN (((labor LEFT JOIN (probs LEFT JOIN wo ON probs.wolink = wo.id) ON labor.link = probs.id) LEFT JOIN rates ON labor.rate = rates.id) LEFT JOIN clients ON wo.client = clients.id) ON travelrates.id = labor.travrate " "WHERE (((labor.tech)~TECH) AND ((labor.stop) Between #~STRT# And #~END_#) AND ((clients.czone)~ZONE) AND ((wo.type)~CAT_) AND ((wo.project)~PROJ) AND ((wo.client)~CUST))]. AS techsubq INNER JOIN users ON techsubq.tech = users.id " "GROUP BY techsubq.tech, [users].[last] & \", \" & [users].[first] " "ORDER BY [users].[last] & \", \" & [users].[first];"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=17));",q2); rs->Ex(q); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"139\";"); nVersion=139; } break; case 139://changed to 140 on Feb 15 2001 Added color to status items { rs->Ex("ALTER TABLE probstat ADD COLUMN red INTEGER;"); rs->Ex("ALTER TABLE probstat ADD COLUMN green INTEGER;"); rs->Ex("ALTER TABLE probstat ADD COLUMN blue INTEGER;"); rs->Ex("ALTER TABLE probstat ALTER red SET DEFAULT '0';"); rs->Ex("ALTER TABLE probstat ALTER green SET DEFAULT '0';"); rs->Ex("ALTER TABLE probstat ALTER blue SET DEFAULT '0';"); //set all to black initially rs->Ex("UPDATE probstat SET probstat.red = 0;"); rs->Ex("UPDATE probstat SET probstat.green = 0;"); rs->Ex("UPDATE probstat SET probstat.blue = 0;"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"140\";"); nVersion=140; } break; case 140://changed to 141 on March 7th 2001 bug in report: Billing summary - hours/parts/3rd party { q2="SELECT IIf(IsNull([clients].[company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]) AS company, Choose([typeUNIONsub].[type],\"Service\",\"3rd party\",\"Parts\") AS chargesfrom, Sum(typeUNIONsub.total) AS total " "FROM ([SELECT probs.wolink AS link, \"1\" AS type, (rates.rate*labor.hours)+(travelrates.rate*labor.travhours) AS total " "FROM (rates INNER JOIN (rates AS travelrates INNER JOIN labor ON travelrates.id = labor.travrate) ON rates.id = labor.rate) INNER JOIN (clients INNER JOIN (wo INNER JOIN probs ON wo.id = probs.wolink) ON clients.id = wo.client) ON labor.link = probs.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((clients.czone)~ZONE) AND ((wo.client)~CUST) AND ((wo.type)~CAT_) AND ((wo.project)~PROJ)) " "UNION ALL (SELECT probs.wolink AS link, \"2\" AS type, subrepair.charge AS total " "FROM subrepair INNER JOIN (clients INNER JOIN (wo INNER JOIN probs ON wo.id = probs.wolink) ON clients.id = wo.client) ON subrepair.link = probs.id " "WHERE (((subrepair.charge)<>0) AND ((wo.created) Between #~STRT# And #~END_#) AND ((clients.czone)~ZONE) AND ((wo.client)~CUST) AND ((wo.type)~CAT_) AND ((wo.project)~PROJ)) " "UNION ALL (SELECT probs.wolink, \"3\" AS type, woparts.quantity*woparts.price AS total " "FROM woparts INNER JOIN (clients INNER JOIN (wo INNER JOIN probs ON wo.id = probs.wolink) ON clients.id = wo.client) ON woparts.link = probs.id " "WHERE (((clients.czone)~ZONE) AND ((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.type)~CAT_) AND ((wo.project)~PROJ))) " " )]. AS typeUNIONsub INNER JOIN wo ON typeUNIONsub.link = wo.id) INNER JOIN clients ON wo.client = clients.id " "GROUP BY IIf(IsNull([clients].[company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]), Choose([typeUNIONsub].[type],\"Service\",\"3rd party\",\"Parts\");"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=4));",q2); rs->Ex(q); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"141\";"); nVersion=141; } break; case 141://changed to 142 on March 26th 2001 various updates { //Add zone field to users rs->Ex("ALTER TABLE users ADD COLUMN defzone INTEGER;"); rs->Ex("ALTER TABLE users ALTER defzone SET DEFAULT '0';"); //set all zones to 0 initially rs->Ex("UPDATE users SET users.defzone = 0;"); //Add default wo status fields to defaults rs->Ex("ALTER TABLE defaults ADD COLUMN wonewstat INTEGER;"); rs->Ex("ALTER TABLE defaults ADD COLUMN woclosestat INTEGER;"); rs->Ex("ALTER TABLE defaults ADD COLUMN woreopenstat INTEGER;"); //add default schedule screen refresh time period rs->Ex("ALTER TABLE defaults ADD COLUMN schedrfrshsecs INTEGER;"); //set all 0 initially rs->Ex("UPDATE defaults SET defaults.wonewstat = 0, defaults.woclosestat = 0, defaults.woreopenstat = 0, defaults.schedrfrshsecs = 60;"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"142\";"); nVersion=142; } break; case 142://changed to 143 on April 6th 2001 various updates { //Add default wo status fields to defaults rs->Ex("ALTER TABLE defaults ADD COLUMN schedwindow INTEGER;"); //set to 30 day window by default rs->Ex("UPDATE defaults SET defaults.schedwindow = 30;"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"143\";"); nVersion=143; } break; case 143://changed to 144 on May 8th 2001 various updates { //Add xfertempl table and set values. This is for import export q=("CREATE TABLE xfertempl (" "name TEXT(80) CONSTRAINT PK_name PRIMARY KEY, " "import YESNO DEFAULT False, " "delimiter TEXT(1), " "fields MEMO, " "builtin YESNO DEFAULT False, " "fieldnames YESNO DEFAULT False, " "path MEMO, " "[sql] MEMO, " "[table] TEXT(50));"); rs->Ex(q); rs->Close(); q2="\"+first\",\"+last\",\"+company\",\"+mailaddress\",\"+streetaddress\",\"+city\",\"+stateprov\",\"+postal\",\"+country\",\"+bizphone\",\"+extension\",\"+fax\",\"+email\",\"+technotes\",\"+alert\",\"+generalnotes\",\"-acctnumber\""; q.Format("INSERT INTO xfertempl ( name, import, delimiter, fields, builtin, fieldnames, path, [sql], [table] ) " "SELECT \"Clients\" , False, \",\",'%s', True, True, \"c:\\\", \"SELECT * FROM clients;\",\"clients\";",q2); rs->Ex(q); q2="\"+partnumber\",\"+description\",\"+avgcost\",\"+retail\",\"+notes\",\"+supplierpart\",\"-upc\""; q.Format("INSERT INTO xfertempl ( name, import, delimiter, fields, builtin, fieldnames, path, [sql], [table] ) " "SELECT \"Parts\" , False, \",\",'%s', True, True, \"c:\\\", \"SELECT * FROM parts;\",\"parts\";",q2); rs->Ex(q); q2="\"+Customer\",\"+Contact\",\"+Phone\",\"+Fax\",\"+Address\",\"+Notes\",\"+Account\""; q.Format("INSERT INTO xfertempl ( name, import, delimiter, fields, builtin, fieldnames, path, [sql], [table] ) " "SELECT \"Quick Books - Clients\" , True, \"T\",'%s', True, False, \"c:\\\", \"\",\"QBCLIENTS\";",q2); rs->Ex(q); q2="\"+id\",\"+sn\",\"+id1\",\"+id2\",\"+id3\",\"+company\",\"+first\",\"+last\",\"+receipt\",\"+purchasedate\",\"+model\",\"+manufacturer\",\"+name\",\"+loaner\",\"+lastmeter\""; q.Format("INSERT INTO xfertempl ( name, import, delimiter, fields, builtin, fieldnames, path, [sql], [table] ) " "SELECT \"Units\" , False, \",\",'%s', True, True, \"c:\\\", \"SELECT units.id, units.sn, units.id1, units.id2, units.id3, clients.company, clients.first, clients.last, units.receipt, units.purchasedate, unitmodels.model, nonclients.company_person AS manufacturer, unitmodelcats.name, units.loaner, units.lastmeter " "FROM ((units LEFT JOIN (unitmodels LEFT JOIN unitmodelcats ON unitmodels.category = unitmodelcats.id) ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN clients ON units.client = clients.id;\",\"sql\";",q2); rs->Ex(q); rs->Ex("ALTER TABLE wo ADD COLUMN indexed YESNO;"); rs->Ex("UPDATE wo SET wo.indexed = False;"); //new account number field for non-clients rs->Ex("ALTER TABLE nonclients ADD COLUMN account TEXT(40);"); //new custref column stuff here: rs->Ex("ALTER TABLE statusviews ADD COLUMN custref INTEGER;"); rs->Ex("ALTER TABLE statusviews ALTER custref SET DEFAULT '0';"); rs->Ex("UPDATE statusviews SET statusviews.custref = 1;"); rs->Ex("UPDATE statusviews SET statusviews.viewprofile = \"(18,18) 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17\";"); //fix of pmprofile bug where it defaults to 7 columns for new users rather //then the actual value of 8 //set correct report control profile for PM check screen now 8 columns was 7 rs->Ex("UPDATE users SET users.pmprofile = \"(8,8) 111 70 91 93 67 67 258 0 0 1 2 3 4 5 6 7\";"); rs->Ex("ALTER TABLE users ALTER pmprofile SET DEFAULT \"(8,8) 111 70 91 93 67 67 258 0 0 1 2 3 4 5 6 7\";"); //Add new parts used on workorder reports to rptsmaster //DETAILED rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Parts on workorders\", \"partwo.rpt\", \"mgr\", True, 397, 25;"); //SUMMARY rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Parts on workorder - summarized\", \"prtwosum.rpt\", \"mgr\", True, 397, 26;"); //DETAILED q2="SELECT IIf(IsNull([company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]) AS CLIENT, wo.id AS WORKORDER, #~STRT# AS STARTDATE, #~END_# AS ENDDATE, wo.starttime AS SCHEDULED, IIf(IsNull([partnumber]),\"misc.\",[partnumber]) AS PART, IIf(IsNull([partnumber]),[misc],[description]) AS [DESC], woparts.quantity, woparts.sn, users.last AS TECH, wo.closed, woparts.price AS WOPRICE, parts.retail, clients.id AS CLIENTID, wo.created AS WOCREATED, wo.project, wo.type " "FROM (((woparts RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) ON woparts.link = probs.id) LEFT JOIN parts ON woparts.partnum = parts.id) LEFT JOIN users ON wo.assigntech = users.id) LEFT JOIN clients ON wo.client = clients.id " "WHERE (((clients.id)~CUST) AND ((wo.created) Between #~STRT# And #~END_#) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_) AND ((woparts.id) Is Not Null)) " "ORDER BY IIf(IsNull([partnumber]),\"misc.\",[partnumber]);"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=25));",q2); rs->Ex(q); //SUMMARY q2="SELECT IIf(IsNull([partnumber]),\"misc.\",[partnumber]) AS PART, IIf(IsNull([partnumber]),[misc],[description]) AS [DESC], #~STRT# AS STARTDATE, #~END_# AS ENDDATE, Sum(woparts.quantity) AS [TOTAL USED] " "FROM (((woparts RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) ON woparts.link = probs.id) LEFT JOIN parts ON woparts.partnum = parts.id) LEFT JOIN users ON wo.assigntech = users.id) LEFT JOIN clients ON wo.client = clients.id " "WHERE (((clients.id)~CUST) AND ((wo.created) Between #~STRT# And #~END_#) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_) AND ((woparts.id) Is Not Null)) " "GROUP BY IIf(IsNull([partnumber]),\"misc.\",[partnumber]), IIf(IsNull([partnumber]),[misc],[description]) " "ORDER BY IIf(IsNull([partnumber]),\"misc.\",[partnumber]);"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=26));",q2); rs->Ex(q); //Add SUBREPAIR REPORTS AND QUERIES //OUTSTANDING rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Subrepair status - outstanding\", \"subrepair.rpt\", \"mgr\", True, 401, 27;"); //ALL rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Subrepair status - all\", \"subrepairall.rpt\", \"mgr\", True, 401, 28;"); //OUTSTANDING q2="SELECT IIf(IsNull([company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]) AS CLIENT, wo.id AS WORKORDER, #~STRT# AS STARTDATE, #~END_# AS ENDDATE, nonclients.company_person AS SENTTO, nonclients_1.company_person AS SENTVIA, subrepair.sent AS DATESENT, subrepair.eta AS RECEIVEETA, subrepair.received AS DATERECEIVED, [nonclients_2].[company_person] & \" \" & [unitmodels].[model] & \" \" & [unitmodels].[description] & \" sn: \" & [units].[sn] AS ITEM, units.sn, nonclients_2.company_person AS MANUFACTURER, unitmodels.model, unitmodels.description, subrepair.waybill, subrepair.rma, subrepair.isback " "FROM nonclients AS nonclients_2 RIGHT JOIN (((units RIGHT JOIN ((clients RIGHT JOIN (subrepair RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) ON subrepair.link = probs.id) ON clients.id = wo.client) LEFT JOIN nonclients ON subrepair.where = nonclients.id) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients AS nonclients_1 ON subrepair.sentvia = nonclients_1.id) ON nonclients_2.id = unitmodels.manufacturer " "WHERE (((subrepair.sent) Between #~STRT# And #~END_#) AND ((subrepair.id) Is Not Null) AND ((subrepair.isback)=False) AND ((wo.client)~CUST) AND ((units.id)~UNIT)) " "ORDER BY subrepair.sent;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=27));",q2); rs->Ex(q); //ALL q2="SELECT IIf(IsNull([company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]) AS CLIENT, wo.id AS WORKORDER, #~STRT# AS STARTDATE, #~END_# AS ENDDATE, nonclients.company_person AS SENTTO, nonclients_1.company_person AS SENTVIA, subrepair.sent AS DATESENT, subrepair.eta AS RECEIVEETA, subrepair.received AS DATERECEIVED, [nonclients_2].[company_person] & \" \" & [unitmodels].[model] & \" \" & [unitmodels].[description] & \" sn: \" & [units].[sn] AS ITEM, units.sn, nonclients_2.company_person AS MANUFACTURER, unitmodels.model, unitmodels.description, subrepair.waybill, subrepair.rma, subrepair.isback " "FROM nonclients AS nonclients_2 RIGHT JOIN (((units RIGHT JOIN ((clients RIGHT JOIN (subrepair RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) ON subrepair.link = probs.id) ON clients.id = wo.client) LEFT JOIN nonclients ON subrepair.where = nonclients.id) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients AS nonclients_1 ON subrepair.sentvia = nonclients_1.id) ON nonclients_2.id = unitmodels.manufacturer " "WHERE (((subrepair.sent) Between #~STRT# And #~END_#) AND ((subrepair.id) Is Not Null) AND ((wo.client)~CUST) AND ((units.id)~UNIT)) " "ORDER BY subrepair.sent;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=28));",q2); rs->Ex(q); //WARNING MESSAGE ABOUT COLUMN FORMATS IN MAIN WORKORDER VIEW BEING MESSED UP AfxMessageBox("Part of this update modifies the main workorder list view screen to add the \r\nCUSTOMER REFERENCE NUMBER column.\r\n\r\n" "You will need to re-order the columns in the main view to your preferences and re-save the views.\r\n\r\n" "This update affects the column order only, not the underlying restriction settings."); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"144\";"); nVersion=144; } break; case 144://changed to 145 on May 23rd 2001 various updates { //Add securenet's fields to wo header rs->Ex("ALTER TABLE wo ADD COLUMN prob_reported TEXT(255);"); rs->Ex("ALTER TABLE wo ADD COLUMN prob_found TEXT(255);"); rs->Ex("ALTER TABLE wo ADD COLUMN action_taken TEXT(255);"); //Add corresponding entry to defaults to flag whether to show //those new fields or not rs->Ex("ALTER TABLE defaults ADD COLUMN showprobaction YESNO;"); rs->Close(); //Default to no for everyone for now rs->Ex("UPDATE defaults SET showprobaction = False;"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"145\";"); nVersion=145; } break; case 145://changed to 146 on May 27th 2001 various updates { //Add weeks and days fields to pm header rs->Ex("ALTER TABLE pmhead ADD COLUMN rptweeks INTEGER;"); rs->Ex("ALTER TABLE pmhead ADD COLUMN rptdays INTEGER;"); rs->Ex("ALTER TABLE pmhead ALTER rptweeks SET DEFAULT '0';"); rs->Ex("ALTER TABLE pmhead ALTER rptdays SET DEFAULT '0';"); rs->Close(); //set all to 0 initially rs->Ex("UPDATE pmhead SET rptweeks = 0;"); rs->Ex("UPDATE pmhead SET rptdays = 0;"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"146\";"); nVersion=146; } break; case 146://changed to 147 on june 21th 2001 various updates { //set all blank company fields to last, first names rs->QueryReadOnly("SELECT clients.last, clients.first, clients.bizphone FROM clients " "WHERE (((clients.first) In (SELECT [first] FROM [clients] As Tmp GROUP BY [first],[last] HAVING Count(*)>1 And [last] = [clients].[last])) AND ((clients.company) Is Null)) " "ORDER BY clients.last;"); if(rs->IsEmpty()) { rs->Ex("UPDATE clients SET clients.company = [last] & \", \" & [first] " "WHERE (((clients.company) Is Null));"); rs->Close(); } else { AfxMessageBox( "Warning: Due to a change in the clients table in the database\r\n" "this update needs to move the contact first and last names to the former \r\n" "\"Company\" field which is now the single client field.\r\n\r\n" "Your help is required to correct a problem before the update can finish:\r\n" "You have duplicate non-company clients and need to change them in the clients screen.\r\n\r\n" "When this update completes and returns you to AyaNova, \r\n" "go directly to the client screen (Options->Edit->Clients) where you will be given\r\n" "more instructions on fixing the duplicate client names."); //m_pApp->ShowStuff(strData); //stop from doing anything further buptodate=true; break; } //---------------------------------------------------------------------------- //Performance boost - new indexes rs->Ex("CREATE INDEX idxanytime ON wo (anytime);"); rs->Ex("CREATE INDEX idxquick ON wo (quick);"); rs->Ex("CREATE INDEX idxassigntech ON wo (assigntech);"); rs->Ex("CREATE INDEX idxstarttime ON wo (starttime);"); AfxMessageBox("This update contains speed improvements to the database.\r\n\r\n" "This will not take effect until *after* you COMPACT the database after updating.\r\n" "The COMPACT option is on the database utilities menu.\r\n" "(Re-indexing is not necessary, only COMPACT)"); //----------------------------------------------------------------------------- //---------------------------------------------------------------------------- //Add new schedule groups tables q.Format( "CREATE TABLE schdgrps (" "id COUNTER CONSTRAINT PK_pmitem PRIMARY KEY, " "name TEXT(80));"); rs->Ex(q); q.Format("CREATE TABLE schdets (" "grpid INTEGER DEFAULT 0, " "techid INTEGER DEFAULT 0);"); rs->Ex(q); rs->Close(); //group get's indexed because it's the searched and linked field rs->Ex("CREATE INDEX idxgrpid ON schdets (grpid);"); //techid's don't get indexed because they are simply retrieved //----------------------------------------------------------------------------- //create subunits table q.Format("CREATE TABLE subunits (" "masterunitid INTEGER DEFAULT 0, " "unitid INTEGER DEFAULT 0, " "creator INTEGER DEFAULT 0, "//user who created record "created DATETIME, " //date created "modifier INTEGER DEFAULT 0, "//date modified who cares?? probably no one "modified DATETIME);"); rs->Ex(q); rs->Ex("CREATE INDEX idxmstrunit " "ON subunits (masterunitid);"); //----------------------------------------------------------------------------- //add the master/sub unit report to reports screen rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Master and sub units (kits)\", \"unitkits.rpt\", \"mgr\", True, 3217, 29;"); q2="SELECT units.sn AS mastersn, units.id, units.client, unitmodels.manufacturer, units.model, unitmodels.description AS mastermodel, nonclients.company_person AS mastermake, unitmodelcats.name AS mastertype, units_1.sn AS subsn, unitmodels_1.description AS submodel, nonclients_1.company_person AS submake, unitmodelcats_1.name AS subtype " "FROM ((((subunits RIGHT JOIN (((units LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN unitmodelcats ON unitmodels.category = unitmodelcats.id) ON subunits.masterunitid = units.id) LEFT JOIN units AS units_1 ON subunits.unitid = units_1.id) LEFT JOIN unitmodels AS unitmodels_1 ON units_1.model = unitmodels_1.id) LEFT JOIN unitmodelcats AS unitmodelcats_1 ON unitmodels_1.category = unitmodelcats_1.id) LEFT JOIN nonclients AS nonclients_1 ON unitmodels_1.manufacturer = nonclients_1.id " "WHERE (((units.id)~UNIT) AND ((units.client)~CUST) AND ((unitmodels.manufacturer)~MANU) AND ((units.model)~MODL)) " "ORDER BY units.sn, units.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=29));",q2); rs->Ex(q); //----------------------------------------------------------------------------- //----------------------------------------------------------------------------- //add the rate billing summary report to reports screen rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Billing summary by rate\", \"ratesums.rpt\", \"mgr\", True, 463, 30;"); q2="SELECT rates.name, Sum(labor.hours) AS SumOfhours, Sum(labor.nchours) AS SumOfnchours, Sum(labor.travhours) AS SumOftravhours, rates.rate, rates.travelrate " "FROM ((wo RIGHT JOIN probs ON wo.id = probs.wolink) RIGHT JOIN labor ON probs.id = labor.link) LEFT JOIN rates ON labor.rate = rates.id " "WHERE (((labor.start) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((labor.tech)~TECH) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_) AND ((rates.id)~RATE) AND ((rates.active)=True)) " "GROUP BY rates.name, rates.rate, rates.travelrate, rates.id UNION (SELECT rates.name, Sum(labor.hours) AS SumOfhours, Sum(labor.nchours) AS SumOfnchours, Sum(labor.travhours) AS SumOftravhours, rates.rate, rates.travelrate " "FROM ((wo RIGHT JOIN probs ON wo.id = probs.wolink) RIGHT JOIN labor ON probs.id = labor.link) LEFT JOIN rates ON labor.travrate = rates.id " "WHERE (((labor.start) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((labor.tech)~TECH) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_) AND ((rates.id)~RATE) AND ((rates.active)=True)) " "GROUP BY rates.name, rates.rate, rates.travelrate, rates.id) " "ORDER BY rates.name;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=30));",q2); rs->Ex(q); //----------------------------------------------------------------------------- //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"147\";"); nVersion=147; //----------------------------------------------------------------------------- } break; case 147://changed to 148 on july 6th 2001 for version 1.7.1.7 { //---------------------------------------------------------------------------- //increase size of srchdict.word from 30 characters to 50 rs->Ex("ALTER TABLE srchdict ALTER COLUMN word TEXT(50);"); //increase size of srch.client from 50 characters to 80 rs->Ex("ALTER TABLE srch ALTER COLUMN client TEXT(80);"); //----------------------------------------------------------------------------- //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"148\";"); //----------------------------------------------------------------------------- nVersion=148; } break; case 148: { //---------------------------------------------------------------------------- //Add a program version number field to the database rs->Ex("ALTER TABLE defaults ADD COLUMN min_exe TEXT(25);"); //----------------------------------------------------------- //Add schedule markers table and indices rs->Ex( "CREATE TABLE schedmarkers (" "id COUNTER CONSTRAINT PK_schedmrk PRIMARY KEY, " "link INTEGER DEFAULT 0," "startdate DATETIME, " "enddate DATETIME, " "notes TEXT(15), " "red INTEGER DEFAULT 128, " "green INTEGER DEFAULT 128, " "blue INTEGER DEFAULT 128" ");"); rs->Ex("CREATE INDEX idxsmlink " "ON schedmarkers (link);"); rs->Ex("CREATE INDEX idxsmstdate " "ON schedmarkers (startdate);"); rs->Ex("CREATE INDEX idxsmendate " "ON schedmarkers (enddate);"); //---------------------------------------------------------- //---------------------------------------------- rs->Ex("ALTER TABLE wo ADD COLUMN starttime2 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN stoptime2 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN assigntech2 INTEGER;"); rs->Ex("ALTER TABLE wo ADD COLUMN starttime3 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN stoptime3 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN assigntech3 INTEGER;"); rs->Ex("ALTER TABLE wo ADD COLUMN starttime4 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN stoptime4 DATETIME;"); rs->Ex("ALTER TABLE wo ADD COLUMN assigntech4 INTEGER;"); rs->Ex("ALTER TABLE wo ALTER assigntech SET DEFAULT '-1';"); rs->Ex("ALTER TABLE wo ALTER assigntech2 SET DEFAULT '-1';"); rs->Ex("ALTER TABLE wo ALTER assigntech3 SET DEFAULT '-1';"); rs->Ex("ALTER TABLE wo ALTER assigntech4 SET DEFAULT '-1';"); //---------------------------------------------- rs->Ex("CREATE INDEX idxassigntech2 ON wo (assigntech2);"); rs->Ex("CREATE INDEX idxstarttime2 ON wo (starttime2);"); rs->Ex("CREATE INDEX idxassigntech3 ON wo (assigntech3);"); rs->Ex("CREATE INDEX idxstarttime3 ON wo (starttime3);"); rs->Ex("CREATE INDEX idxassigntech4 ON wo (assigntech4);"); rs->Ex("CREATE INDEX idxstarttime4 ON wo (starttime4);"); //set extra techs to -1 meaning not assigned yet rs->Ex("UPDATE wo SET wo.assigntech2 = -1, wo.assigntech3 = -1, wo.assigntech4 = -1;"); //set non-scheduled workorders first tech to non assigned -1 rs->Ex("UPDATE wo SET wo.assigntech = -1 WHERE (((wo.anytime)=True));"); //----------------------------------------------------------------------------- //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"149\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); //----------------------------------------------------------------------------- nVersion=149; } break; case 149: { //Last modified 07/30/2001 - added category/type column //COLUMNMOD //new CATEGORY column stuff here: rs->Ex("ALTER TABLE statusviews ADD COLUMN category INTEGER;"); rs->Ex("ALTER TABLE statusviews ALTER category SET DEFAULT '0';"); rs->Ex("UPDATE statusviews SET statusviews.category = -1;"); //new project column here rs->Ex("ALTER TABLE statusviews ADD COLUMN project INTEGER;"); rs->Ex("ALTER TABLE statusviews ALTER project SET DEFAULT '0';"); rs->Ex("UPDATE statusviews SET statusviews.category = -1;"); //update all views to handle extra columns rs->Ex("UPDATE statusviews SET statusviews.viewprofile = \"(20,20) 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 80 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19\";"); //fix the version number up as long as updates seem ok rs->Ex("UPDATE defaults SET defaults.versioninfo = \"150\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); //WARNING MESSAGE ABOUT COLUMN FORMATS IN MAIN WORKORDER VIEW BEING MESSED UP AfxMessageBox("Part of this update modifies the main workorder list view screen to add the \r\n" "WORKORDER CATEGORY and PROJECT columns.\r\n\r\n" "This change will affect *all* the views you have configured in AyaNova.\r\n" "You will need to re-order the columns in the main view to your preferences and re-save each view separately.\r\n\r\n" "This update affects the column order only, not the underlying restriction settings.\r\n" "\r\nDo not attempt to edit your views until after you have restarted AyaNova when this update completes."); //----------------------------------------------------------------------------- nVersion=150; } break; case 150: { //ADD AYANOTIFY TABLES //--------------------------------------- rs->Ex( "CREATE TABLE notify_cfg (freq_mm INTEGER, [dow] INTEGER, stop_hour DATETIME, start_hour DATETIME, " "[attempts] INTEGER, [mapi] YESNO, keeplogdays INTEGER, [verboseLog] YESNO, login_name TEXT(50), " "login_pw TEXT(50), [connection] TEXT(120), from_address TEXT(80), [server] TEXT(120), " "next_xmit DATETIME, [dialup] YESNO, last_xmit DATETIME, dayspast INTEGER , " "daysfuture INTEGER);"); rs->Ex("ALTER TABLE notify_cfg ALTER freq_mm SET DEFAULT '0';"); rs->Ex("ALTER TABLE notify_cfg ALTER dow SET DEFAULT '0';"); rs->Ex("ALTER TABLE notify_cfg ALTER attempts SET DEFAULT '0';"); rs->Ex("ALTER TABLE notify_cfg ALTER keeplogdays SET DEFAULT '30';"); rs->Ex("ALTER TABLE notify_cfg ALTER dayspast SET DEFAULT '0';"); rs->Ex("ALTER TABLE notify_cfg ALTER daysfuture SET DEFAULT '14';"); rs->Ex( "INSERT INTO notify_cfg ( freq_mm, dow, stop_hour, start_hour, attempts, mapi, " "keeplogdays, verboseLog, login_name, login_pw, [connection], from_address, server, " "next_xmit, dialup, last_xmit, dayspast, daysfuture ) " "SELECT 60 , 0, #12/30/1899 19:0:0#, #12/30/1899 7:0:0#, 0, False, 30, False, " "\"login\", \"password\", \"My ISP\", \"from_me@my_isp.com\", \"smtp.mail.my_isp.com\", " "#1/1/2000#, False, #1/1/2000#, 1, 14;"); //log table rs->Ex( "CREATE TABLE notify_log (" "id INTEGER DEFAULT 0, " "nwhen DATETIME, " "nwho INTEGER DEFAULT 0, " "nwhat TEXT(255), " "ntype INTEGER DEFAULT 0, " "nresult TEXT(255) " ");"); //temp table for building notifications rs->Ex( "CREATE TABLE notify_temp (" "woid INTEGER DEFAULT 0, " "scheddate DATETIME, " "schedstop DATETIME, " "schedtech INTEGER DEFAULT 0 " ");"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"151\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); nVersion=151; } break; case 151: { //--------------------------------------- //add the WORKORDERS report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Workorders\", \"allwo.rpt\", \"mgr\", True, 397, 31;"); q2="SELECT ~CRITERIA AS CRITERIA, wo.id AS wonumber, \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) & \"Unit: \" & [nonclients].[company_person] & \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") AS probheader, \"test\" AS compname, wom.probnum, wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, wom.PROBBRIEF, wom.item, wom.linetotal, wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created AS wodate, wo.invoice, wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, clients.bizphone, clients.extension, clients.fax, clients.email, clients.company AS clientname, wom.details, wom.START, wom.STOP,wom.REGHOURS, wom.TRAVHOURS, wom.NCHOURS, projects.name AS PROJNAME, projects.notes AS PROJNOTES, wo.client, wo.project, wo.type, wotypes.category AS CATEGORY " "FROM ((((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT \"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink AS wonum, \"Service: \" & users.first & \" \" & users.last & \" - \" & IIf(labor.hours>0,labor.hours & \" @ \" & Format(rates.rate,\"Currency\") & \" (pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" (\" & labor.nchours & \" no charge)\",\"\") & IIf(labor.travhours>0,\", \" & labor.travhours & \" travel @ \" & Format(travelrates.rate,\"Currency\") & IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" & travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) AS linetotal, labor.details , labor.start AS START, labor.stop AS STOP, labor.hours AS REGHOURS, labor.travhours AS TRAVHOURS, labor.nchours as NCHOURS FROM users INNER JOIN (rates AS travelrates INNER JOIN (rates INNER JOIN (labor INNER JOIN probs ON labor.link = probs.id) ON rates.id = labor.rate) ON travelrates.id = labor.travrate) ON users.id = labor.tech WHERE (((probs.wolink)<>0)) " " UNION ALL (SELECT \"2\" AS ctype, \"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Parts: \" & IIf(woparts.misc= \"\",parts.partnumber & \" \" & parts.description & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") & \" ea.(sn:\" & woparts.sn & \")\",woparts.misc & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" & woparts.sn & \")\") AS item, woparts.quantity*woparts.price AS linetotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM (probs INNER JOIN woparts ON probs.id = woparts.link) " " LEFT JOIN parts ON woparts.partnum = parts.id WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Third party service: \" AS item, subrepair.charge AS linettotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM probs INNER JOIN subrepair ON probs.id = subrepair.link WHERE (((probs.wolink)<>0) AND ((subrepair.charge)<>0))))]. AS wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN clients AS headoffices ON clients.headoffice = headoffices.id) ON probs.id = wom.probnum) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN projects ON wo.project = projects.id ) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_)) " "ORDER BY wo.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=31));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the WORKORDERS BRIEF report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Workorders - brief\", \"allwobrief.rpt\", \"mgr\", True, 397, 32;"); q2="SELECT ~CRITERIA AS CRITERIA, wo.id AS wonumber, \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) & \"Unit: \" & [nonclients].[company_person] & \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") AS probheader, \"test\" AS compname, wom.probnum, wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, wom.PROBBRIEF, wom.item, wom.linetotal, wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created AS wodate, wo.invoice, wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, clients.bizphone, clients.extension, clients.fax, clients.email, clients.company AS clientname, wom.details, wom.START, wom.STOP,wom.REGHOURS, wom.TRAVHOURS, wom.NCHOURS, projects.name AS PROJNAME, projects.notes AS PROJNOTES, wo.client, wo.project, wo.type, wotypes.category AS CATEGORY " "FROM ((((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT \"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink AS wonum, \"Service: \" & users.first & \" \" & users.last & \" - \" & IIf(labor.hours>0,labor.hours & \" @ \" & Format(rates.rate,\"Currency\") & \" (pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" (\" & labor.nchours & \" no charge)\",\"\") & IIf(labor.travhours>0,\", \" & labor.travhours & \" travel @ \" & Format(travelrates.rate,\"Currency\") & IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" & travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) AS linetotal, labor.details , labor.start AS START, labor.stop AS STOP, labor.hours AS REGHOURS, labor.travhours AS TRAVHOURS, labor.nchours as NCHOURS FROM users INNER JOIN (rates AS travelrates INNER JOIN (rates INNER JOIN (labor INNER JOIN probs ON labor.link = probs.id) ON rates.id = labor.rate) ON travelrates.id = labor.travrate) ON users.id = labor.tech WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"2\" AS ctype, \"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Parts: \" & IIf(woparts.misc= \"\",parts.partnumber & \" \" & parts.description & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") & \" ea.(sn:\" & woparts.sn & \")\",woparts.misc & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" & woparts.sn & \")\") AS item, woparts.quantity*woparts.price AS linetotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM (probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Third party service: \" AS item, subrepair.charge AS linettotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM probs INNER JOIN subrepair ON probs.id = subrepair.link WHERE (((probs.wolink)<>0) AND ((subrepair.charge)<>0))))]. AS wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN clients AS headoffices ON clients.headoffice = headoffices.id) ON probs.id = wom.probnum) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN projects ON wo.project = projects.id ) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_)) " "ORDER BY wo.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=32));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the Units by P.M. report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Units by P.M.\", \"pmunits.rpt\", \"mgr\", True, 2193, 33;"); q2="SELECT ~CRITERIA AS CRITERIA, pmhead.id, nonclients.company_person AS MAKE, unitmodels.model, units.sn, unitmodels.description AS UNITDESC, units.id1, units.id2, units.id3, clients.company, nonclients.phone, pmhead.description, pmhead.notes, pmhead.nextsrvdate, pmhead.nextsrvmeter, units.lastmeter, pmhead.woconvert, pmhead.repeatevery AS rptmonths_count, pmhead.rptweeks, pmhead.rptdays, units.purchasedate, pmhead.ageyears, pmhead.agemonths, users.initials, users.first, users.last, pmhead.isclient " "FROM ((pmhead LEFT JOIN ((units LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) ON pmhead.link = units.id) LEFT JOIN clients ON units.client = clients.id) LEFT JOIN users ON pmhead.tech = users.id " "WHERE (((pmhead.isclient)=False) AND ((units.client)~CUST) AND ((units.id)~UNIT) AND ((units.model)~MODL)) " "ORDER BY nonclients.company_person, unitmodels.model, units.sn, clients.company;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=33));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the P.M. by Units report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"P.M. by Units\", \"unitspm.rpt\", \"mgr\", True, 2193, 34;"); q2="SELECT ~CRITERIA AS CRITERIA, pmhead.id, nonclients.company_person AS MAKE, unitmodels.model, units.sn, unitmodels.description AS UNITDESC, units.id1, units.id2, units.id3, clients.company, nonclients.phone, pmhead.description, pmhead.notes, pmhead.nextsrvdate, pmhead.nextsrvmeter, units.lastmeter, pmhead.woconvert, pmhead.repeatevery AS rptmonths_count, pmhead.rptweeks, pmhead.rptdays, units.purchasedate, pmhead.ageyears, pmhead.agemonths, users.initials, users.first, users.last, pmhead.isclient " "FROM ((pmhead LEFT JOIN ((units LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) ON pmhead.link = units.id) LEFT JOIN clients ON units.client = clients.id) LEFT JOIN users ON pmhead.tech = users.id " "WHERE (((pmhead.isclient)=False) AND ((units.client)~CUST) AND ((units.id)~UNIT) AND ((units.model)~MODL)) " "ORDER BY nonclients.company_person, unitmodels.model, units.sn, clients.company;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=34));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the P.M. by Client report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"P.M. by Client\", \"clientpm.rpt\", \"mgr\", True, 385, 35;"); q2="SELECT ~CRITERIA AS CRITERIA, clients.company, pmhead.description, pmhead.notes, pmhead.nextsrvdate, pmhead.link AS CLIENTID, pmhead.woconvert, pmhead.repeatevery AS rptmonths_count, pmhead.rptweeks, pmhead.rptdays, pmhead.ageyears, pmhead.agemonths, users.initials, users.first AS TECH_FIRST, users.last AS TECH_LAST " "FROM clients RIGHT JOIN (pmhead LEFT JOIN users ON pmhead.tech = users.id) ON clients.id = pmhead.link " "WHERE (((pmhead.nextsrvdate) Between #~STRT# And #~END_#) AND ((pmhead.link)~CUST) AND ((pmhead.isclient)=True)) " "ORDER BY clients.company;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=35));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the Workorders not invoiced report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Workorders not invoiced\", \"notbilled.rpt\", \"mgr\", True, 385, 36;"); q2=strData="SELECT ~CRITERIA AS CRITERIA, wo.id, clients.company, wo.modified, wo.ourref, wo.clientrefnum, wo.clientcontact, wo.closed, wo.invoice, wo.notes " "FROM probstat RIGHT JOIN (wo LEFT JOIN clients ON wo.client = clients.id) ON probstat.id = wo.status " "WHERE (((wo.modified) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.invoice) Is Null)) " "ORDER BY wo.modified DESC;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=36));",q2); rs->Ex(q); //------------------------------------------------ //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"152\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); nVersion=152; } break; case 152: //update for v1720 added extra security rights items { CString strID,strName,strRights,strHash; long lData; GZK k; //Add new right: //loop through all the group records rs->Query("SELECT groups.* FROM groups;"); do{ rs->FetchField("id",&lData); rs->FetchField("a",&strName); rs->FetchField("b",&strRights); //decrypt the original rights string k.GZDecrypt(&strRights,false); strRights=strRights+"111";//add on the extra right for schedule view //re-'crypt' k.GZEncrypt(&strRights,false); //HASH strHash.Format("%u%s%s",lData,strName,strRights); k.GZHash(&strHash); //save the rights rs->UpdateField("b",&strRights); //save the hash rs->UpdateField("c",&strHash); //save the record if(!rs->SaveRecord()) AfxMessageBox("Error trying to save rights record"); }while(rs->MoveForward()); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"153\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); nVersion=153; } break; case 153: //update for v1720 modified client equipment report query //and added eval field for web server { //"KJB3BoICxnQM9KvUO+1mzQ==" Evaluate 8 chars rs->Ex("ALTER TABLE defaults ADD COLUMN mango TEXT(80);"); rs->Ex("UPDATE defaults SET defaults.mango = \"KJB3BoICxnQM9KvUO+1mzQ\";"); /* How web server mango column works: if = Evaluate then means ready to be evaluated first time webserver runs sets mango to expiry date when expires sets column to Expired and web server stops working */ //ADD EMAIL NOTIFICATION FIELDS TO USERS TABLE (oops forgot to do it earlier) rs->Ex("ALTER TABLE users ADD COLUMN email TEXT(120);"); rs->Ex("ALTER TABLE users ADD COLUMN emailnotify YESNO;"); rs->Ex("ALTER TABLE users ALTER emailnotify SET DEFAULT '0';"); rs->Ex("UPDATE users SET users.emailnotify = False;"); //UPDATE CLIENT EQUIPMENT REPORT QUERY q2="SELECT clients.id, IIf(IsNull([clients].[company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]) AS client, [clients].[first] & \" \" & [clients].[last] AS clientcontact, clients.bizphone, [manufacturers].[company_person] & \" \" & [unitmodels].[model] AS item, units.sn, IIf([units].[boughthere],\"us\",[nonclients].[company_person]) AS vendor, units.purchasedate, units.receipt AS invoice, units.notes, units.description " "FROM (((units LEFT JOIN clients ON units.client = clients.id) LEFT JOIN nonclients ON units.purchasedfrom = nonclients.id) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients AS manufacturers ON unitmodels.manufacturer = manufacturers.id " "WHERE (((clients.id)~CUST) AND ((units.purchasedate) Between #~STRT# And #~END_#) AND ((units.loaner)=False)) " "ORDER BY IIf(IsNull([clients].[company]),[clients].[last] & \", \" & [clients].[first],[clients].[company]);"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=20));",q2); rs->Ex(q); //UPDATE UNIT HISTORY REPORT QUERY q2="SELECT ~USERNAME AS zCurrentUser, probs.id, probs.wolink AS WORKORDERID, probs.brief AS PROBBRIEF, probs.notes " "AS PROBNOTES, Format([start],\"Short Date\") AS servdate, labor.details, clients.company AS clientcompany, " "units.sn, unitmodels.model, users.initials, probs.meter, ztotalparts.totalparts, ztotallabor.totallabor FROM " "[SELECT Sum((labor.hours*rates.rate)+(labor.travhours*travrates.rate)) AS totallabor, probs.id FROM probs INNER " "JOIN (rates INNER JOIN (rates AS travrates INNER JOIN labor ON travrates.id = labor.rate) ON rates.id = labor.rate) " "ON probs.id = labor.link GROUP BY probs.id]. AS ztotallabor RIGHT JOIN ([SELECT IIf(IsNull(Sum(woparts.quantity*woparts.price)), 0,Sum(woparts.quantity*woparts.price)) AS totalparts, " "probs.id FROM probs LEFT JOIN woparts ON probs.id = woparts.link GROUP BY probs.id]. AS ztotalparts RIGHT " "JOIN (users RIGHT JOIN ((labor RIGHT JOIN (((wo RIGHT JOIN probs ON wo.id = probs.wolink) LEFT JOIN units " "ON probs.unit = units.id) LEFT JOIN unitmodels ON units.model = unitmodels.id) ON labor.link = probs.id) LEFT " "JOIN clients ON wo.client = clients.id) ON users.id = labor.tech) ON ztotalparts.id = probs.id) ON " "ztotallabor.id = probs.id WHERE (((probs.unit)~UNIT) AND ((units.sn) Is Not Null) AND ((labor.start) " "Between #~STRT# And #~END_#)) ORDER BY labor.start DESC;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=7));",q2); rs->Ex(q); //UPDATE CALLBACKS BY DATE q="UPDATE rptsmaster SET rptsmaster.x = True " "WHERE (((rptsmaster.id)=2));"; rs->Ex(q); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"154\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.0\";"); nVersion=154; } break; case 154: //update for v1721 { rs->Ex("ALTER TABLE users ADD COLUMN schedrnd YESNO;"); rs->Ex("UPDATE users SET users.schedrnd = True;"); rs->Ex("ALTER TABLE users ADD COLUMN schedoneday YESNO;"); rs->Ex("UPDATE users SET users.schedoneday = False;"); rs->Ex("ALTER TABLE rentals ADD COLUMN ref TEXT(80);"); rs->Ex("ALTER TABLE users ALTER COLUMN rentalprofile TEXT(80);"); rs->Ex("ALTER TABLE users ALTER rentalprofile SET DEFAULT \"(9,9) 42 169 195 103 88 129 0 105 109 0 1 8 7 2 3 4 5 6\";"); rs->Ex("UPDATE users SET users.rentalprofile = '(9,9) 42 169 195 103 88 129 0 105 109 0 1 8 7 2 3 4 5 6';"); //--------------------------------------- //add the LOANERS report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"loaners\", \"loaners.rpt\", \"mgr\", False, 32767, 37;"); //------------------------------------------------ //--------------------------------------- //add the RESPONSE TIME BY PROBLEM report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Response time by problem item (first response)\", \"respprob.rpt\", \"mgr\", True, 399, 38;"); q2="SELECT ~CRITERIA AS CRITERIA, probs.created AS prob_entered, probs.wolink, Min(labor.start) AS First_response, wo.id AS Workorder, wotypes.category AS CategoryName, projects.name AS ProjectName, clients.company AS ClientName, probs.brief " "FROM (((labor LEFT JOIN (wo RIGHT JOIN probs ON wo.id = probs.wolink) ON labor.link = probs.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN projects ON wo.project = projects.id) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.project)~PROJ) AND ((wo.client)~CUST) AND ((wo.type)~CAT_) AND ((labor.tech)~TECH) AND ((wo.quick)=False)) " "GROUP BY probs.created, probs.wolink, wo.id, wotypes.category, projects.name, clients.company, probs.brief, wo.created " "HAVING (((Min(labor.start)) Is Not Null)) " "ORDER BY wo.created DESC , probs.wolink;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=38));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //add the RESPONSE TIME BY WORKORDER report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Response time for standard WO (first response)\", \"respwo.rpt\", \"mgr\", True, 399, 39;"); q2="SELECT ~CRITERIA AS CRITERIA, wo.created AS wo_entered, probs.wolink, Min(labor.start) AS First_response, wo.id AS Workorder, wotypes.category AS CategoryName, projects.name AS ProjectName, clients.company AS ClientName " "FROM (((labor LEFT JOIN (wo RIGHT JOIN probs ON wo.id = probs.wolink) ON labor.link = probs.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN projects ON wo.project = projects.id) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.project)~PROJ) AND ((wo.client)~CUST) AND ((wo.type)~CAT_) AND ((labor.tech)~TECH) AND ((wo.quick)=False)) " "GROUP BY wo.created, probs.wolink, wo.id, wotypes.category, projects.name, clients.company " "HAVING (((Min(labor.start)) Is Not Null)) " "ORDER BY wo.created DESC , probs.wolink;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=39));",q2); rs->Ex(q); //------------------------------------------------ //ADD the tables for ARAS clients //------------------------------------------------ //clients_aras rs->Ex( "CREATE TABLE clients_aras (" "id COUNTER CONSTRAINT PK_clntaras PRIMARY KEY, " "clientlink INTEGER DEFAULT 0," "loginid TEXT(50), " "loginpw TEXT(50), " "view_wo_status YESNO DEFAULT False, " "search_history YESNO DEFAULT False, " "wo_view YESNO DEFAULT False, " "wo_report YESNO DEFAULT False, " "request_service YESNO DEFAULT False, " "view_request_list YESNO DEFAULT False, " "private_notes MEMO, " "last_login_date DATETIME, " "creator INTEGER DEFAULT 0, "//user who created record "created DATETIME, " //date created "modifier INTEGER DEFAULT 0, "//date modified "modified DATETIME " ");"); //------------------------------------------------ //client_requests rs->Ex( "CREATE TABLE client_requests (" "id COUNTER CONSTRAINT PK_clntrqsts PRIMARY KEY, " "clientlink INTEGER DEFAULT 0," "requestor_id INTEGER DEFAULT 0," "workorderid INTEGER DEFAULT 0," "request TEXT(110), " "probdetails MEMO, " "prefertech INTEGER DEFAULT -1," "refnum TEXT(80), " "ournotes MEMO, " "created DATETIME, " //date created "urgency INTEGER DEFAULT 0"//0=not 2=extreme ");"); //------------------------------------------------ //ADD new profile key to user table for ARAS request view screen rs->Ex("ALTER TABLE users ADD COLUMN aras_req_profile TEXT(80);"); rs->Ex("ALTER TABLE users ALTER aras_req_profile SET DEFAULT \"(7,7) 52 76 128 73 217 162 0 0 1 2 3 4 5 6\";"); rs->Ex("UPDATE users SET users.aras_req_profile = '(7,7) 52 76 128 73 217 162 0 0 1 2 3 4 5 6';"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"155\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.7.2.1\";"); nVersion=155; } break; case 155://changed to 156 on Sept 30th 2002 for version 1.9 { //Added field to turn on or off transaction support //true=database execute queries are wrapped in transactions //false=old style pre 1.9 not wrapped in transactions //made it an option in case users have problems //should improve data currency on a busy network rs->Ex("ALTER TABLE defaults ADD COLUMN transact YESNO;"); rs->Ex("UPDATE defaults SET defaults.transact = True;"); //client alternate phone number rs->Ex("ALTER TABLE clients ADD COLUMN phone2 TEXT(40);"); rs->Ex("ALTER TABLE clients ADD COLUMN phone3 TEXT(40);"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"156\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=156; } break; case 156://changed to 157 on Oct 4th 2002 for version 1.9 { //Horizontal grid on main work order list screen //user preference field. Default to true so they //know it's there and we can get all those emails //bitching about it because they don't read the docs and know that //they can turn it off rs->Ex("ALTER TABLE users ADD COLUMN hgrid YESNO;"); rs->Ex("UPDATE users SET users.hgrid = True;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"157\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=157; break; } case 157://changed to 158 on Oct 8th 2002 for version 1.9 { //drop location field in wo which is not used and //add a pmid field rs->Ex("ALTER TABLE wo ADD COLUMN pmid INTEGER;"); rs->Ex("ALTER TABLE wo ALTER pmid SET DEFAULT '0';"); rs->Ex("UPDATE wo SET wo.pmid = 0;"); rs->Ex("ALTER TABLE wo DROP COLUMN location;"); //update pmhead table to include the two new time fields rs->Ex("ALTER TABLE pmhead ADD COLUMN starttime DATETIME;"); rs->Ex("ALTER TABLE pmhead ADD COLUMN endtime DATETIME;"); rs->Ex("UPDATE pmhead SET pmhead.starttime = #10/8/2002 8:0:0#;"); rs->Ex("UPDATE pmhead SET pmhead.endtime = #10/8/2002 9:0:0#;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"158\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=158; break; } case 158://changed to 159 on Oct 9th 2002 for version 1.9 { //-2 now means don't show scheduled tech column in workorder list //where it used to be 0 for that so change all 0's to -2's rs->Ex("UPDATE statusviews SET statusviews.schedtech = -2 " "WHERE (((statusviews.schedtech)=0));"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"159\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=159; break; } case 159://changed to 160 on Oct 11th 2002 for version 1.9 { //add created days column to status views table rs->Ex("ALTER TABLE statusviews ADD COLUMN createddays INTEGER;"); rs->Ex("ALTER TABLE statusviews ALTER createddays SET DEFAULT '0';"); rs->Ex("UPDATE statusviews SET statusviews.createddays = 0;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"160\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=160; break; } case 160://changed to 161 on Oct 12th 2002 for version 1.9 { //Add distance column to labor table rs->Ex("ALTER TABLE labor ADD COLUMN distance REAL;"); rs->Ex("ALTER TABLE labor ALTER distance SET DEFAULT '0';"); rs->Ex("UPDATE labor SET labor.distance = 0;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"161\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=161; break; } case 161://changed to 162 on Oct 12th 2002 for version 1.9 { //Add distance column to labor table rs->Ex("ALTER TABLE clients ADD COLUMN inactive YESNO;"); rs->Ex("ALTER TABLE clients ALTER inactive SET DEFAULT '0';"); rs->Ex("UPDATE clients SET clients.inactive = False;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"162\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=162; break; } case 162://changed to 163 on Oct 12th 2002 for version 1.9 { //Set all woparts.misc to NULL as some may be empty //other changes will ensure it is never set to empty in future //this is just to catch any existing ones. rs->Ex("UPDATE woparts SET woparts.misc = Null WHERE (((woparts.misc)=\"\"));"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"163\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=163; break; } case 163://changed to 164 on Oct 13th 2002 for version 1.9 { //Add subquery field to rptsmaster //required for parts printing on dispatch standard workorder rs->Ex("ALTER TABLE rptsmaster ADD COLUMN subreportquery MEMO;"); //REMOVE ANY OLD RPTS MASTER ENTRIES FOR WORKORDER REPORTS //STANDARD DISPATCH q2="SELECT \"~ESTRATE\" AS estrate, \"~SCHEDTECH\" AS scheduledtech, " "~ESTHOURS AS esthours, IIf(IsNull([clients].[company]),[clients].[last] " "& \", \" & [clients].[first],[clients].[company]) " "AS clientname, IIf(IsNull([clients].[streetaddress]),[clients].[mailaddress],[clients].[streetaddress]) ""& IIf(IsNull([clients].[city]),\"\",Chr(13) " "& [clients].[city]) & IIf(IsNull([clients].[stateprov]),\"\",\", " "\" & [clients].[stateprov] " "& IIf(IsNull([clients].[postal]),\"\",\" " "\" & [clients].[postal])) AS address, \"Work required: " "\" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] " "& \") SN: \" & [units].[sn],\"\") AS probheader, " "\"~REGTO\" AS compname, wo.notes AS wonotes, " "wo.clientrefnum, wo.clientcontact, wo.ourref, " "wo.prob_reported, wo.prob_found, wo.action_taken, " "wo.id AS wonumber, wo.created, labor.details, probs.notes, " "IIf(IsNull(contracts_1.name),[contracts].[name],contracts_1.name) " "AS contractinfo, IIf([probs].[unit]<>0,\"Unit: " "\" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & \" (\" " "& [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS Equipment, wo.starttime AS [Booked for], wo.stoptime " "AS [Booked for END], wo.closed, probs.brief, " "clients.mailaddress, clients.streetaddress, clients.city, " "clients.stateprov, clients.postal, clients.country, " "clients.bizphone, clients.extension, " "clients.technotes, clients.first, clients.last, probstat.notes " "AS STATUS, probstat_1.notes AS ITEMSTATUS, " "projects.name AS PROJNAME, projects.notes AS " "PROJNOTES FROM projects RIGHT JOIN ((((((labor RIGHT " "JOIN (((units RIGHT JOIN probs ON units.id = " "probs.unit) LEFT JOIN unitmodels ON units.model = " "unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer " "= nonclients.id) ON labor.link = probs.id) " "RIGHT JOIN ((wo LEFT JOIN clients ON wo.client " "= clients.id) LEFT JOIN clients AS headoffices " "ON clients.headoffice = headoffices.id) ON probs.wolink " "= wo.id) LEFT JOIN contracts ON clients.contract " "= contracts.id) LEFT JOIN contracts AS contracts_1 " "ON headoffices.contract = contracts_1.id) LEFT " "JOIN probstat ON wo.status = probstat.id) LEFT " "JOIN probstat AS probstat_1 ON probs.status = probstat_1.id) " "ON projects.id = wo.project WHERE (((wo.id)=~WOID)); "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=21));",q2); rs->Ex(q); //***** SUBREPORT ****************** q2="SELECT probs.id, woparts.quantity, woparts.sn, parts.partnumber, " "woparts.misc, parts.description, parts.retail, " "IIf(IsNull(woparts.misc),[parts].[partnumber] " "& \" \" & [parts].[description] & \": \" & [woparts].[quantity] " "& \" @ \" & Format([woparts].[price],\"Currency\") " "& \" ea.\" & IIf(IsNull([woparts].[sn]),\"\",\" sn:\" & [woparts].[sn]) " ", [woparts].[misc] " "& \": \" & [woparts].[quantity] & \" @ \" & Format([woparts].[price],\"Currency\") " "& \" ea.sn:\" & [woparts].[sn] " ") AS item, [woparts].[quantity]*[woparts].[price] " "AS linetotal FROM (woparts RIGHT JOIN " "(probs RIGHT JOIN wo ON probs.wolink = wo.id) ON " "woparts.link = probs.id) LEFT JOIN parts ON woparts.partnum " "= parts.id WHERE (((woparts.quantity) " "Is Not Null) AND ((wo.id)=~WOID));"; q.Format("UPDATE rptsmaster SET rptsmaster.subreportquery = '%s' " "WHERE (((rptsmaster.id)=21));",q2); rs->Ex(q); //------------------------------------------------ //STANDARD BRIEF q2="SELECT \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] " "& \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS probheader, \"~REGTO\" AS compname, wom.probnum, " "wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, " "wom.PROBBRIEF, wom.item, wom.linetotal, " "wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created " "AS wodate, wo.id AS wonumber, wo.invoice, " "wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, " "clients.billheadoffice, clients.first, clients.last, " "clients.mailaddress, clients.streetaddress, " "clients.city, clients.stateprov, clients.postal, " "clients.country, clients.bizphone, clients.extension, " "clients.fax, clients.email, [clients].[company] " "AS clientname, IIf(IsNull([headoffices].[company]),[headoffices].[last] " "& \", \" & [headoffices].[first],[headoffices].[company]) " "AS headname, wom.details, " "wom.STARTDATE, wom.STOPDATE, projects.name " "AS PROJNAME, projects.notes AS PROJNOTES FROM " "(((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT " "\"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum " "AS TRAVPN, probs.notes AS PROBNOTES, probs.brief " "AS PROBBRIEF, probs.id AS probnum, probs.wolink " "AS wonum, \"Service: \" & users.first & \" \" & " "users.last & \" - \" & IIf(labor.hours>0,labor.hours " "& \" hrs. @ \" & Format(rates.rate,\"Currency\") & \" " "(pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" " "(\" & labor.nchours & \" hrs. no charge)\",\"\") " "& IIf(labor.travhours>0,\", \" & labor.travhours & \" " "hrs. travel @ \" & Format(travelrates.rate,\"Currency\") " "& IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" " "& travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) " "AS linetotal,labor.details, labor.start AS STARTDATE, " "labor.stop as STOPDATE FROM users INNER JOIN " "(rates AS travelrates INNER JOIN (rates INNER JOIN " "(labor INNER JOIN probs ON labor.link = probs.id) " "ON rates.id = labor.rate) ON travelrates.id = labor.travrate) " "ON users.id = labor.tech WHERE (((probs.wolink)=~WOID)) " "UNION ALL (SELECT \"2\" AS ctype, " "\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, " "probs.brief AS PROBBRIEF, probs.id AS probnum, " " probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc),parts.partnumber " "& \" \" & parts.description " "& \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") " "& \" ea.(sn:\" & woparts.sn " "& \")\",woparts.misc & \": \" & woparts.quantity " "& \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" " "& woparts.sn & \")\") AS item, woparts.quantity*woparts.price " "AS linetotal,\"\" AS details, #03/12/1968# " "AS STARTDATE, #03/12/1968# AS STOPDATE FROM " "(probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id " "WHERE (((probs.wolink)=~WOID)) UNION ALL (SELECT " " \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes " "AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id " "AS probnum, probs.wolink as wonum, \"Third party " "service: \" AS item, subrepair.charge AS linettotal, " "\"\" AS details, #03/12/1968# AS STARTDATE, #03/12/1968# " "AS STOPDATE FROM probs INNER JOIN subrepair " "ON probs.id = subrepair.link WHERE (((probs.wolink)=~WOID) " "AND ((subrepair.charge)<>0))))]. AS " "wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN " "clients ON wo.client = clients.id) LEFT JOIN clients " "AS headoffices ON clients.headoffice = headoffices.id) " "ON probs.id = wom.probnum) ON units.id = probs.unit) " "LEFT JOIN unitmodels ON units.model = unitmodels.id) " "LEFT JOIN nonclients ON unitmodels.manufacturer " "= nonclients.id) LEFT JOIN projects ON " "wo.project = projects.id ORDER BY wom.STARTDATE DESC; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=1));",q2); rs->Ex(q); //------------------------------------------------ //STANDARD COMPLETED q2="SELECT \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] " "& \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS probheader, \"~REGTO\" AS compname, wom.probnum, " "wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, " "wom.PROBBRIEF, wom.item, wom.linetotal, " "wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created " "AS wodate, wo.id AS wonumber, wo.invoice, " "wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, " "clients.billheadoffice, clients.first, clients.last, " "clients.mailaddress, clients.streetaddress, " "clients.city, clients.stateprov, clients.postal, " "clients.country, clients.bizphone, clients.extension, " "clients.fax, clients.email, [clients].[company] " "AS clientname, IIf(IsNull([headoffices].[company]),[headoffices].[last] " "& \", \" & [headoffices].[first],[headoffices].[company]) " "AS headname, wom.details, " "wom.STARTDATE, wom.STOPDATE, projects.name " "AS PROJNAME, projects.notes AS PROJNOTES FROM " "(((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT " "\"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum " "AS TRAVPN, probs.notes AS PROBNOTES, probs.brief " "AS PROBBRIEF, probs.id AS probnum, probs.wolink " "AS wonum, \"Service: \" & users.first & \" \" & " "users.last & \" - \" & IIf(labor.hours>0,labor.hours " "& \" hrs. @ \" & Format(rates.rate,\"Currency\") & \" " "(pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" " "(\" & labor.nchours & \" hrs. no charge)\",\"\") " "& IIf(labor.travhours>0,\", \" & labor.travhours & \" " "hrs. travel @ \" & Format(travelrates.rate,\"Currency\") " "& IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" " "& travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) " "AS linetotal,labor.details, labor.start AS STARTDATE, " "labor.stop as STOPDATE FROM users INNER JOIN " "(rates AS travelrates INNER JOIN (rates INNER JOIN " "(labor INNER JOIN probs ON labor.link = probs.id) " "ON rates.id = labor.rate) ON travelrates.id = labor.travrate) " "ON users.id = labor.tech WHERE (((probs.wolink)=~WOID)) " "UNION ALL (SELECT \"2\" AS ctype, " "\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, " "probs.brief AS PROBBRIEF, probs.id AS probnum, " " probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc),parts.partnumber " "& \" \" & parts.description " "& \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") " "& \" ea.(sn:\" & woparts.sn " "& \")\",woparts.misc & \": \" & woparts.quantity " "& \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" " "& woparts.sn & \")\") AS item, woparts.quantity*woparts.price " "AS linetotal,\"\" AS details, #03/12/1968# " "AS STARTDATE, #03/12/1968# AS STOPDATE FROM " "(probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id " "WHERE (((probs.wolink)=~WOID)) UNION ALL (SELECT " " \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes " "AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id " "AS probnum, probs.wolink as wonum, \"Third party " "service: \" AS item, subrepair.charge AS linettotal, " "\"\" AS details, #03/12/1968# AS STARTDATE, #03/12/1968# " "AS STOPDATE FROM probs INNER JOIN subrepair " "ON probs.id = subrepair.link WHERE (((probs.wolink)=~WOID) " "AND ((subrepair.charge)<>0))))]. AS " "wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN " "clients ON wo.client = clients.id) LEFT JOIN clients " "AS headoffices ON clients.headoffice = headoffices.id) " "ON probs.id = wom.probnum) ON units.id = probs.unit) " "LEFT JOIN unitmodels ON units.model = unitmodels.id) " "LEFT JOIN nonclients ON unitmodels.manufacturer " "= nonclients.id) LEFT JOIN projects ON " "wo.project = projects.id ORDER BY wom.STARTDATE DESC; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=19));",q2); rs->Ex(q); //------------------------------------------------ //QUICK DISPATCH WORKORDER q2="SELECT IIf(IsNull([clients].[company]),[clients].[last] " "& \", \" & [clients].[first],[clients].[company]) " "AS clientname, IIf(IsNull([clients].[streetaddress]),[clients].[mailaddress],[clients].[streetaddress]) ""& IIf(IsNull([clients].[city]),\"\",[clients].[city]) " "& IIf(IsNull([clients].[stateprov]),\"\",\", " "\" & [clients].[stateprov] & IIf(IsNull([clients].[postal]),\"\",\" " "\" & [clients].[postal])) AS address, " "\"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & " "\" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS probheader, \"~REGTO\" AS compname, wo.id " "AS wonumber, wo.created, labor.details, probs.notes, " "IIf(IsNull(contracts_1.name),[contracts].[name],contracts_1.name) " "AS contractinfo, IIf([probs].[unit]<>0,\"Unit: " "\" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] " "& \") SN: \" & [units].[sn],\"\") AS " "Equipment, wo.starttime AS [Booked for], probs.brief, " "clients.mailaddress, clients.streetaddress, " "clients.city, clients.stateprov, clients.postal, clients.country, " "clients.bizphone, clients.extension, " "clients.technotes, clients.first, clients.last, " "wo.clientrefnum, wo.ourref, wo.clientcontact FROM " "(((labor RIGHT JOIN (((units RIGHT JOIN probs ON " "units.id = probs.unit) LEFT JOIN unitmodels ON units.model " "= unitmodels.id) LEFT JOIN nonclients ON " "unitmodels.manufacturer = nonclients.id) ON labor.link " "= probs.id) RIGHT JOIN ((wo LEFT JOIN clients " "ON wo.client = clients.id) LEFT JOIN clients AS headoffices " "ON clients.headoffice = headoffices.id) " "ON probs.wolink = wo.id) LEFT JOIN contracts ON clients.contract " "= contracts.id) LEFT JOIN contracts " "AS contracts_1 ON headoffices.contract = contracts_1.id " "WHERE (((wo.id)=~WOID));"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=22));",q2); rs->Ex(q); //------------------------------------------------ //QUICK COMPLETED FORMAT WORKORDER REPORT q2="SELECT \"~REGTO\" AS zCompName, wo.id, wo.clientrefnum, " "wo.clientcontact, clients.company AS clientcompany, " "Format(wo.closed,\"Short Date\") AS wodate, " "[users]![first] & \" \" & [users]![last] AS wotech, " "labor.hours, labor.travhours, labor.nchours, rates_1.name " "AS workrate, rates.name AS travrate, labor.start " "AS starttime, labor.stop AS stoptime, wo.invoice, " "labor.details, wo.onsite FROM (((users " "RIGHT JOIN (labor RIGHT JOIN (wo LEFT JOIN probs ON " "wo.id = probs.wolink) ON labor.link = probs.id) " "ON users.id = labor.tech) LEFT JOIN clients ON wo.client " "= clients.id) LEFT JOIN rates ON labor.travrate " "= rates.id) LEFT JOIN rates AS rates_1 ON " "labor.rate = rates_1.id WHERE (((wo.id)=~WOID)); "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=0));",q2); rs->Ex(q); //------------------------------------------------ //fixup the dispatch report recordset fields rs->Ex("UPDATE rptsmaster SET rptsmaster.recordset = \"wostandard\" " "WHERE (((rptsmaster.id)=21));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.recordset = \"woquick\" " "WHERE (((rptsmaster.id)=22));"); //Fix the workorder virtual names so they are //the same as the original menu commands that called them rs->Ex("UPDATE rptsmaster SET rptsmaster.virtualname = \"&Dispatch format work order\" " "WHERE (((rptsmaster.id)=22));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.virtualname = \"&Completed work order\" " "WHERE (((rptsmaster.id)=0));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.virtualname = \"&Dispatch work order\" " "WHERE (((rptsmaster.id)=21));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.virtualname = \"&Brief completed work order\" " "WHERE (((rptsmaster.id)=1));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.virtualname = \"D&etailed completed work order\" " "WHERE (((rptsmaster.id)=19));"); //Add the subreport filename field rs->Ex("ALTER TABLE rptsmaster ADD COLUMN subfilename TEXT(255);"); rs->Ex("UPDATE rptsmaster SET rptsmaster.subfilename = \"wodispstpartssub.rpt\" " "WHERE (((rptsmaster.id)=21));"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"164\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=164; break; } case 164://changed to 165 on Oct 14th 2002 for version 1.9 { //Add cost of parts to woparts //this is used to record cost at time of use rs->Ex("ALTER TABLE woparts ADD COLUMN cost CURRENCY;"); rs->Ex("ALTER TABLE woparts ALTER cost SET DEFAULT '0';"); rs->Ex("UPDATE woparts SET woparts.cost = 0;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"165\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=165; break; } case 165://changed to 166 on Oct 14th 2002 for version 1.9 { /* Add new fields for rptsusers long m_lPaperOrientation; long m_lPaperSize; long m_lPaperSource; long m_lDuplexType; */ rs->Ex("ALTER TABLE rptsusers ADD COLUMN porient INTEGER;"); rs->Ex("ALTER TABLE rptsusers ALTER porient SET DEFAULT '0';"); rs->Ex("UPDATE rptsusers SET rptsusers.porient = 0;"); rs->Ex("ALTER TABLE rptsusers ADD COLUMN psize INTEGER;"); rs->Ex("ALTER TABLE rptsusers ALTER psize SET DEFAULT '0';"); rs->Ex("UPDATE rptsusers SET rptsusers.psize = 0;"); rs->Ex("ALTER TABLE rptsusers ADD COLUMN psource INTEGER;"); rs->Ex("ALTER TABLE rptsusers ALTER psource SET DEFAULT '0';"); rs->Ex("UPDATE rptsusers SET rptsusers.psource = 0;"); rs->Ex("ALTER TABLE rptsusers ADD COLUMN pduplex INTEGER;"); rs->Ex("ALTER TABLE rptsusers ALTER pduplex SET DEFAULT '0';"); rs->Ex("UPDATE rptsusers SET rptsusers.pduplex = 0;"); rs->Ex("ALTER TABLE rptsusers DROP COLUMN devmode;"); rs->Ex("ALTER TABLE rptsusers DROP COLUMN devmodesize;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"166\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=166; break; } case 166://changed to 167 on Oct 16th 2002 for version 1.9 { //--------------------------------------- /* Add new wodispst2.rpt Dispatch work order (with labor) */ rs->Ex("INSERT INTO rptsmaster ( virtualname, filename,subfilename, recordset, x, criteriafields, id ) " "SELECT \"Dispatch work order (with &labor)\", \"wodispst2.rpt\", \"wodispstpartssub.rpt\", \"wostandard\", False, 32767, 40;"); q2="SELECT \"~ESTRATE\" AS estrate, \"~SCHEDTECH\" AS scheduledtech, " "~ESTHOURS AS esthours, IIf(IsNull([clients].[company]),[clients].[last] " "& \", \" & [clients].[first],[clients].[company]) " "AS clientname, IIf(IsNull([clients].[streetaddress]),[clients].[mailaddress],[clients].[streetaddress]) ""& IIf(IsNull([clients].[city]),\"\",Chr(13) " "& [clients].[city]) & IIf(IsNull([clients].[stateprov]),\"\",\", " "\" & [clients].[stateprov] " "& IIf(IsNull([clients].[postal]),\"\",\" " "\" & [clients].[postal])) AS address, \"Work required: " "\" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] " "& \") SN: \" & [units].[sn],\"\") AS probheader, " "\"~REGTO\" AS compname, wo.notes AS wonotes, " "wo.clientrefnum, wo.clientcontact, wo.ourref, " "wo.prob_reported, wo.prob_found, wo.action_taken, " "wo.id AS wonumber, wo.created, labor.details, probs.notes, " "IIf(IsNull(contracts_1.name),[contracts].[name],contracts_1.name) " "AS contractinfo, IIf([probs].[unit]<>0,\"Unit: " "\" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] & \" (\" " "& [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS Equipment, wo.starttime AS [Booked for], wo.stoptime " "AS [Booked for END], wo.closed, probs.brief, " "clients.mailaddress, clients.streetaddress, clients.city, " "clients.stateprov, clients.postal, clients.country, " "clients.bizphone, clients.extension, " "clients.technotes, clients.first, clients.last, probstat.notes " "AS STATUS, probstat_1.notes AS ITEMSTATUS, " "projects.name AS PROJNAME, projects.notes AS " "PROJNOTES, users.first, users.last, users.initials, " "labor.hours, labor.nchours, labor.travhours, labor.start, " "labor.stop, labor.distance FROM (projects " "RIGHT JOIN ((((((labor RIGHT JOIN (((units RIGHT " "JOIN probs ON units.id = probs.unit) LEFT JOIN " "unitmodels ON units.model = unitmodels.id) LEFT JOIN " "nonclients ON unitmodels.manufacturer = nonclients.id) " "ON labor.link = probs.id) RIGHT JOIN ((wo " "LEFT JOIN clients ON wo.client = clients.id) LEFT " "JOIN clients AS headoffices ON clients.headoffice " "= headoffices.id) ON probs.wolink = wo.id) LEFT JOIN " "contracts ON clients.contract = contracts.id) LEFT " "JOIN contracts AS contracts_1 ON headoffices.contract " "= contracts_1.id) LEFT JOIN probstat ON wo.status " "= probstat.id) LEFT JOIN probstat AS probstat_1 " "ON probs.status = probstat_1.id) ON projects.id " "= wo.project) LEFT JOIN users ON labor.tech = " "users.id WHERE (((wo.id)=~WOID));"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=40));",q2); rs->Ex(q); //subreport query q2="SELECT probs.id, woparts.quantity, woparts.sn, parts.partnumber, " "woparts.misc, parts.description, parts.retail, " "IIf(IsNull(woparts.misc),[parts].[partnumber] " "& \" \" & [parts].[description] & \": \" & [woparts].[quantity] " "& \" @ \" & Format([woparts].[price],\"Currency\") " "& \" ea.\" & IIf(IsNull([woparts].[sn]),\"\",\" " "sn:\" & [woparts].[sn]) , [woparts].[misc] " "& \": \" & [woparts].[quantity] & \" @ \" & Format([woparts].[price],\"Currency\") " "& \" ea.sn:\" & [woparts].[sn] " ") AS item, [woparts].[quantity]*[woparts].[price] " "AS linetotal FROM (woparts RIGHT JOIN (probs " "RIGHT JOIN wo ON probs.wolink = wo.id) ON woparts.link " "= probs.id) LEFT JOIN parts ON woparts.partnum " "= parts.id WHERE (((woparts.quantity) Is Not Null) " "AND ((wo.id)=~WOID));"; q.Format("UPDATE rptsmaster SET rptsmaster.subreportquery = '%s' " "WHERE (((rptsmaster.id)=40));",q2); rs->Ex(q); //------------------------------------------------ //---------- ADD DISPLAY ORDER FIELD TO RPTS MASTER rs->Ex("ALTER TABLE rptsmaster ADD COLUMN wodisplayorder INTEGER;"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 1 " "WHERE (((rptsmaster.virtualname)=\"&Dispatch format work order\"));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 2 " "WHERE (((rptsmaster.virtualname)=\"&Completed work order\"));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 3 " "WHERE (((rptsmaster.virtualname)=\"&Dispatch work order\"));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 4 " "WHERE (((rptsmaster.virtualname)=\"Dispatch work order (with &labor)\"));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 5 " "WHERE (((rptsmaster.virtualname)=\"&Brief completed work order\"));"); rs->Ex("UPDATE rptsmaster SET rptsmaster.wodisplayorder = 6 " "WHERE (((rptsmaster.virtualname)=\"D&etailed completed work order\"));"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"167\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=167; break; } case 167: { //Addition of client address book Report rs->Ex("INSERT INTO rptsmaster ( virtualname, filename, recordset, x, criteriafields, id ) " "SELECT \"Client address book\", \"clntadd.rpt\", \"mgr\", True, 32767, 41;"); q2="SELECT clients.*, HEADS.* FROM clients LEFT JOIN clients " "AS HEADS ON clients.headoffice = HEADS.id WHERE " "(((clients.id)~CUST)) ORDER BY clients.company; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=41));",q2); rs->Ex(q); //Set STATUS column in statusviews to -1 if it was previously 1 as -1 //now means any status where 1 used to mean any status q.Format("UPDATE statusviews SET statusviews.status = -1 WHERE (((statusviews.status)=1));"); rs->Ex(q); //10/26/2002 //set assigntech to correct value on old quick work orders q="UPDATE labor RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) " "ON labor.link = probs.id SET wo.assigntech = [labor].[tech] " "WHERE (((wo.quick)=True) AND ((wo.assigntech)=-1));"; rs->Ex(q); //Add aras_client field to rptsmaster rs->Ex("ALTER TABLE rptsmaster ADD COLUMN client_aras YESNO;"); rs->Ex("ALTER TABLE rptsmaster ALTER client_aras SET DEFAULT '-1';"); rs->Ex("UPDATE rptsmaster SET rptsmaster.client_aras = True;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"168\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.0.0\";"); nVersion=168; //buptodate=true;//<<==========CRITICAL!!!!!, should be at end of last case statement only break; } case 168: { //Changed ....... rs->Ex("ALTER TABLE probs ALTER COLUMN meter INTEGER;"); //Update report 31 to fix bug in query causing part descriptions to be blank q2="SELECT ~CRITERIA AS CRITERIA, wo.id AS wonumber, \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) & \"Unit: \" & [nonclients].[company_person] & \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") AS probheader, \"test\" AS compname, wom.probnum, wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, wom.PROBBRIEF, wom.item, wom.linetotal, wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created AS wodate, wo.invoice, wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, clients.bizphone, clients.extension, clients.fax, clients.email, clients.company AS clientname, wom.details, wom.START, wom.STOP,wom.REGHOURS, wom.TRAVHOURS, wom.NCHOURS, projects.name AS PROJNAME, projects.notes AS PROJNOTES, wo.client, wo.project, wo.type, wotypes.category AS CATEGORY " "FROM ((((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT \"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink AS wonum, \"Service: \" & users.first & \" \" & users.last & \" - \" & IIf(labor.hours>0,labor.hours & \" hrs. @ \" & Format(rates.rate,\"Currency\") & \" (pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" (\" & labor.nchours & \" hrs. no charge)\",\"\") & IIf(labor.travhours>0,\", \" & labor.travhours & \" hrs. travel @ \" & Format(travelrates.rate,\"Currency\") & IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" & travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) AS linetotal, labor.details , labor.start AS START, labor.stop AS STOP, labor.hours AS REGHOURS, labor.travhours AS TRAVHOURS, labor.nchours as NCHOURS FROM users INNER JOIN (rates AS travelrates INNER JOIN (rates INNER JOIN (labor INNER JOIN probs ON labor.link = probs.id) ON rates.id = labor.rate) ON travelrates.id = labor.travrate) ON users.id = labor.tech WHERE (((probs.wolink)<>0)) " " UNION ALL (SELECT \"2\" AS ctype, \"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc), parts.partnumber & \" \" & parts.description & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") & \" ea.(sn:\" & woparts.sn & \")\",woparts.misc & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" & woparts.sn & \")\") AS item, woparts.quantity*woparts.price AS linetotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM (probs INNER JOIN woparts ON probs.id = woparts.link) " " LEFT JOIN parts ON woparts.partnum = parts.id WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Third party service: \" AS item, subrepair.charge AS linettotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM probs INNER JOIN subrepair ON probs.id = subrepair.link WHERE (((probs.wolink)<>0) AND ((subrepair.charge)<>0))))]. AS wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN clients AS headoffices ON clients.headoffice = headoffices.id) ON probs.id = wom.probnum) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN projects ON wo.project = projects.id ) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_)) " "ORDER BY wo.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=31));",q2); rs->Ex(q); //************* change any client aras logins that match ayanova user logins ********** CString strReportDupes,str; CString sLoginARAS,sLoginARASHash,sCompany,sNewLogin; GZK k; long l=0; long lARASID=0; //check for and zap any aras client login names that match AyaNova login names //loop through all aras login names //for each that hashes out to same as ayanova login name, change login name to prepend unique string q="SELECT clients.company AS COMP1, clients_aras.loginid, " "clients_aras.id AS ARASID FROM clients_aras LEFT " "JOIN clients ON clients_aras.clientlink = clients.id " "ORDER BY clients.company, clients_aras.loginid;"; rs2->QueryReadOnly(q); if(!rs2->IsEmpty()) { do{ rs2->FetchField("loginid",&sLoginARAS); sLoginARASHash=sLoginARAS; k.GZHash(&sLoginARASHash); q.Format("SELECT users.login FROM users WHERE (((users.login)=\"%s\"));",sLoginARASHash); rs3->QueryReadOnly(q); if(!rs3->IsEmpty())//This ARAS client login matches AyaNova login { l++; sNewLogin.Format("Temporary%u",l); rs2->FetchField("COMP1",&sCompany); str.Format("Client %s ARAS login account %s changed to %s\r\n",sCompany,sLoginARAS,sNewLogin); strReportDupes+=str; rs2->FetchField("ARASID",&lARASID); q.Format("UPDATE clients_aras SET clients_aras.loginid = \"%s\" " "WHERE (((clients_aras.id) = %u ));",sNewLogin,lARASID); rs->Ex(q); } }while(rs2->MoveForward()); } //Check for duplicate ARAS client login names q="SELECT clients_aras.loginid, clients_aras.id AS ARASID, clients.company AS COMP1 " "FROM clients_aras LEFT JOIN clients ON " "clients_aras.clientlink = clients.id WHERE (((clients_aras.loginid) " "In (SELECT [loginid] FROM [clients_aras] " "As Tmp GROUP BY [loginid] HAVING Count(*)>1 " "))) ORDER BY clients_aras.loginid;"; rs2->QueryReadOnly(q); if(!rs2->IsEmpty())//there are dupes { do{ l++; sNewLogin.Format("Temporary%u",l); rs2->FetchField("COMP1",&sCompany); str.Format("Client %s ARAS login account %s changed to %s\r\n",sCompany,sLoginARAS,sNewLogin); strReportDupes+=str; rs2->FetchField("ARASID",&lARASID); q.Format("UPDATE clients_aras SET clients_aras.loginid = \"%s\" " "WHERE (((clients_aras.id) = %u ));",sNewLogin,lARASID); rs->Ex(q); }while(rs2->MoveForward()); } if(!strReportDupes.IsEmpty()) { strReportDupes= "******** READ THIS CAREFULLY ********\r\n" "The following client(s) ARAS login ID's we're changed for security reasons.\r\n\r\n" "You should save this information now and change them after the update has\r\n" "completed. (otherwise they will not be able to log in)\r\n\r\n" "To save this information click on the copy all text.. button, open a word processor or\r\n" "Microsoft Notepad and paste. You can then save / print this list.\r\n" "=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-\r\n"+strReportDupes; m_pApp->ShowStuff(strReportDupes); strReportDupes.Empty(); } //****************************************************************************** //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"169\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.3.0\";"); nVersion=169; //buptodate=true;//<<==========CRITICAL!!!!!, should be at end of last case statement only break; } case 169: { //------------------------------------------------ //REMOVE Hrs. FROM WORK ORDER REPORT QUERIES //STANDARD BRIEF q2="SELECT \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] " "& \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS probheader, \"~REGTO\" AS compname, wom.probnum, " "wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, " "wom.PROBBRIEF, wom.item, wom.linetotal, " "wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created " "AS wodate, wo.id AS wonumber, wo.invoice, " "wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, " "clients.billheadoffice, clients.first, clients.last, " "clients.mailaddress, clients.streetaddress, " "clients.city, clients.stateprov, clients.postal, " "clients.country, clients.bizphone, clients.extension, " "clients.fax, clients.email, [clients].[company] " "AS clientname, IIf(IsNull([headoffices].[company]),[headoffices].[last] " "& \", \" & [headoffices].[first],[headoffices].[company]) " "AS headname, wom.details, " "wom.STARTDATE, wom.STOPDATE, projects.name " "AS PROJNAME, projects.notes AS PROJNOTES FROM " "(((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT " "\"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum " "AS TRAVPN, probs.notes AS PROBNOTES, probs.brief " "AS PROBBRIEF, probs.id AS probnum, probs.wolink " "AS wonum, \"Service: \" & users.first & \" \" & " "users.last & \" - \" & IIf(labor.hours>0,labor.hours " "& \" @ \" & Format(rates.rate,\"Currency\") & \" " "(pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" " "(\" & labor.nchours & \" no charge)\",\"\") " "& IIf(labor.travhours>0,\", \" & labor.travhours & \" " "travel @ \" & Format(travelrates.rate,\"Currency\") " "& IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" " "& travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) " "AS linetotal,labor.details, labor.start AS STARTDATE, " "labor.stop as STOPDATE FROM users INNER JOIN " "(rates AS travelrates INNER JOIN (rates INNER JOIN " "(labor INNER JOIN probs ON labor.link = probs.id) " "ON rates.id = labor.rate) ON travelrates.id = labor.travrate) " "ON users.id = labor.tech WHERE (((probs.wolink)=~WOID)) " "UNION ALL (SELECT \"2\" AS ctype, " "\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, " "probs.brief AS PROBBRIEF, probs.id AS probnum, " " probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc),parts.partnumber " "& \" \" & parts.description " "& \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") " "& \" ea.(sn:\" & woparts.sn " "& \")\",woparts.misc & \": \" & woparts.quantity " "& \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" " "& woparts.sn & \")\") AS item, woparts.quantity*woparts.price " "AS linetotal,\"\" AS details, #03/12/1968# " "AS STARTDATE, #03/12/1968# AS STOPDATE FROM " "(probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id " "WHERE (((probs.wolink)=~WOID)) UNION ALL (SELECT " " \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes " "AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id " "AS probnum, probs.wolink as wonum, \"Third party " "service: \" AS item, subrepair.charge AS linettotal, " "\"\" AS details, #03/12/1968# AS STARTDATE, #03/12/1968# " "AS STOPDATE FROM probs INNER JOIN subrepair " "ON probs.id = subrepair.link WHERE (((probs.wolink)=~WOID) " "AND ((subrepair.charge)<>0))))]. AS " "wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN " "clients ON wo.client = clients.id) LEFT JOIN clients " "AS headoffices ON clients.headoffice = headoffices.id) " "ON probs.id = wom.probnum) ON units.id = probs.unit) " "LEFT JOIN unitmodels ON units.model = unitmodels.id) " "LEFT JOIN nonclients ON unitmodels.manufacturer " "= nonclients.id) LEFT JOIN projects ON " "wo.project = projects.id ORDER BY wom.STARTDATE DESC; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=1));",q2); rs->Ex(q); //------------------------------------------------ //STANDARD COMPLETED q2="SELECT \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) " "& \"Unit: \" & [nonclients].[company_person] " "& \" \" & [unitmodels].[description] " "& \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") " "AS probheader, \"~REGTO\" AS compname, wom.probnum, " "wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, " "wom.PROBBRIEF, wom.item, wom.linetotal, " "wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created " "AS wodate, wo.id AS wonumber, wo.invoice, " "wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, " "clients.billheadoffice, clients.first, clients.last, " "clients.mailaddress, clients.streetaddress, " "clients.city, clients.stateprov, clients.postal, " "clients.country, clients.bizphone, clients.extension, " "clients.fax, clients.email, [clients].[company] " "AS clientname, IIf(IsNull([headoffices].[company]),[headoffices].[last] " "& \", \" & [headoffices].[first],[headoffices].[company]) " "AS headname, wom.details, " "wom.STARTDATE, wom.STOPDATE, projects.name " "AS PROJNAME, projects.notes AS PROJNOTES FROM " "(((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT " "\"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum " "AS TRAVPN, probs.notes AS PROBNOTES, probs.brief " "AS PROBBRIEF, probs.id AS probnum, probs.wolink " "AS wonum, \"Service: \" & users.first & \" \" & " "users.last & \" - \" & IIf(labor.hours>0,labor.hours " "& \" @ \" & Format(rates.rate,\"Currency\") & \" " "(pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" " "(\" & labor.nchours & \" no charge)\",\"\") " "& IIf(labor.travhours>0,\", \" & labor.travhours & \" " "travel @ \" & Format(travelrates.rate,\"Currency\") " "& IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" " "& travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) " "AS linetotal,labor.details, labor.start AS STARTDATE, " "labor.stop as STOPDATE FROM users INNER JOIN " "(rates AS travelrates INNER JOIN (rates INNER JOIN " "(labor INNER JOIN probs ON labor.link = probs.id) " "ON rates.id = labor.rate) ON travelrates.id = labor.travrate) " "ON users.id = labor.tech WHERE (((probs.wolink)=~WOID)) " "UNION ALL (SELECT \"2\" AS ctype, " "\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, " "probs.brief AS PROBBRIEF, probs.id AS probnum, " " probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc),parts.partnumber " "& \" \" & parts.description " "& \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") " "& \" ea.(sn:\" & woparts.sn " "& \")\",woparts.misc & \": \" & woparts.quantity " "& \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" " "& woparts.sn & \")\") AS item, woparts.quantity*woparts.price " "AS linetotal,\"\" AS details, #03/12/1968# " "AS STARTDATE, #03/12/1968# AS STOPDATE FROM " "(probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id " "WHERE (((probs.wolink)=~WOID)) UNION ALL (SELECT " " \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes " "AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id " "AS probnum, probs.wolink as wonum, \"Third party " "service: \" AS item, subrepair.charge AS linettotal, " "\"\" AS details, #03/12/1968# AS STARTDATE, #03/12/1968# " "AS STOPDATE FROM probs INNER JOIN subrepair " "ON probs.id = subrepair.link WHERE (((probs.wolink)=~WOID) " "AND ((subrepair.charge)<>0))))]. AS " "wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN " "clients ON wo.client = clients.id) LEFT JOIN clients " "AS headoffices ON clients.headoffice = headoffices.id) " "ON probs.id = wom.probnum) ON units.id = probs.unit) " "LEFT JOIN unitmodels ON units.model = unitmodels.id) " "LEFT JOIN nonclients ON unitmodels.manufacturer " "= nonclients.id) LEFT JOIN projects ON " "wo.project = projects.id ORDER BY wom.STARTDATE DESC; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=19));",q2); rs->Ex(q); //------------------------------------------------ //WORKORDERS BRIEF q2="SELECT ~CRITERIA AS CRITERIA, wo.id AS wonumber, \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) & \"Unit: \" & [nonclients].[company_person] & \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") AS probheader, \"test\" AS compname, wom.probnum, wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, wom.PROBBRIEF, wom.item, wom.linetotal, wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created AS wodate, wo.invoice, wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, clients.bizphone, clients.extension, clients.fax, clients.email, clients.company AS clientname, wom.details, wom.START, wom.STOP,wom.REGHOURS, wom.TRAVHOURS, wom.NCHOURS, projects.name AS PROJNAME, projects.notes AS PROJNOTES, wo.client, wo.project, wo.type, wotypes.category AS CATEGORY " "FROM ((((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT \"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink AS wonum, \"Service: \" & users.first & \" \" & users.last & \" - \" & IIf(labor.hours>0,labor.hours & \" @ \" & Format(rates.rate,\"Currency\") & \" (pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" (\" & labor.nchours & \" no charge)\",\"\") & IIf(labor.travhours>0,\", \" & labor.travhours & \" travel @ \" & Format(travelrates.rate,\"Currency\") & IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" & travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) AS linetotal, labor.details , labor.start AS START, labor.stop AS STOP, labor.hours AS REGHOURS, labor.travhours AS TRAVHOURS, labor.nchours as NCHOURS FROM users INNER JOIN (rates AS travelrates INNER JOIN (rates INNER JOIN (labor INNER JOIN probs ON labor.link = probs.id) ON rates.id = labor.rate) ON travelrates.id = labor.travrate) ON users.id = labor.tech WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"2\" AS ctype, \"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Parts: \" & IIf(woparts.misc= \"\",parts.partnumber & \" \" & parts.description & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") & \" ea.(sn:\" & woparts.sn & \")\",woparts.misc & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" & woparts.sn & \")\") AS item, woparts.quantity*woparts.price AS linetotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM (probs INNER JOIN woparts ON probs.id = woparts.link) " "LEFT JOIN parts ON woparts.partnum = parts.id WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Third party service: \" AS item, subrepair.charge AS linettotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM probs INNER JOIN subrepair ON probs.id = subrepair.link WHERE (((probs.wolink)<>0) AND ((subrepair.charge)<>0))))]. AS wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN clients AS headoffices ON clients.headoffice = headoffices.id) ON probs.id = wom.probnum) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN projects ON wo.project = projects.id ) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_)) " "ORDER BY wo.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=32));",q2); rs->Ex(q); //WORKORDERS DETAILED q2="SELECT ~CRITERIA AS CRITERIA, wo.id AS wonumber, \"Work required: \" & [probs].[brief] & IIf([probs].[unit]<>0,Chr(13) & \"Unit: \" & [nonclients].[company_person] & \" \" & [unitmodels].[description] & \" (\" & [unitmodels].[model] & \") SN: \" & [units].[sn],\"\") AS probheader, \"test\" AS compname, wom.probnum, wom.ctype, wom.LABPN, wom.TRAVPN, wom.PROBNOTES, wom.PROBBRIEF, wom.item, wom.linetotal, wo.clientrefnum, wo.clientcontact, wo.ourref, wo.created AS wodate, wo.invoice, wo.notes, wo.prob_reported, wo.prob_found, wo.action_taken, clients.bizphone, clients.extension, clients.fax, clients.email, clients.company AS clientname, wom.details, wom.START, wom.STOP,wom.REGHOURS, wom.TRAVHOURS, wom.NCHOURS, projects.name AS PROJNAME, projects.notes AS PROJNOTES, wo.client, wo.project, wo.type, wotypes.category AS CATEGORY " "FROM ((((units RIGHT JOIN (probs RIGHT JOIN ((([SELECT \"1\" AS ctype, rates.partnum AS LABPN, travelrates.partnum AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink AS wonum, \"Service: \" & users.first & \" \" & users.last & \" - \" & IIf(labor.hours>0,labor.hours & \" @ \" & Format(rates.rate,\"Currency\") & \" (pn:\" & rates.partnum & \")\",\"\") & IIf(labor.nchours>0,\" (\" & labor.nchours & \" no charge)\",\"\") & IIf(labor.travhours>0,\", \" & labor.travhours & \" travel @ \" & Format(travelrates.rate,\"Currency\") & IIf(IsNull(travelrates.partnum),\"\",\" (pn:\" & travelrates.partnum & \")\"),\"\") AS item, (labor.hours*rates.rate)+(labor.travhours*travelrates.rate) AS linetotal, labor.details , labor.start AS START, labor.stop AS STOP, labor.hours AS REGHOURS, labor.travhours AS TRAVHOURS, labor.nchours as NCHOURS FROM users INNER JOIN (rates AS travelrates INNER JOIN (rates INNER JOIN (labor INNER JOIN probs ON labor.link = probs.id) ON rates.id = labor.rate) ON travelrates.id = labor.travrate) ON users.id = labor.tech WHERE (((probs.wolink)<>0)) " " UNION ALL (SELECT \"2\" AS ctype, \"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Parts: \" & IIf(IsNull(woparts.misc), parts.partnumber & \" \" & parts.description & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\") & \" ea.(sn:\" & woparts.sn & \")\",woparts.misc & \": \" & woparts.quantity & \" @ \" & Format(woparts.price,\"Currency\")& \" ea.(sn:\" & woparts.sn & \")\") AS item, woparts.quantity*woparts.price AS linetotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM (probs INNER JOIN woparts ON probs.id = woparts.link) " " LEFT JOIN parts ON woparts.partnum = parts.id WHERE (((probs.wolink)<>0)) " "UNION ALL (SELECT \"3\" AS ctype,\"na\" AS LABPN, \"na\" AS TRAVPN, probs.notes AS PROBNOTES, probs.brief AS PROBBRIEF, probs.id AS probnum, probs.wolink as wonum, \"Third party service: \" AS item, subrepair.charge AS linettotal, \"\" AS details, #03/12/1968# AS START, #03/12/1968# AS STOP, 0 AS REGHOURS, 0 AS TRAVHOURS, 0 as NCHOURS FROM probs INNER JOIN subrepair ON probs.id = subrepair.link WHERE (((probs.wolink)<>0) AND ((subrepair.charge)<>0))))]. AS wom LEFT JOIN wo ON wom.wonum = wo.id) LEFT JOIN clients ON wo.client = clients.id) LEFT JOIN clients AS headoffices ON clients.headoffice = headoffices.id) ON probs.id = wom.probnum) ON units.id = probs.unit) LEFT JOIN unitmodels ON units.model = unitmodels.id) LEFT JOIN nonclients ON unitmodels.manufacturer = nonclients.id) LEFT JOIN projects ON wo.project = projects.id ) LEFT JOIN wotypes ON wo.type = wotypes.id " "WHERE (((wo.created) Between #~STRT# And #~END_#) AND ((wo.client)~CUST) AND ((wo.project)~PROJ) AND ((wo.type)~CAT_)) " "ORDER BY wo.id;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=31));",q2); rs->Ex(q); //=-=-=-=- PM by UNIT bug fix q2="SELECT ~CRITERIA AS CRITERIA, pmhead.id, nonclients.company_person " "AS MAKE, unitmodels.model, units.sn, " "unitmodels.description AS UNITDESC, units.id1, " "units.id2, units.id3, clients.company, nonclients.phone, " "pmhead.description, pmhead.notes, Min(pmitems.schedate) " "AS nextsrvdate, Min(pmitems.schedmeter) " "AS nextsrvmeter, units.lastmeter, pmhead.woconvert, " "pmhead.repeatevery AS rptmonths_count, pmhead.rptweeks, " "pmhead.rptdays, units.purchasedate, pmhead.ageyears, " "pmhead.agemonths, users.initials, users.first, " "users.last, pmhead.isclient FROM pmitems " "RIGHT JOIN (((pmhead LEFT JOIN ((units LEFT JOIN " "unitmodels ON units.model = unitmodels.id) LEFT JOIN " "nonclients ON unitmodels.manufacturer = nonclients.id) " "ON pmhead.link = units.id) LEFT JOIN clients " "ON units.client = clients.id) LEFT JOIN users " "ON pmhead.tech = users.id) ON pmitems.pmschedlink " "= pmhead.id GROUP BY ~CRITERIA , pmhead.id, nonclients.company_person, " "unitmodels.model, units.sn, unitmodels.description, " "units.id1, units.id2, units.id3, " "clients.company, nonclients.phone, pmhead.description, " "pmhead.notes, units.lastmeter, pmhead.woconvert, " "pmhead.repeatevery, pmhead.rptweeks, pmhead.rptdays, " "units.purchasedate, pmhead.ageyears, " "pmhead.agemonths, users.initials, users.first, users.last, " "pmhead.isclient, units.client, units.id, " "units.model HAVING (((pmhead.isclient)=False) AND " "((units.client)~CUST) AND ((units.id)~UNIT) AND ((units.model)~MODL)) " "ORDER BY nonclients.company_person, " "unitmodels.model, units.sn, clients.company;"; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=34));",q2); rs->Ex(q); //------------------------------------------------ //--------------------------------------- //P.M. by client bug fix q2="SELECT ~CRITERIA AS CRITERIA, [clients].[company], " "[pmhead].[description], [pmhead].[notes], Min([pmitems].[schedate]) " "AS nextsrvdate, [pmhead].[link] " "AS CLIENTID, [pmhead].[woconvert], [pmhead].[repeatevery] " "AS rptmonths_count, [pmhead].[rptweeks], [pmhead].[rptdays], " "[pmhead].[ageyears], [pmhead].[agemonths], " "[users].[initials], [users].[first] AS " "TECH_FIRST, [users].[last] AS TECH_LAST FROM pmitems " "RIGHT JOIN (clients RIGHT JOIN (pmhead LEFT JOIN " "users ON [pmhead].[tech]=[users].[id]) ON [clients].[id]=[pmhead].[link]) " "ON [pmitems].[pmschedlink]=[pmhead].[id] " "GROUP BY ~CRITERIA, [clients].[company], " "[pmhead].[description], [pmhead].[notes], " "[pmhead].[link], [pmhead].[woconvert], [pmhead].[repeatevery], " "[pmhead].[rptweeks], [pmhead].[rptdays], " "[pmhead].[ageyears], [pmhead].[agemonths], [users].[initials], " "[users].[first], [users].[last], " "[pmhead].[isclient] HAVING (((Min(pmitems.schedate)) " "Between #~STRT# And #~END_#) AND ((pmhead.link)~CUST) " "AND ((pmhead.isclient)=True)) ORDER BY [clients].[company]; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=35));",q2); rs->Ex(q); //------------------------------------------------ CString strID,strName,strRights,strHash; long lData; GZK k; //Add new ARAS REQUEST right: //loop through all the group records rs->Query("SELECT groups.* FROM groups;"); do{ rs->FetchField("id",&lData); rs->FetchField("a",&strName); rs->FetchField("b",&strRights); //decrypt the original rights string k.GZDecrypt(&strRights,false); strRights=strRights+"1";//add on the extra right for schedule view //re-'crypt' k.GZEncrypt(&strRights,false); //HASH strHash.Format("%u%s%s",lData,strName,strRights); k.GZHash(&strHash); //save the rights rs->UpdateField("b",&strRights); //save the hash rs->UpdateField("c",&strHash); //save the record if(!rs->SaveRecord()) AfxMessageBox("Error trying to save rights record"); }while(rs->MoveForward()); //Remove any bogus sub-repair records that were created by ARAS with a "where" set to zero //change has already been made in ARAS 2.9.3 that will prevent them from being created in future rs->Ex("DELETE subrepair.*, subrepair.where FROM subrepair WHERE (((subrepair.where)=0));"); //remove any blank customer service requests rs->Ex("DELETE client_requests.workorderid, client_requests.request, " "client_requests.probdetails, client_requests.refnum, " "client_requests.requestor_id, client_requests.* " "FROM client_requests WHERE (((client_requests.workorderid)=0) " "AND ((client_requests.request) " "Is Null) AND ((client_requests.probdetails) Is " "Null) AND ((client_requests.refnum) Is Null)); "); //Add the UNIT id to the ARAS requests table //Add aras_client field to rptsmaster rs->Ex("ALTER TABLE client_requests ADD COLUMN unitid INTEGER;"); rs->Ex("ALTER TABLE client_requests ALTER unitid SET DEFAULT '0';"); rs->Ex("UPDATE client_requests SET client_requests.unitid = 0;"); //add a field to defaults to control what client sees in ARAS workorder screen rs->Ex("ALTER TABLE defaults ADD COLUMN limit_client_aras YESNO;"); rs->Ex("UPDATE defaults SET defaults.limit_client_aras = False;"); //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"170\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.4.0\";"); nVersion=170; //buptodate=true;//<<==========CRITICAL!!!!!, should be at end of last case statement only break; } case 170: { //v1.9.4.4 changes //Fix client address book report criteria fields rs->Ex("UPDATE rptsmaster SET rptsmaster.criteriafields = 129 " "WHERE (((rptsmaster.id)=41));"); //Fix technician billing summary report criteria fields rs->Ex("UPDATE rptsmaster SET rptsmaster.criteriafields = 911 " "WHERE (((rptsmaster.id)=17));"); rs->Ex("UPDATE wo SET wo.modified = [wo].[created], wo.modifier " "= [wo].[creator] WHERE (((wo.modified) Is Null)); "); /* q2="SELECT clients.*, HEADS.* FROM clients LEFT JOIN clients " "AS HEADS ON clients.headoffice = HEADS.id WHERE " "(((clients.id)~CUST)) ORDER BY clients.company; "; q.Format("UPDATE rptsmaster SET rptsmaster.query = '%s' " "WHERE (((rptsmaster.id)=41));",q2); rs->Ex(q); //Set STATUS column in statusviews to -1 if it was previously 1 as -1 //now means any status where 1 used to mean any status q.Format("UPDATE statusviews SET statusviews.status = -1 WHERE (((statusviews.status)=1));"); rs->Ex(q); //10/26/2002 //set assigntech to correct value on old quick work orders q="UPDATE labor RIGHT JOIN (probs RIGHT JOIN wo ON probs.wolink = wo.id) " "ON labor.link = probs.id SET wo.assigntech = [labor].[tech] " "WHERE (((wo.quick)=True) AND ((wo.assigntech)=-1));"; rs->Ex(q); */ //fix the version number up rs->Ex("UPDATE defaults SET defaults.versioninfo = \"171\";"); rs->Ex("UPDATE defaults SET defaults.min_exe = \"1.9.4.0\";"); nVersion=171; buptodate=true;//<<==========CRITICAL!!!!!, should be at end of last case statement only break; } //<--------Insert new version before here -------------------- default: { msg.Format( "Your database version was not recognized and can not be updated automatically\r\n" "Please email support@ayanova.com immediately with this version number: %i\r\n",nVersion); AfxMessageBox(msg); return; } break; } }//while not buptodate rs->Close(); AfxMessageBox("You should close and re-start AyaNova now\r\n\r\n OR \r\n\r\n" "follow any instructions given during the update\r\n" "as directed before restarting"); } //Used when checking PM items for conversion to workorder //duplicate of item in pmcheckdlg void CDBUtils::MakeIntoWorkorder(CString strPMItem) { CString q,strDescription,strNotes; long lHeaderID,lTech,lLink,lClient,lModifier,lCategory,lProject,lWOID,lProbID; long lSchedMeter,lHighestPMID,lRepeat,lDays,lWeeks,lDOW; bool bIsClient,bQuick,bOnsite,bAutorpt,bAutoWO, bHold; int nDOW,d,nTemp; COleDateTime dtScheduled,dtNow,dtDefault,dtStartTime,dtEndTime,dtSchedStart,dtSchedStop; dtDefault.SetDate(1968,03,12); dtNow=COleDateTime::GetCurrentTime(); //Get all the details from the detail record first q.Format("SELECT * " "FROM pmitems WHERE (((pmitems.id)=%s));",strPMItem); rs2->QueryReadOnly(q); if(rs2->IsEmpty()) { q.Format("Error converting PM Item %s to workorder",strPMItem); AfxMessageBox(q); rs2->Close(); rs3->Close(); return; } rs2->FetchField("pmschedlink",&lHeaderID); rs2->FetchField("schedtech",&lTech); rs2->FetchField("link",&lLink); rs2->FetchField("isclient",&bIsClient); rs2->FetchField("clientlink",&lClient); rs2->FetchField("schedmeter",&lSchedMeter); rs2->FetchField("schedate",&dtScheduled); rs2->FetchField("autowo",&bAutoWO); rs2->FetchField("hold",&bHold); /*PMDAYS*/ //Get the rest of the info from the header record q.Format("SELECT pmhead.description, pmhead.notes, pmhead.modifier, pmhead.autorpt, pmhead.dow, " "pmhead.repeatevery,pmhead.rptdays, pmhead.rptweeks, pmhead.series, pmhead.wotype, pmhead.woquick, " "pmhead.woproject, pmhead.woonsite, pmhead.starttime, pmhead.endtime " "FROM pmhead WHERE (((pmhead.id)=%u));",lHeaderID); rs2->QueryReadOnly(q); if(rs2->IsEmpty()) { q.Format("Error converting PM head item %u to workorder",lHeaderID); AfxMessageBox(q); rs2->Close(); rs3->Close(); return; } rs2->FetchField("description",&strDescription); rs2->FetchField("notes",&strNotes); rs2->FetchField("modifier",&lModifier); rs2->FetchField("wotype",&lCategory); rs2->FetchField("woquick",&bQuick); rs2->FetchField("woproject",&lProject); rs2->FetchField("woonsite",&bOnsite); rs2->FetchField("autorpt",&bAutorpt); rs2->FetchField("dow",&lDOW); rs2->FetchField("repeatevery",&lRepeat); rs2->FetchField("rptdays",&lDays); rs2->FetchField("rptweeks",&lWeeks); rs2->FetchField("starttime",&dtStartTime); rs2->FetchField("endtime",&dtEndTime); //Move the date into the time fields dtSchedStart.SetDateTime(dtScheduled.GetYear(),dtScheduled.GetMonth(),dtScheduled.GetDay(), dtStartTime.GetHour(),dtStartTime.GetMinute(),dtStartTime.GetSecond()); // dtSchedStop dtSchedStop.SetDateTime(dtScheduled.GetYear(),dtScheduled.GetMonth(),dtScheduled.GetDay(), dtEndTime.GetHour(),dtEndTime.GetMinute(),dtEndTime.GetSecond()); //FIXUP DATE if(dtScheduled.GetYear()==1968) dtScheduled=COleDateTime::GetCurrentTime(); //PROCESS INTO A WORKORDER //modified Feb 20 2001 to create as open, not closed q.Format("INSERT INTO wo ( " "project, client, type, closed, onsite, " "anytime, assigntech, quick, creator, modifier, created, modified, " "starttime, stoptime, notes, pmid ) " "SELECT %u, %u, %u, #%s#, %s, %s, %u, %s, %u, %u, " "#%s#, #%s#, #%s#, #%s#, \"%s\",%u;", lProject, lClient, lCategory, bQuick ? dtScheduled.Format(_T("%m/%d/%Y %H:%M:%S")) : "03/12/1968", bOnsite ? "True" : "False", "False", lTech, bQuick ? "True" : "False", lModifier, lModifier, dtNow.Format(_T("%m/%d/%Y %H:%M:%S")),dtNow.Format(_T("%m/%d/%Y %H:%M:%S")), /*starttime*/dtSchedStart.Format(_T("%m/%d/%Y %H:%M:%S")), /*stoptime*/dtSchedStop.Format(_T("%m/%d/%Y %H:%M:%S")), strDescription,lHeaderID); ///////m_pApp->ShowStuff(q); rs2->Ex(q,&lWOID);//modified Nov 5th [some year] rs2->Close();//flush it..flush it.....flush it reeeal good //Create a companion problem record if(bQuick) q.Format("INSERT INTO probs ( wolink, creator, created, pmscheduleid ) " "SELECT %u, %u, #%s#, %u;", lWOID, lModifier, dtNow.Format(_T("%m/%d/%Y %H:%M:%S")), lHeaderID); else q.Format("INSERT INTO probs ( " "wolink, creator, created, brief, notes, pmscheduleid, unit ) " "SELECT %u, %u, #%s#, \"%s\", \"%s\", %u, %u;", lWOID, lModifier, dtNow.Format(_T("%m/%d/%Y %H:%M:%S")), strDescription, strNotes, lHeaderID, bIsClient ? 0 : lLink) ;//if client 0 else link=unit rs2->Ex(q,&lProbID); rs2->Close(); //QUICK WORKORDER: CREATE A LABOUR RECORD if(bQuick) { //v1.9.4.4 get and set default client rates //various changes in this block long lDefRate=0; long lDefTravelRate=0; q.Format("SELECT clients.defrate, clients.deftravelrate FROM " "clients WHERE (((clients.id)=%u));",lClient); rs3->QueryReadOnly(q); if(!rs3->IsEmpty()) { rs3->FetchField("defrate",&lDefRate); rs3->FetchField("deftravelrate",&lDefTravelRate); } rs3->Close(); q.Format("INSERT INTO labor ( link, tech, rate, travrate, start, stop, details ) " "SELECT %u, %u,%u, %u, #%s#, #%s#, \"%s\";",lProbID,lTech,lDefRate,lDefTravelRate, dtScheduled.Format(_T("%m/%d/%Y")),dtScheduled.Format(_T("%m/%d/%Y")), strDescription + "\r\n" + strNotes+"\r\n----------\r\n"); rs2->Ex(q); rs2->Close(); //v1.9.4.4 end of changes in this block } //STANDARD WORKORDER: CHECK FOR PARTS AND CREATE WOPARTS RECORDS AS NECESSARY if(!bQuick) { q.Format("SELECT pmparts.pmlink, pmparts.partnum, pmparts.quantity, parts.retail, parts.avgcost " "FROM pmparts LEFT JOIN parts ON pmparts.partnum = parts.id " "WHERE (((pmparts.pmlink)=%u));",lHeaderID); rs2->QueryReadOnly(q); if(!rs2->IsEmpty()) { COleCurrency crData; COleCurrency crCost; CgzCurrencyFormatter cfm; long lPartID; float fQuant; //CREATE PARTS RECORDS UNTIL NO MORE do { rs2->FetchField("partnum",&lPartID); rs2->FetchField("quantity",&fQuant); rs2->FetchField("retail",&crData); rs2->FetchField("avgcost",&crCost); q.Format("INSERT INTO woparts ( " "link, partnum, quantity, price, cost, usedby, misc ) " "SELECT %u, %u, %f, '%s', '%s', %u, Null;",lProbID,lPartID,fQuant,cfm.Format(crData), cfm.Format(crCost),lTech); rs3->Ex(q); rs3->Close(); }while(rs2->MoveForward()); } } //RESCHEDULE TO REPLACE CONVERTED ITEM OR DELETE IF NOT RECURRING if(!bAutorpt) { //Remove PM ITEM here if not recurring, else just change date/meter count: q.Format("DELETE pmitems.* FROM pmitems WHERE pmitems.id=%s;",strPMItem); rs2->Ex(q); } else {//increment this record. //Find out which record is the highest q.Format("SELECT TOP 1 pmitems.id " "FROM pmitems " "WHERE (((pmitems.pmschedlink)=%u) AND ((pmitems.link)=%u)) " "ORDER BY pmitems.id DESC;",lHeaderID,lLink); rs2->QueryReadOnly(q); if(rs2->IsEmpty()) { AfxMessageBox("Error: Can't locate the highest pmschedule for rescheduling.\r\n Contact tech support with the details."); rs2->Close(); rs3->Close(); return; } rs2->FetchField("id",&lHighestPMID); //ASCERTAIN THE HIGHEST RECORD if(lHighestPMID!=atol(strPMItem))//are were already at the highest to convert to workorder? {//if no: load in the highest records meter and or date data for processing q.Format("SELECT pmitems.schedate, pmitems.schedmeter FROM pmitems " "WHERE (((pmitems.id)=%u));",lHighestPMID); rs2->QueryReadOnly(q); if(rs2->IsEmpty()) { AfxMessageBox("Error: Can't open the highest pmschedule for rescheduling.\r\n Contact tech support with the details."); rs2->Close(); rs3->Close(); return; } rs2->FetchField("schedmeter",&lSchedMeter); rs2->FetchField("schedate",&dtScheduled); //>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> //INCREMENT DATE OR METER DEPENDING if(dtScheduled.GetYear()==1968)//it's meter based { //Process as a meter based record //this one's easy: lSchedMeter+=lRepeat; } else //calculate next date based pmitem record { //prepare a simpledate class object CSimpleDate sdTemp(dtScheduled.GetMonth(),dtScheduled.GetDay(),dtScheduled.GetYear()); //Add the months, then increment to the right //day of week if necessary. sdTemp.AddDays(lDays); sdTemp.AddDays(lWeeks*7); sdTemp.AddMonths(lRepeat); //******************************************************************* //ADD DAYS HERE //******************************************************************* //Advance to day of week selected. //temporary version of nDOW to matchup sunday as first day of week //make our desired date numeric base match the one returned by the getdayofweek nDOW=(int)lDOW; if(nDOW==7) //sunday=0 in CSimpleDate land nTemp=0; else nTemp=nDOW; d=sdTemp.GetDayOfWeek(); if(nDOW==0)//any weekday { if(d==0)//sunday sdTemp.AddDays(1);//move to monday if(d==6)//saturday sdTemp.SubtractDays(1);//move to Friday } else//specific day { while(d!=nTemp) { sdTemp.AddDays(1); d=sdTemp.GetDayOfWeek(); } } //set dtTemp back again. dtScheduled.SetDate(sdTemp.GetYear(),sdTemp.GetMonth(),sdTemp.GetDay()); } //<<<<<<<<<<<<<<<<<<<<< //OK, at this point we have incremented either the date //or the meter reading and can now insert the replacement record //and then delete the old record //done this way rather than updating existing record because were //relying on a higher id value to indicate the farthest "flung" scheduled item q.Format("INSERT INTO pmitems ( " "pmschedlink, schedate, schedmeter, autowo, hold, schedtech, " "link, isclient, clientlink) " "SELECT %u, #%s#, %u, %s, %s, %u, %u, %s, %u;", lHeaderID, dtScheduled.Format(_T("%m/%d/%Y")), lSchedMeter, bAutoWO ? "True" : "False", bHold ? "True" : "False", lTech, lLink, bIsClient ? "True" : "False", lClient); rs2->Ex(q); rs2->Close(); q.Format("DELETE pmitems.* FROM pmitems WHERE pmitems.id=%s;",strPMItem); rs2->Ex(q); rs2->Close(); //ADDED 09/05/2001 to fix motorola "problem" //update nextsrvdate to = next scheduled item //first fetch the date / meter q.Format("SELECT TOP 1 pmitems.id, pmitems.schedate, pmitems.schedmeter " "FROM pmitems " "WHERE (((pmitems.pmschedlink)=%u)) " "ORDER BY pmitems.id;",lHeaderID); rs2->QueryReadOnly(q); if(!rs2->IsEmpty()) { rs2->FetchField("schedate",&dtScheduled); rs2->FetchField("schedmeter",&lSchedMeter); rs2->Close(); q.Format("UPDATE pmhead SET pmhead.nextsrvdate = #%s#, " "pmhead.nextsrvmeter = %u WHERE (((pmhead.id)=%u));", dtScheduled.Format(_T("%m/%d/%Y")), lSchedMeter,lHeaderID); rs2->Ex(q); } } } rs2->Close(); rs3->Close(); } //BootScan //cool name eh? //Check for any maintenance items that need to be done void CDBUtils::BootScan() { #ifdef _WTF_ AfxMessageBox("Entering bootscan"); #endif COleDateTime dtTemp,dtNow,dtMaint,dtDefault; CString q,strMsg; bool bFirstBoot; long lPMItem; CString strPMItem; dtDefault.SetDate(1968,03,12); m_bBootScanDone=true; //================================================== //************************************************** //Check to ensure that there is rates and one client //warn user if not so that we avoid service call //about error when creating workorder strMsg.Empty(); //SEE if any clients: rs->QueryReadOnly("SELECT clients.id FROM clients;"); if(rs->IsEmpty()) strMsg+="CLIENTS\r\n(from main menu take Options->Edit->Clients).\r\n\r\n"; //SEE if any TECHS: rs->QueryReadOnly("SELECT users.id, users.tech FROM users WHERE (((users.id)<>1) AND ((users.tech)=True));"); if(rs->IsEmpty()) strMsg+="TECHS\r\n(from main menu take Options->Edit->Users & Rights).\r\n\r\n"; //SEE if any ZONES: rs->QueryReadOnly("SELECT * FROM zones;"); if(rs->IsEmpty()) strMsg+="ZONES (even if you don't plan to use them).\r\n(from main menu take Options->Edit->Zones).\r\n\r\n"; //SEE if any regular rates rs->QueryReadOnly("SELECT rates.id FROM rates WHERE (((rates.travelrate)=False));"); if(rs->IsEmpty()) strMsg+="SERVICE RATES\r\n(from main menu take Options->Edit->Rates).\r\n\r\n"; //SEE if any travel rates rs->QueryReadOnly("SELECT rates.id FROM rates WHERE (((rates.travelrate)=True));"); if(rs->IsEmpty()) strMsg+="TRAVEL RATES (even if you don't plan to use them).\r\n" "(from main menu take Options->Edit->Rates).\r\n\r\n"; if(strMsg.GetLength() > 1) { strMsg="You must now enter at least one of each of the following...\r\n\r\n" + strMsg + "\r\nYou should do this now before you enter any workorders\r\n" "or serious errors and other problems could result."; AfxMessageBox(strMsg); } //************************************************** //================================================== //See if maint has been done already dtNow=COleDateTime::GetCurrentTime(); rs->QueryReadOnly("SELECT defaults.lastmaintdate, defaults.firstboot FROM defaults;"); rs->FetchField("firstboot",&bFirstBoot); //moved below to avoid delay between check and snagging it //rs->FetchField("lastmaintdate",&dtMaint); //SEE IF THIS IS A NEW EVAL VERSION //IS registered? if(m_pApp->m_uiFeatures&LICENSE_REGISTERED) ;//Yes this is supposed to be here else { //Is first boot? if(bFirstBoot) { WelcomeToSC(); rs->Close(); return; } } #ifdef AYQB//process no further if this is the QBI version rs->Close(); return; #endif //#ifndef _DEBUG rs->FetchField("lastmaintdate",&dtMaint); //Snag the maintenance job... //done here regardless because it means less time between read and write //and won't affect things anyway q.Format("UPDATE defaults SET defaults.lastmaintdate = #%s#;",dtNow.Format(_T("%m/%d/%Y"))); rs->Ex(q); rs->Close(); if(dtMaint.GetDayOfYear()==dtNow.GetDayOfYear())//same day? return; //#endif //CONVERT ALL THAT'S DUE FOR CONVERTIN' //DO DATE ITEMS FIRST q.Format("SELECT pmitems.id " "FROM pmitems INNER JOIN pmhead ON pmitems.pmschedlink = pmhead.id " "WHERE (((pmitems.schedate)>#%s#) AND ((DateDiff(\"d\",Now(),[schedate]))<[woconvert]) AND ((pmitems.hold)=False));",dtDefault.Format(_T("%m/%d/%Y"))); //=======-=-=-=-=-=-=-=-=-= #ifdef _DEBUG // m_pApp->ShowStuff(q); #endif rs->QueryReadOnly(q); if(!rs->IsEmpty()) { do { rs->FetchField("id",&lPMItem); strPMItem.Format("%u",lPMItem); MakeIntoWorkorder(strPMItem); } while(rs->MoveForward()); } //DO METRIC ITEMS q.Format("SELECT pmitems.id " "FROM (pmitems INNER JOIN pmhead ON pmitems.pmschedlink = pmhead.id) INNER JOIN units ON pmitems.link = units.id " "WHERE (((pmitems.schedate)=#%s#) AND (([schedmeter]-[lastmeter])<=[woconvert]) AND ((pmitems.hold)=False));",dtDefault.Format(_T("%m/%d/%Y"))); #ifdef _DEBUG //m_pApp->ShowStuff(q); #endif rs->QueryReadOnly(q); if(!rs->IsEmpty()) { do { rs->FetchField("id",&lPMItem); strPMItem.Format("%u",lPMItem); MakeIntoWorkorder(strPMItem); } while(rs->MoveForward()); } rs->Close(); //POISON PILL - November 21 2001 //wipes the key for anyone on the list of non-paids CString strREGKEY,strCOMPARE; GZK k; rs->QueryReadOnly("SELECT * FROM defaults;"); rs->FetchField("key",&strREGKEY); k.GZDecrypt(&strREGKEY,false); CStringList sl; sl.AddTail("g070YEU+l209n+dfIg+zHStkGe4eZGKtDlwRDL2/C2s7ojhhssX08gYo2wglNo2v"/*"dupjPUa#3kLol#5wMOkc#9#5VwcXz#0#9ajqBqwaZ#5pMNuZuQ"*/);//LELIA PROCTOR sl.AddTail("50x1+MYBBDbDL/JKwXMWc4v6S3XkSrhF4gUA3kCBwfvzYEd8/kaZN8orJ7IZiQfR"/*"#8#4QZ#0+ahDL#3YEM#6OMjJ#0FbZN#1LIJElkoXkMpYtF#2ynE"*/);//Signature Control Systems sl.AddTail("n/Ad2lzsaObnea2VYCGk9wWpBXDuHa/D8tNxH681jJ6WuoAGo9tbybcGnenvM3zl"/*"#2+IHm#4UZipapRBcWJMZ/qTuJQvtGGwuuCD#2w+y#8Bb#4g"*/);//Hi-Tech sl.AddTail("A9HMgGGz/TC2QwJvz3scy+R6mECDZ148xPjhn8nW72KMAanBhMSfZEzzE8rGCDC6"/*"YMWACcaYiMo#0lWpS#0rAy#2#6mmkjjQfRW#3cMDwY#8eN/kA"*/);//WDS victor garcia sl.AddTail("sAKjGPxOtVpqaAdIv/UlreoxsuA8xynK4MdQkEoi/FxO7TgPhptFkJshx1qFVuTVWwe6SkiMBYSqH6N29S6kEg"/*"#2aPmF#4fEVMKzbu#1iq#5t+QXdf#5xH#7#8HEy#4pfWfcsDuIo"*/);//Bellwether solutions order 362 sl.AddTail("ArLxjCbQe2oV8rmHQH6+5of5AEVBkVVmei5DthiLc0UZKg2j2r2vKW2uIYz0ZgF5VrWRQZfiGif2QDr5fiGkwg"/*"#7/b#1h#8mml#1fPQ#5UqRMAZB#9HF#8c#6#4zOkkFAEQzRNH#4oo"*/);//Bellwether solutions order 365 sl.AddTail("IkS9UcBtwxXMbYMI0DdbvLfP3VMRtal0bmbLgpGM7lfa0vjtzaU8wt7/69y+scwiZfrj9EQgf/C2eGQUeFHTGQ"/*"#4Uo/ZS#5tAeFWwhlYtR#1#9#8/otVEamFGiNyeaFgwr#5p#9w"*/);//Vandy enterprises, changed company name to primetime - new key issued sl.AddTail("y4LL98AnmEYHMMbQ8g3Ut9gxwJnez7o5vauxMPzs/NjxQmtIhX1nPmnC/HImI/TMwnMSBC1TPPXWCBGsiWBMJA"/*"W#2OP#4jDc+hrl#9#2bA+mKWo#6HtoBF#2#7Pvi#4cIIadFAM#0k"*/);//LEXCOM TELECOMMUNICATIONS CO "duplicate order" number 391 feb 20 2002 sl.AddTail("3kQQW48GO1nCKwx3tiwCpUKORay8fVKN1iN5E4Z5DMHOwBlKiQtSA2wKFLU/HGlc1Wh4PSva" "BY48NBt/6OIC5Q");//"Fpbe#7uGcoOp#4fokdBLaFm#1#7JYywOAEeddQMXZkALK#1c"*/);//Mexico Express order#45 placed on Dec 21 2000, refunded on Dec 22, 2000 as duplicate order sl.AddTail("lPFqNkJlGrE0vKuChxmCPnZovtQtfYCDpUerSqjebVLWAaR9PPeZNoYenX8ghSFlP5Di3JEB" "sffmcEGCobHiQw");//"#8s#0#5SlO#2uOnKPgLddGoNn#0og#7hj#5swPVDajUF#9uFqnA "*/);//E/C Vibration & Balancing Service Ltd order#177 placed on June 22 2001, refunded on July 3, 2001 sl.AddTail("JLwQ2p0KX8eRo6ZsJg0KU/NTq7ljyFXcS4dSL9ExsbLmCdkd/tPDFcJXC3OkK4Fj");//*"BXan#9obwoIalinGXF#0yYfsYR+gurwQDRnSyewpJlysM"*/);//Tom Rice order#577 placed on August 2, 2002, refunded October 14, 2002 sl.AddTail("7+IZBTNEbf/rNu9Al0Yyckb3FUoi35v1X5LnabFOLoLFFBVgHoRA8fAdPObZFIsNvBF9QRbt" "AmbhvbRSWfKo6Q");//*"JGjzLMdnVS#0v#4m#7Xmhm#9tcBrOPtHo#7#1Bsmt/JDln#8gs"*/);//Computer Solutions Professionals order#602 placed on August 30, 2002 - purchase order not paid as of October 21 // // // // //original keys that have now been replaced ( in legal agreement, they are not to use them) // sl.AddTail("3I1eTPbMRvXFUOdCOhAh1DaOf8x5rj3ChF0ygnjhLiAYB3HCXBo7pptxNFdU8ES6kPBUBl3v" "6DQ8y7H8iYp97Q");//Registered to:[ZFC Consulting] Activation key:[R#9#3zApZIYrBnaUhXjz#3#5#6K+#7OSyBIXbLpUr#3C#3RX#9G#4] sl.AddTail("vfatmzeAAyMSfKjx6G17/E0ohDJNXUZt+0VvLL0loPGCT+CPxzES/wjp72veuf54Goxksc49" "Wl0BuKlRGH/x5Q");//Registered to:[WS Electrical & A/C, Inc.] Activation key:[W#7oKFr#9FQhefdvfPQ#7IUm#3RkBjy#8Y+R#7B#8tafrlMUMA] sl.AddTail("8DQ9DHxoDAAhQdFNvhuQ4hcj5ZbYQIME1bIag3eWuytT0Rs3co8bspvHlL5R0eMYbNTFT4zw" "D3UHx2/UbKswSQ");//WKT Communications [XGILF#0/kBnBx#3#9#1+OXUsy#7ttMkivQkqRaSZme#6Jqg#9E] sl.AddTail("/I90xJXJYEHbRHfZuVoLGndWMebuKfUzn2MnyuL1jqa+kWoA0S/k8oEK4a1JSIso");//Registered to:[Wizard Enterprises] Activation key:[WfPPvuL#3mohNMjk#8lGIcOG#3L#1piAqzcAvwvINL+ImOE] sl.AddTail("06tvS/2Cz8VMXugkkwtKtzwOPv94V+tShZAWx2BvUqoZ2WLOrehKtv91v+0s3QnTy+Gmd068" "PFs6wcP3Dc9RSw");//Victor Computer Consultants [aT#0rRQO#0TTES#4AjHRSE#2B#3ASPf#7F#2z#8X#5cIFfgAOH#7c] sl.AddTail("HYkPpRKvaxj21RZy5koeBsUWxzDlYMRh2Yplulo4Z0pXfcGMCEh+o3HzSjvID/ZzRCVAYOtd" "UK+1SrlyMXX4WA");//Viablelinks LLC [#0q#2eI#1JumsNlUM#8R#0+qLPfqkvursSfnirRWbq#7HU#5lI] sl.AddTail("CFXK7+KHUYXMB/WKIHBPnemqClqJCtkDFH7TIFNBKTm7d/nyYh1jRJwh16cBuRZVonGG8uJ+" "EX2DdKSUvqrtOg");//Version 4 Holdings, LLC [Z#9RFRrbF#5RTz#1#5Oh#8/KKm#8aTjU#1yD#4CbdxHkCdo#0T+#8] sl.AddTail("GZzcI+UWVDl3JVvgjYGsd2B28IPNM3vBRDM1UBuTKa2w6H44l/9VRAww6pJEBN7B57sti96G" "7dfRSMca65K7Ig");//The Digiticians [+cM#2vI#5QM#2DzCnfp+#2MKg+YDrkZHesWJEj#5f#7+TL#7nc] sl.AddTail("EIYACI5umM0ViM1lfs/b3ogdJUA1IpToYu8L3PYuggslPEeeYTjidW4YRLO3RRxukgEOJcN9" "G8U4yTVJNwLH7w");//TekWorks [wqvxuW#7KuyFB#9aqILRWN#9#6KttOJnvecfIf#7b/PEnQss] sl.AddTail("8Pscwx1k27gYQpVMqIw24TUiXAON08ysxkKHi3ciRbSEgh3YWsr9YZVpvX959P4N3MFPCrKk" "B98RarTpx+u68A");//Registered to:[Superior Service]Activation key:[dSXB#8UoZDMrbkN#9ScYcA#4zqvqieQsmyd#9qzR#7JSXBBM] sl.AddTail("IOCnO282pFJdawUGbsy8hU6IZh3dm5rn+Mlow8CbbVR7olZyUR8R4zc9WXnBJ7X5pwbn3CJT" "C2b++EYRhAW3sg");//Superior Service [WHRJLmYGbW#5KeTrAcmSfXwW#9W#0Qa#1vez#3yIZysw/FNE] sl.AddTail("cvm73wa3KD7w0mwd/ZyJ0T3ArSnLy9wl/rMRycenNDNJrRx8xcYOxEdjXFlMNaXohDKLgiS0" "Vjo2OTEMeSrasQ");//Speed Technology Development Limited [nVw#6Tw#6sgS#1WVgzKu#6mCnONJGQZA/MP#2cFVmjdMvWBA] sl.AddTail("gss9LXe8/dbpO0QuRhCFKF/fxGqUjyfEEbbFT15O5nIvKHZdnHj2VbcTd7O/D0Zafpp9UCJT" "3imWER+dlm3YSA");//Speed Technology Development Ltd. [hNK+Lbz#5OYy#7DptsVS/#5N#8KbWzgLerLTtjol#2JztdPA] sl.AddTail("sptlwwWO3zVRo3Wzq1KM70P7psCaNrV4oDb7Bel6P7kufjd8tFssfCZiZxSJAjQXR582K660" "71MmxkElwE9TYA");//Speed Technology Development Ltd. [#9xaSTyanBJLn#1#2kabGaVuO#3PU/XWyhnxOOaVXc#7JII#0] sl.AddTail("SiWfJ9qRKNdYgzPWKzjcACBt6ihxZSNWNL5vCOCjamw8xune28gFP8cggo6n8DGy");//Smith Cooper IT Solutions and Services Ltd [XDmAIK/brXnjrZtxWqv/Y#3Erey#4G#6mT#3jKYtpEtqkqQ] sl.AddTail("uKKfdtDmx3S+OLVb1Xjv7WaCfYTTjejhIA3yYkWIFPfZcn2sL7xMtAiEhO5Tx175Hg99gSdP" "yAFD8VWBaXKpuQ");//Registered to:[CREATIVE SIGNWORKS]Activation key:[GlB#6xMSAvy#1Onq#5LfHFrq#3kQ#4a#0Puc#0g#8zmcyoMAQdk] sl.AddTail("LjbpdynWb3YEpDSOFXnIbk0zuTo8hEWO/pMssefOcGKoG2oO5MgLmNqODAmp/cI9");//Schwartz Ophthalmic Services, Inc [KPefutFRiRvjhLzpOkpueq//hgXaXIFmBDha+Ia#2FIM] sl.AddTail("Ml+x3XEpM6fYllgcRJsNLgmB7mRAYiUQF9zYYGl20t+iyrXGKEga+Bbvm+4Jt+MrWwW8uhHf" "EI7iBvzRoS8pMQ");//Safe Data, Inc. [c#7RcyjcyKinY#9sEYO#5lSu#8ad/XS#4LtWwPiau#8L#3Kwls] sl.AddTail("pM9Zq6F8vA1k1d+JfsIQyFdBOuCbZ4FVmD5lcQ8xmy7lOeawqsVSJ1mdybehBsObZDvQI4wA" "vPBdy27SZASetw");//Rinnier Development Company [Y#5C#0vquOld#4/pJvgPlKKS#9fkkXbfEsA#3d#0pVfNopskA] sl.AddTail("EtnX0Bi1YP97uRN488wRKfcytKV/XfWbgnlwN0x33ZG1NXJTJ/ghPoLSwzSL5Vx6VC+7U9Z4" "YDXEAsyTainRUQ");//Q Enterprises, Inc. [FHcYu/CIH#2EP/I#6OumEskdTgpBst#2#8R1M+gtgsg#3Mz#0] sl.AddTail("xsnQoAXUUzO+f+nCth2xpQgCpVoqSRV8KC8RN+BKxN5xX+W7Lpky637wuYafGxukhZpRRQtH" "6kGD+egLQ31fIw");//Press Automation, Inc. [#3ZbsmhbFM#9xwr#1F#9Zn#2ahEwkAByTY#5IgD#7#3szJrvM#2A] sl.AddTail("nBQAe1IJMO37isUIToWQSwWY84637e20Dr7iaL8e99l+7zFn3yZX4b1Zsk9EYq3gAkVf4E0w" "pvPT705gNDfa3w");//Premier Beverages Limited [IvkJk#2vv/FzGJiK#4sleHO#2pivbnl/#4#3WS#8ntiVHphVU] sl.AddTail("t35LglDBnpOzPAsmaWFzugCxoY6TfP8UU5kWI6ojjbrsm9Olds6M5Ec5I3pdlg8hLbqdCQB6" "tVMBX7QBuvko2A");//Planet Earth PC [MQgWRDTgxDqkonnyLvB#4BNa#5#0BChj#4p#3IdVWNPldprU] sl.AddTail("Cew3LDFVgpBoNmNXP1TiH5Qeg/iqQ93381FnIZjTx9JEHRGysWYihdbr3EfRwyOIMYRJAGfT" "fddt7Eh7O051og");//Registered to:[Planet Earth PC]Activation key:[fBIdjQSztA#3JFygNYZqCBwNDG#6uV#9KpL#0#4IHrPlrYIM] sl.AddTail("9kyKK/apqZivA0KTuaIjEfJpvBzJJljQVUA9fdjoAwgdoBd/PE1oWyMs9yptd91Eh3BnOBSZ" "gTHX5jHZxPY2ag");//OneUP Technology [mMUH#6#4Rgf+EN#8u+jMa#9XwsfNtK#4AQR#4eVl/teT#6/I#4A] sl.AddTail("cOZz00IQL/Df1TxVrfLzPzTJ4/FeU2rvh6vf20AKxp4EKfgJvdTM5Xaw06J5tjAWUMwiXd2o" "5IcuNi7OQ/a9Tw");//Omni Management Group, Inc. [FaDNe#0NpxOA#3xagWHgKxihXntuGRrYVxZUNm#5#8B#9A#4o] sl.AddTail("5yIJhjQZ8mWTl1Lus7DhPmzaofdpThZhQabNTQdzuiJzA3NjpurWrLDCgso+lWD/aa5/LNzB" "FsLEYWcBKRYLxg");//Ohmart/VEGA Corp. [#2gsZq#7i#4#6UnkxxO+SxjhRFmNUhpMFGU#7JRqLZLa#5Oc#4] sl.AddTail("+Uzglutbog1vXZV5lJaiQLCx+KFnZxBICZpe09ME3P4XWL5j77UV6xwdIFv3pdYk7gXsE4X+" "67HJVwYu+pfERQ");//New Brookland Systems [lrVDCijjgXM#4#0#2Tdj/#4zbYXQ/PATaO#3#8PgqRHqm#6Mgs] sl.AddTail("/T7XoJK/GqBFFkl1+lsjuP6oP8cjtOckRZp8jZ3aWl2fhE0mZ+9lhz5D2mFZmc8JdsKNqHcA" "7MUX8vyKKNnoNg");//Network Neighborhood, Inc. [bZsTU+yPCE#4ATTDqu#1SyyhguskgRv#4#7#0lSmKcqbO#9#3E] sl.AddTail("j+uV8J/l0BGO/DsvUtvHdh8mIRFnLcFLz7sezaVNlYZRsESAw9tT0AqtdgPtSdNpkNcJByri" "8d9Z7gKW3zI0Tw");//Network Neighborhood, Inc. [npH#8czCVb#0pA#6AxU#2aAZ+pVuELGjwIAy#5#1#0/#6UmXIX#8] sl.AddTail("+o7xvoA3mBUOpaUOZgqmylo/kwPzFJJuBJfSRdjNR28aUx93sClL83BCJcZmMIC3");//Network Neighborhood, Inc. [Kn+VGQLL/G+U#7RGLbpwlKWvuKfEl#3IHTqSngPdnMQy#8] sl.AddTail("t9JCn4GDEFRE1RwKj/oD6wi+1IIGmoRjyM+GpWvJ6wIt+v5Y+kyLQX7TQ6NjAbDpBpTvZI1O" "udScP2eDEF3w9g");//Network Computer Solutions, Inc. [nIyH#0VTjzkMjHMBe#5g#0qge#2s#7nQ#3uxhcz#4#9lJr+qFw#0] sl.AddTail("z/Z+wTDNroJQ0N2RbrtnL89L9gn/l0rVWlN7HHkn/aa9qXy9Ls/YtTyu2KVk7qsNpKAsDb4J" "nDeGXLY2+C0HgQ");//Net/Complete, LLC [fGWdsT#6h#2F+m+ZseolBogClU#9XLW#0lOTh#7CuBQ/Tzw#8] sl.AddTail("fyb9R2PK56fctIICnfI2OJFksl9RgRbMhzK7Zv/8KhI+1Bdu9zZWAUW3J3hKOdZPJjo6OV1h" "2cismhJ1+X50HA");//NET Xperts LLC [#7QJqIEsh#2jqYFkTrLeylaDi#5VBresfASt#9tgY#4/JRyU] sl.AddTail("1tTX/LSJYz96Duvzv/LonUa7j4k086gKaU9LZQYKGwxAgWs2widKU3XngroVEIGXqctPtOg2" "+rEsBAW8AePZRg");//MIAD Systems Ltd. [W#2hIc/p#7eTuL#9eGlyf#7TO//YCasDJ#1oLq#7ZWw#1fj#1aY] sl.AddTail("3g/2JIoB6CkNuVSmrMMUTnJ1XoE/lYHXbYuZSM2og9qowgqTw5MXliU6ts3jTY6dMYThLlVB" "U/162XL1vrGqBA");//Megabytes Computers & Networking, Inc. [#5VdKs#0M+GDN/RlvOlTP#5sPfl#5vf#5#7Hya#0QQSEJBZd#6#8] sl.AddTail("pqOIcaE2WBDF7Btvga+eVaHEP0S4xfoDdIP4W/10XZpL9NsHZ3+D202qj0QwpZxSXp1VbX2f" "9KEfgK+65j5lEQ");//Mass Electronics [fM#2nF#7IIp#4Qvd#6kkgmSdXRPBxfsEJm#2QHaacDTAyxxI] sl.AddTail("12JbTFvRI+qnZDdVH+wg2XVeux9+CM4WhIZTm+HSubUlAOVjSJjnfZjPgb2WRExtnFdDQogb" "KpR3l9QKQEXGRA");//Marcraft Marine [YWhoxUqi#2Q+itlqcbsdDMOiFMwzKNr#8kX#0C#8BXB#8fh#0] sl.AddTail("DyHliKgfl2DLsy/eZZW2DLv1JNR/5iOVnM7GMCkXMrmIepezRD6X5Y7rD9PmWYDC1P1N4PCy" "fhdjmaEAEp0xGw");//Mag-Net Internet Inc. [#0WFbRcMNDm#9#8v+u#3QD/#7OTGbe#7WtTa#3IQA#7N#1oe#7dcY] sl.AddTail("i+U4JSj6UshJqblB40Y+BhWbs8qYm1zlAvGFqH7RGtPCnKmt5V7l2yXznrvisANxG/fwjeyu" "oTsC0M9uRQppOg");//Mag-Net Internet Inc. [DxjFdd#6aKqVwh/#8#5#9zTOwTfMFbXYeQePg+rGfB#8#2gpo] sl.AddTail("MfjpEiO/lVgJXQvNhj7ACvir18+o5CUvFc8E1iIma9sISiO4K3QxWzJ8hiQ1d9s0");//Mag-Net Internet Inc. [ZRxZSUHxHLSku#4F#4yMyMK/BLcLJyL+YYejQkQpoZQAM] sl.AddTail("wRMtC9UKV8ZTsVOhE+3DdQKFhrLSRHFGxu5OTUHpAJaPBVKtRMFO5lcLXmKHMxP44eCsSysz" "kopR0YQU+X4oVw");//KRK Associates, Inc. [vahQI#5wWWbq#7CWckTnwS+uWvxZEPe#9j#8#9V#6#9JKVzyko] sl.AddTail("M0MnVrVN8cVaHS9M3d4izMgZUPYcobl9h1AcIGFOiIq2G8iYq99nYawmiAkFDpqX4ClmCTjo" "2VdbIm1WSuo9mA");//Kramer Computer Services [WDRFplcZa#4MbiFSm#0#1N#3ljYFLuN#3pb#0Nkvci#8EE/#8Lc] sl.AddTail("AyaKFn2otdlDel4fPQiCY5d6h2iKlY3EquLCswCb4/6ICazQAonMX9LwsaswHnfwbxfF8Urs" "xz21nRrehCEDrg");//Kiel Bros. Oil Company, Inc. [fK#6NQ#2E#6GXZdc#4mq#1VsulEm#0C#6pakmWpoRVkNKTCqHM] sl.AddTail("0ikhTl3VPEOUYS2VvSxaUJ65bmgtMrkUdeGdR5DoBbVzUVt99ZjCq6MTUlrOrfZzZZY8cr1l" "WSVTURqhmcaPyw");//InterMountain PC Support [#7C/pbaZnKLbuSruuLEbV/Ll#5B#8#2P#2knG#2PXjvafJcUI] sl.AddTail("4/3IXlWj4IF0t9SlKnrx2ZRCeoLHWWkSsbTCf+MxlnQGySK7AS7H7ra2zkZshlcbDSW5RcB3" "5pTidJhdp3LMpQ");//Integrated Electronic Designs, Inc. [iC#7KwGpBtlwLYKQQofEnsN#1qvWTciWH#3qGlWJxPkx#1#8] sl.AddTail("7KnSFQnpnq5S5U5vbMLuZVRsPFPhMkJMxy1DFDnWwNd/mai/BPeCmGf2GBJiWcCL");//Integrated Electronic Designs, Inc. [/#4HxUkJ+wIkimfAAklFbODW#0#2GGIOnwtumhSIxQAoIo] sl.AddTail("v6knwr3KV2COMiRmlRvIRda/DSdM1y/WeN8ai2N2ZBq4/JP4IxeURphWz1kKpBWoXzzEjuch" "U1FNSnP5knuDRQ");//Info-Tel USA [#6RnHgFrKRT#7KkwqjZ#7Z#1nxifqcetU#6b#0KfXccZtkC#2c] sl.AddTail("idDSrm9VRstW5RgeGyhTK1Bci0WYxKQ/O8xr/rrYaKJXFtgAcEvhVqlCRmtj+qFt1QtNT4e0" "k9m55L4/on5OeQ");//Image Computer Services Inc. [Q#3oMVPoW#2NH#0#3zHUa+fWd#2lgkrQc#4+al#6qzLbCWhE#1M] sl.AddTail("22mROCOYwbnbsr1l+b7j3fnfByLfg9xWDqDUPf7lltzTKpaecyCrZPMB97q2NsnOPXfd7Qkm" "RWF4rXSlalmblQ");//Image Computer Services Inc. [ySrz#9#0vbHPCwuD#4ypV#1asQEzpLKh/#8UEA#6JwZWeN#6dQ] sl.AddTail("WabCJmHgo/gTE31R7nSCGCls0agVfHxp7+BuRFPoM4qbX9V8pX9TqkevpApUc3bf");//Icon Data Systems [qrprTwN/hCttvPVl/FoPrupUKTVs#2e+ZSZzQNk+#5KYI] sl.AddTail("aGBWsEuuNxrn/bzXtzrb8hu2mlMg4kjFIkf+xN4RnQimgH7ssVCqF51dLH7jlDhOXLKWwTe4" "iaRwQKdW0tK0rQ");//Icon Data Systems [kILku/igYLvrFrRYbvasw#5eTX#9YFglKLW#5#7+sFB#2IOo] sl.AddTail("BoMdp0xZLWHROPq6O4Go4q+Bcid3GIR7KtW2/76PXohXUX96HSdc8WoBvAY9lv0A1n4NU+mK" "xBLYMeJyuaox4w");//Hot Fish Global [wp#3va#5zSSaI#1SvyC#6#1F#7bL#1#3+lhCmbwseTfmM+ptMCA] sl.AddTail("CDfz733WImNFlnLMd121mKQninVco9IWuXwLlpp52hnultXTbVgGmnLd0TE3V5AB1jLLDzMq" "OPkU/cpAFaeWOA");//Hawkfire Technologies [mi#2XecQ#1QFryj#2fbp#8P#3RkJv#3u#9eXVUqA#4JrzBEm#2MM] sl.AddTail("34LrG5I0urlJ5rqqWmqzhjdO1EYNnMcUS1fnfek5I5j9z/JJmZAZi8MStQG1xSCiwHtj1Bl+" "ZicG9T42g6eeNg");//Exclusive Traders, Inc. [iP#2W#6eoEe#1v#3qNA#6/zdPUvfGcD#7#9uGebqrJRtosTM#7w] sl.AddTail("AKbvpzuj4VTG7FpfK6RKGrbKbquDx8vNDxpxmHUN0cSZ0eSxXwsHlG2DF5dqplSRPHF9AC3L" "DAGIK06NQPkIoA");//Epitec [jpNb+hzwOSv/t#7Y#0#7PpviJ#7VW+#9sR#3sjCuJ#8K#2fJCzs] sl.AddTail("CLmStcVq5JEbXg+VNrODAQIq4y/n2GiAIt3RzYRMfGlEPb6Mw6mtcS2u8G2HKYSj");//ENT Networks Inc. [JCXJjRrJSGnY#1O#7xGRoCNOCONmrIo#8omkITvAo#4oTpA] sl.AddTail("iuIcfg1cHi6JBU3+5Nql1xdnX8rKYoOV3/KL1AFQes+j1RTtMJd0zSw9xri6zngDJsasmcCE" "e3uMFJbGnuTlOw");//Easton Electronics [k#6ZHW#0#6QJNuunIK#5zOUWftwpghuB#4#9#8A#5m#8lwThbf#7w] sl.AddTail("JCvmOzvNeUBJWeqzjZNzNwffI0CEKCEhUvmnD3IUcYdC+Z1ee7QpG3D+Wa85YdDdlqK1rasr" "nJ/jRmIvYuIYRw");//Easton Electronics [liJBKiPqAyiE#2Zo#9Tockf#0M#5EjOz#4oGeEvsFo#1#5cSw#8] sl.AddTail("3kPlx2DTsn2UtNDh0gSZz3pSZY+BHOrzxtwLlXx+am/0g46m5IjA6v1P8qyhUCdHw1plZXnM" "QCwGLlKTWnPrfQ");//Easton Electronics [Nqw#2+#7xT#9m#3sxpOwpGPby#1CDEp#4QtlBHyPifJtHsTh#0] sl.AddTail("9Re1S5bJ4d3fUdR9h9W1MKYJLV0Wyxd2oERg8+O8htFTn+Lnp9s1Sfd5193vGR6EOUu13He1" "9pplu2m/PjfZIw");//Easton Electronics [gLfLoLkPA#4xKnKN#9lr#3K#6#9GiojixKgNjN#8DwyhZ#8#6go] sl.AddTail("tK6GY8PuVC3GuF2APpf1wTfhbeC9YZh4zdl1xAFnOHmaCmNBSIW2ACTzUMztbMvwD8twPpTS" "DoLQNFLpXOikGA");//Dosatron International, Inc. (Test) [JFb#7cFyB#1in#5YVZMapg#7d#2DU#1+qtypM#5#8BPZdcp#6GUE] sl.AddTail("wUknLcCS9C6Iw8zHwzLSl4WHB9CFlcb5PhMe/1vq/Ocr0T2DsS6aHEeV65g2RVtW3zw10820" "IXHob90wP6EdAg");//Dosatron International, Inc. (Test) [Vvoyw#0OkeJTMomE#6TBZVKSo#4Fyq#4L#8VZkEFp#8TxOp#3E] sl.AddTail("C3S6hU/PVBZK4mY2YD7qW7Q6kUonPh0bam3N5UbL3Ouvi47breSme56YXbV4+Pg8/l6IoIs7" "AOaqPFrlpqPqqQ");//Dosatron International, Inc. (Test) [KgP#2b#3+oninlOcE#0cCJWyQtqEaBn#8AtQ#3#0FWhPwyxII] sl.AddTail("h417NLCvT/pOPIp1S8XjB3HrGaiGP9PiWiROVDCqXHg8QNR4hrZZijplo1nUbkxCRwMpXHDO" "FRoaIR0MQoEqUQ");//Dosatron International, Inc. (Test) [ZEeR#2dYYy#5VHS#0Gl#4WbmaejOVbvBg#7hoH#8v#8FxVfIx#8] sl.AddTail("qmmZkhVKUVrN9tQKF/aGrGfZmZg0+D949/y8reeo2M4CnumPWRHCkacX7GJxhomVtk9H7rKV" "7pdIxycIhK4ioA");//Digital Knowledge [qUHA#4sFEgUj#8#5vQD#2XrrPQNg#1gP#0wYz#6cCcDLzB+#8RI] sl.AddTail("HSmTfuBSecDIrKvRmc5y5/Vd2cZ57orkh33teO2U0BNw4PQtDfE47NvwNsFOlcnm");//Dattio Corp [UYFykl#2NzXKh#5vfut/MVVz#7GNPKpXfjjqPnHLoDpxLE] sl.AddTail("4m57MNqmRaeXt8Ul3jcbPBxmNqdzoOVsN48Ff5huHRYYjX0K7fPHxg/wCh0TEa9gGIAENcK4" "YvLAedw5XYxpag");//Dattio Corp [JXtxk#5#6bdl+#6RU+uuOQlrpwl#8ohx#2jKMHe#5jywBEe#8g] sl.AddTail("E/eNrG/GxggnGCHb/bgbjTuIihnQlqseKSAUYeuRSqDIP2+ybFXfyQkoGa8oM9dS");//DATAKOM [ReaVLKnMRAfJHV#1vIBdCxSA#1nsEi#1SG#9bXDaFN/GmkQ] sl.AddTail("HfcoSW6PmTjUt18/dmZ1cVx7iAy8tfI/g/5taMsOCWjNldUESev5ZYfRd81ERpUYCGVdReMR" "35xhC2Utx4y+pQ");//CTS Integration, Inc. [y#0OW#8yKslWcwnRWbfUA#2IAxOSNQF#4pyJT#4T#1GfkTFE#8] sl.AddTail("MQdERanxxGxdnhY4OG9lAFLv3ECz6d13PsC0F+/i4NezVIhue2MRcLInV+xudFFxEWL7zQhs" "+DugpRVVFROsRw");//CTS Integration, Inc. [VV#6ohff#2pk#5TwclPLhO#9UNFOAgpdYdLQ#5#7#3jXoyC#1kQ] sl.AddTail("NdRtIE1qM0ulzwJIRHOhsBtk9mQu0ac6FnhcE6B3hswyfrn+hhehx3TJcs37Dy/VrSFwd22m" "euJq0NuvTwEB7g");//Computer Werx, Inc. [Ew+gTFDw#7#3#6#1WUIvxqWIg#7UkMjgfHsuWikUT#4#5sb#6gs] sl.AddTail("SZRHJManmPC/GYfhfTkqvnF36AvkLRvHm8fYuFx6on1ktZ9o1y0ZGUC+JHLNEyQrLOuVe5wV" "X9DHUKEQTZ5HqA");//Computer Service & Repair [sXmTbNP#9t#2hOLAfB+#0T+iMFSo#9Fi#8UQWbZCSQnHoHck] sl.AddTail("hxckfpuyVa6AYtinZiTWIdBvBEt7KiW82/MH15ZTswFwCudzsEjaThDXp0DYz+VHKCNNfYSH" "ezzPHvy3orZyZQ");//Computer Service & Repair [Ham/Bp#9+F#7Y#4#9VZPUey#1/rZvS#2uj+SN#7psW/qe#3QS#2A] sl.AddTail("SwWgNfHf98LkHC+rn/AHbA76rq7XY7nkcXnLL+HFoeenusoKPQ58738M5Ag+dzG7DTLk4495" "aXfYjZUjVQzTZw");//Computer Service & Repair [#7CXMW#6HVLZEo#8#9eD/LbefOBBQh+lAOKJ#4#8#5ClLQPmhk] sl.AddTail("uhMw/eAXeSPDUZEe5+vsLzKtJnErEtpDt+2NeoEpXXEfH+qTxru3u8EYR7UuFcw+KCyc9a2d" "Wo1ZGTmAjlCVCw");//Computer Creations, Inc. [LIGLUe#5yN#3V#7ILIbN#3NeDiYA#8#1bZ#5veL#9iy#8ZgjPEDA] sl.AddTail("MZQgmoJmRC36f1ab2hh9GgFPp3BeYOgik0kDJyKfw1uvNW3YA+KrrCk+mPzYDERqV5Ojis8e" "cvraii9ppHSfyg");//Computer Creations [QQUg/Pqa#3Ixq#8akrMV#1#4mJv#9#7ktyAMInZ#2mqWzf+JeM] sl.AddTail("n6iIHbDDCfN6dRtGl/+6iau5SJoJ0E8sabqpDohOpK++2i/iZMVkhZ9N3nm/9xlQH9hDYXL2" "qxqwHia0aH1UyA");//Computer Creations [T#8k/K+Dec#8#0LgTi#8by#8tga+#9x#8BBsPPz#7i#1rLwjEjeM] sl.AddTail("+lZ7yRc+ArVoU32q/pKZ9V7+ytlH5lXzfoYP3imfaXJvPhW5AiBOBmNfAWFHq9OjyEdvqJRl" "PWRswR1H/zRuDg");//Computer Corner Ltd [+#3#8oJ#6T#9QnWwuBCOxRbIK+/F#7VRXcSy#3#0L#3F#1TLXuhw] sl.AddTail("zQm03Ae2Rc50OXh9U0DTW+iZsh9ZT1QcQYcRv3z7wXyBrKY+XQ4bjB8p8em2gvyNUAIC3S3q" "I8N9d599EVijmw");//Compnet Internet Service [ouBbzQ+Jxl#2KytNP#3mGinlbl#0B#2#8#3aNgn#2FWILeA/aU] sl.AddTail("is494/A6gZ12yZjKp4B3/3uYQZg4iL+87qYMwPyfsDZF2lgn6yXYE3D3hAODcWCWUmG2sXfu" "Aissd/xq2GM90g");//Comfort Control Air Conditioning [FgvDzE#5X/TEzgL/#6Bk/v+pHRVhom#5baS#3Gf+#5TdVko#8] sl.AddTail("9xLRdF6rA/qjcbUZj9MVWKHPINdO1+VGZ7xqtK87C8nAPnpwFyUyp2LyyxWQFJjZe5uQtbq7" "px6AF5V/qQT6cQ");//Castellini UK [kR#5ntEiD#1RxoaEZinm#4U+JHJmNbXizfWw#8SU#3Lx#8slQ] sl.AddTail("ifO2g1qQcUVLwKUgzUppqwKiY8p4lpJ2bO23Qzk7Z/fweJINHUI7SPWLpyXGvlW4");//Boat Medics, Inc. [#9Ipqiiix#1cTcTSgXInirWnjK#5RyckH+sBwxVmFTsWSU] sl.AddTail("RqEWLLXW8NCGZsrDWi1hVAI+3GvKEMosx93Kfat5SVGCy2/Wbhsb3f2zDYEI70MH+DVAXoT7" "PT4woxvR66Pdeg");//Bits Technical Solutions [W/vnCI#2MGY#7yahCZZwXIdx/xtYV#9NA#6IillUPi#5#3ZGE] sl.AddTail("/CxjTvyFb83ebO3Rm9tP61+nVtWk2wUSKJy2cOwIE2BagtF9OkY+AWfdgDG9AbEY4iAF/7gQ" "kgk/lbzZ3fYitQ");//American Eagle Federal Credit Union [KiK#8phGgxakUxmosz#4#8B#5UTX#0HmuUZ#0zBgb#8RE#8h#0Pg] sl.AddTail("//ujMI27oHp+YhvptGA3HMe10RN11s85O67QpGFuw6FuTUS1+qFZJlMR6HY/BZEf18th+a0E" "CVGM9LioQwdK2w");//Altech Communications [N#4ZuO#2ZAScHXA#4BEuuKbG#6jA#2#5Pq#8#2djqkoVokF#6RF#8] sl.AddTail("QMhIauV71GaGch7UrOQKjXJFp/m0m4PaORI7M+7kD+dALNf3HdtSUZe1pQSVcOSC+zXXqxi3" "ed93dhhfdZqHyA");//Altech Communications [Wl#9GETyOB#7qvtuB#1hldN#6nMtTl#1CXbqhCOW#4AXUouKw] sl.AddTail("ol45MVZqW7U7SdY4oJzvpwU9lSzI2uvzfbPBkcPibPQ+AZCqsU0OUnfLp0Ap/jzV");//Allstar Show Industries Inc [MXpMGGIlDPJU#4DNwaK#0FbUK/ky#6Rve#6AutGKqqX/tkI] sl.AddTail("v+DTZ7k0HCV/w+sLqdz9QfHa53Nq5vn844+uZFw04rfiGAZezOKJl/CvIo8Przq1T8HlBcgu" "kbIsmwlnsMAM6A");//Allendale Machinery Systems [RG#3eLHFZ#7vw#5Afa#4B#1CADmKH#2ldBfF#6#4s#1+pFsqIfLQ] sl.AddTail("DRF4ee+jU1ol0UrrN0EnizaKSN0cydd9fGb0bjhRuTqT3Id8+lZmGtPSdfEYkQ0J");//allendale machinery systems [f/ZIhsds#3zAJoR#5hNZn/VvNhKZfhiYyu#3ormnrBjzNg] sl.AddTail("jPW4ZxDYSSJUn02G7kb8lVHpAAAL1dqMFS3stayCEGNydNqQdCEh+LAXX2bqXc3Uq48fNRms" "3e+x75AR1IPDgg");//Advanced POS Solutions Inc. [aac#3xQWhVjB#7nIYjCCu#4PvEAn#9#6EkUITAcf+V#8u#8Jww] sl.AddTail("rG0bXEQAfCYFrP+4otWhniD6s4WtzTNMlYGpxzva1ZtzJEOt6B60N8+X7yx+myjKBZ+CB1Ao" "Xw0jdTrmDBMjXQ");//ADVANCED DATA SYSTEMS [pnXTvxvSk#8NAilSyXv/Amw#0zN#4g/Z/Ex/HG#7U#3FfdEU] sl.AddTail("ZSEzD/RJHChakLX1Yl3U5/glU2/n/UoEO1zYGry/lvbvuBACu998eXRNeS7KtWYTHZ2vwclp" "RSkyQbCN0RNM1g");//Adtech Systems Inc.[g#4dawDP#6DzEqkdwFAZcZsIazGcKgcR#2#7#7#5CA/Z#6CYu#4] sl.AddTail("jlRFxn8y6B3UtiOYlgWXpY2QuQmr578ADOEvZHCxffbfdBxihQPaljSdK9/8dIgCjOzMK1oG" "feacP+8J32JwjA");//Aboriginal Technology Solutions [w/#5Kp#4Cm#8B#2#9nnranbsnds#0Y#4BYP#0CdR#5+FNmgctU#7Y] sl.AddTail("lVOAg0IIEZwsEhJlu/FJBq6ANoEeIKi7dL46C+CbAB1fI+kc18sqM98c3yPQVbWWYTKRS+AG" "0dcON1v2/aoNaQ");//Aboriginal Technology Solutions [C#2atbxlT/#0#5LfweSTsDxkDX#3Arku#9wZYM#2UkcMZqRkQ] sl.AddTail("I5ESyUZVpN5hSKj0lCmiCnOu+XRN/ZV2ORyK0xVwejlIy1pSv5xjK735JUEHkiLslt1RYN59" "6k9rlFzZhoktCw");//ABM [NCaP#6nGweTKuuXw#5KZfFQdEZkTnNr#3MX#5LYVX#7hiWR#4] //Bethany Lutheran Village Tower uJiq#5nWeSUbdCeqhcOnce#3PT#5YzGWI#9#3lw#3AFHKOCaI sl.AddTail("bOW/KsYo5EaCha5SiSaJ3kLvQ7kcjsYpEgLuQABka4RMNrTUdgDuQEbcaETHigwBH4Pf6poq" "dQ4QwikONb3B/Q"); ////City of Quincy JTm#1l#1baVSUz#3CpCoLg#0#0hUudHDZSwawo#1E#0WUO#1Joo //Update Dec 19 2002 - paid //sl.AddTail("9eb4rPzI4WZdeiw1vcqjWm3Li66ryTrdmr8Az5RBA0do71/G5YeR2Dq7sIpGWjBgfU7+7tD+" //"wYRwPeluoEx9lg"); //New Brookland Systems FTJqsgPHObedj#9#0#2GzndIIr#1#1nSlXk#5PWSkYmFbxbbc sl.AddTail("2zDOeArppx2bhdhKjrVxwzxmSS602x2lfBZ3rvz1xgMkXnFLEHozDKCET0qFlXJc328yUndI" "Ntxxjl816mOfog"); //United Business Communications WIxRPVFaLi#9IEuyR#5rp#6EpggL#9eJsy#4vSzRkG#9xC#7Lc sl.AddTail("r+QiRHL0DVfocI4HrYKeRAQ8gCqcBQnbES8t1T8RRd3qiVHak+jFsZaXxQya5fQF8+2oLGdR" "1VgUgkopH9wFAQ"); //Rice University #6#2MrAmx+dHUktLGqI/UMtALPtF#4FptyB#1dfFZiS#2#7#1E sl.AddTail("F6xVySHC8avdZ7rrrmKp909zuAW78VzqSwMW0+XoOYs8A46uLrRyI413tl9ejLxrH7RKsiGJ" "HwlZATqQWj3vUw"); //Cincinnati Test Systems, Inc. c#2#2#2+L#8#8gGKx#8#5NW#0iw#8tZS#8CIFJ#9ME#8G#9v#9wcMmWOs sl.AddTail("2wHL43V2LwSFY+wtvL6ZNYA7G2X7CSUPlMNCdph74P7v1nZdiIUmeSzCEM+tyMt3vh8/PK7/" "SiOkzoVJ6lOo3A"); //Ed's Locksmiths CYpTosuN#8v#1YlVveDhG/WuVG#3#0eosfnf#9Fux#1CGlXew sl.AddTail("0hqWAK1Z8+mmlj3WEyyrspTy5AxylX3L2fkEG45RvAD2/2jk6KtqHk3erlglzLXE7K9DUbGz" "XDIS8GL7jgWmOw"); //DATAKOM SIA gjog#8D#6nOZ#0#8I#6kjHMMx+lyGb#1Q#8F#5tYNBIl#6lIWZmM sl.AddTail("JuYwXYnrU5HTXTsZ8T87zCV+LFsU/MKguuUxcmxxcpC7Mz/Qpoq+fBm/lgvtXJQxz0zpHrAm" "/pgUbB/y0giB8g"); //Enviromech Inc iRCNssYZeUsN#0C#1LExAM#9rSzC#2HxCm#3mrYXFFTuO#5AY sl.AddTail("rxZxyBqMVLzW+qtlHdedtZBUjydVfI8VJreD+nT5LYoUQUT2Fo6fQA7YWw6JSqqO8Ad8KMDH" "ych5KDDScCAt6w"); //DIAL TrS#6NYZldOMS#1q#2EOC#9Ru#5d#9lOh#6QyFHUEd#3E#9BMIEk sl.AddTail("1uJIx2PPy00lXX10sRaZiDqGo1DFtvT/OHdcWxT4RQWs4O3fqKNy6DIkueP8u6dVC+NyWunw" "XD+HsdaTJb1dpg"); //OneUP Technology Nlno#4XWKhgGbM#4#7bbaninFq#7FRxu+OIMKeRNLk/#9Kqo sl.AddTail("v0VAfSGEyxSGxKDqBxXot8OQdMEEiqjlncUei8Movt5NEg/2yUNPzNxKou4TId431In5eryn" "huK6NSm6Hqq3Ow"); //*************ADDED DECEMBER 19th 2002 //Ordered Oct 9 2002 - chargeback Dec 16 2002 (1 license) Graystone Properties [IJfwCJKVrH#1s+#7xDgxnk#1eFbVN#3GCTzGPP/nlOJe#3Ds] //Removed 02/27/2003 apparently we never actually got charged back for it //at this point client has not responded to many emails etc. //sl.AddTail("4mqLXbXbKzVN50stxjqqlicZf+P+solcUtcCsY81OihOCbiFGNFkkTnho/5WxrliN+whXTFJ" //"2mBBrsLct5Aq3w"); //Registered to:[LEXCOM TELECOMMUNICATIONS CO] Activation key:[#4GCq++m#1CUUPjN#6jg#0#4#8/gYh#4pEbicXLFBm#7sSeFzZY]sent out license key for 33 when they only paid for 12 sl.AddTail("REhqlKnu2fIudbkJ1ki1hkUBFfyS7rVT6UmwoyAWN/LwDTLgL3osjSTMjvqt7s1hqqEOirLS" "X8MtGDDWitHjgw"); //OneUP Technology qXxTLyUSsN#6xrsedR#0+#2tYxgNfSjOvq#4bvnV#4/aBiQ#4 sent Feb 26 2002 incorrrectly for 2 users sl.AddTail("io7hjeKtlMuaaYBVgv5VkltzWCMtBd/268wD2JqrgiNks4338aH2jTFPjc9fZ4km4oQghtgJ" "U+fHwSOKpF/Wvg"); //Bethany Lutheran Village Tower Activation key:uJiq#5nWeSUbdCeqhcOnce#3PT#5YzGWI#9#3lw#3AFHKOCaI - incorrect reg name sl.AddTail("bOW/KsYo5EaCha5SiSaJ3kLvQ7kcjsYpEgLuQABka4RMNrTUdgDuQEbcaETHigwBH4Pf6poq" "dQ4QwikONb3B/Q"); //United Business Communications kWo#6#8zNfWHJ/#0SBST#4Emyz#6#4#1uEFjVzcCD#6GSXl#8#4xc replaced with order 747 sl.AddTail("12iQDcyCIoMaaFQtlI/PuNN6QKcW6NhiTKNx7iwvPaYfD594H/afxtiMAwbIXRHzVJgrF/Wx" "T5rdIUNxHi1c6A"); //United Business Communications WIxRPVFaLi#9IEuyR#5rp#6EpggL#9eJsy#4vSzRkG#9xC#7Lc replaced with order 701 sl.AddTail("r+QiRHL0DVfocI4HrYKeRAQ8gCqcBQnbES8t1T8RRd3qiVHak+jFsZaXxQya5fQF8+2oLGdR" "1VgUgkopH9wFAQ"); //Halski Systems, Inc. MnY#3#4LuvCOK#2iHnwctR/xpS#8VU+n#5qNjz#8xeT#3dWTbE replaced with order 746 sl.AddTail("02IjQGIBv3+faD2/9ORxciJw5R/mGUCgMVY3RAjp1NYPK2fBbNiktL5nlDgR3h5mUNK4T6UA" "3y4QxFp9f+aVyA"); //RODIN Computers kjJwtZXyxEA#4rEXDH#3H#2JlzIicG#3E#8Rl#0x#6e#5tF+#9d#8 replaced with order 740 sl.AddTail("jslu0Zg5uOjFCy5Kqet5MnP5lF9q9FoXMN25IsO7OBfgz601jN6CYpoDkyPE4YNoYgBMJBAq" "8hxPPKDG/BNg1w"); //CTT Enterprises LLC oDVXFM#2fcqQg#1#8+Mys#2ZvAZ#8e++nAi#9VOAc#3TwVOkkI replaced with order 730 sl.AddTail("Hgw1sei92aULH24sBxHMbf04yWiovWK8vWyzKzdJ4/ppKfF0eFx+MoXgGhraucqBW7P+zMX7" "ozGxum3fCcQB9Q"); //American Eagle Credit Union #5SvgFpgChPf#8SWXCwe#2awzZfnJPAJWX#2jz#3teI#2#5lLM replaced with order 726 sl.AddTail("ZNrTf1wATOVfEFHepjDKxOLxSlOJSrLpSCwHI6KlXo2u7AMnMvBCKNRe7g+2ABXOLxI1vQuS" "0luqMgU8ayrCIg"); //seamless solutions hjUlVbxLXWredZ#2kQ/eiqOZl/hOkCJ#0#0KYhp#2Gwy#0vs replaced with order 719 sl.AddTail("3jU1NB3hYjTp68o4j1z2RiMfXzUI91tIsznolkmc9qXcoaL3yM6RsGlEw93SJeHH/K75jlVV" "OxuN3M17gpCTVg"); //Cincinnati Test Systems, Inc. o#6oFWxBBYixbsEDN/svh#0U#1#3BREXvTxXJY#2A#2ZOcaLs replaced with order 718 sl.AddTail("AeqZhYdgQXai1bqxVwJBKLSMJdOFtRFpQUe1dqI3nTgSz2jb1u82JeT5+eKATabRf0ekVgoH" "kmyAz+AeblvnEw"); //Cincinnati Test Systems, Inc. c#2#2#2+L#8#8gGKx#8#5NW#0iw#8tZS#8CIFJ#9ME#8G#9v#9wcMmWOs replaced with order 692 sl.AddTail("2wHL43V2LwSFY+wtvL6ZNYA7G2X7CSUPlMNCdph74P7v1nZdiIUmeSzCEM+tyMt3vh8/PK7/" "SiOkzoVJ6lOo3A"); //Superior Service Y#0MHog#1jxf#8OrsWAswNUAuiBMvSDUPZ#0#3WxbglVb#2Hc replaced with order 711 sl.AddTail("yZno722zIC/nvKiUshQNjhWIKoNH3OHDLBowZi/qBa3g0OKankK0CIHftKDrYLoiWqVB1eTr" "h25qOrdEFNZ/fw"); //New Brookland Systems FTJqsgPHObedj#9#0#2GzndIIr#1#1nSlXk#5PWSkYmFbxbbc replaced with order 703 sl.AddTail("2zDOeArppx2bhdhKjrVxwzxmSS602x2lfBZ3rvz1xgMkXnFLEHozDKCET0qFlXJc328yUndI" "Ntxxjl816mOfog"); //Rice University #6#2MrAmx+dHUktLGqI/UMtALPtF#4FptyB#1dfFZiS#2#7#1E replaced with order 695 sl.AddTail("F6xVySHC8avdZ7rrrmKp909zuAW78VzqSwMW0+XoOYs8A46uLrRyI413tl9ejLxrH7RKsiGJ" "HwlZATqQWj3vUw"); //Ed's Locksmiths CYpTosuN#8v#1YlVveDhG/WuVG#3#0eosfnf#9Fux#1CGlXew replaced with order 691 sl.AddTail("0hqWAK1Z8+mmlj3WEyyrspTy5AxylX3L2fkEG45RvAD2/2jk6KtqHk3erlglzLXE7K9DUbGz" "XDIS8GL7jgWmOw"); //OneUP Technology Nlno#4XWKhgGbM#4#7bbaninFq#7FRxu+OIMKeRNLk/#9Kqo replaced with order 688 sl.AddTail("v0VAfSGEyxSGxKDqBxXot8OQdMEEiqjlncUei8Movt5NEg/2yUNPzNxKou4TId431In5eryn" "huK6NSm6Hqq3Ow"); //DATAKOM gjog#8D#6nOZ#0#8I#6kjHMMx+lyGb#1Q#8F#5tYNBIl#6lIWZmM replaced with order 684 sl.AddTail("JuYwXYnrU5HTXTsZ8T87zCV+LFsU/MKguuUxcmxxcpC7Mz/Qpoq+fBm/lgvtXJQxz0zpHrAm" "/pgUbB/y0giB8g"); //Enviromech Inc. iRCNssYZeUsN#0C#1LExAM#9rSzC#2HxCm#3mrYXFFTuO#5AY replaced with order 681 sl.AddTail("rxZxyBqMVLzW+qtlHdedtZBUjydVfI8VJreD+nT5LYoUQUT2Fo6fQA7YWw6JSqqO8Ad8KMDH" "ych5KDDScCAt6w"); //Lutheran Social Services H#7I#9CN#8c#2ZWYqXcBepKbLUcn/cq#1w#1OkRdQiRFcS#9#1s replaced with order 677 sl.AddTail("f/W2bj/x6MTYPpoO5Uvp5dckVlez9j3wINFu+WFUGaercNQasjFyT3JNHiLUelVofW2JLGJd" "cnPwAnd9VjOAJQ"); //DIAL TrS#6NYZldOMS#1q#2EOC#9Ru#5d#9lOh#6QyFHUEd#3E#9BMIEk replaced with order 678 sl.AddTail("1uJIx2PPy00lXX10sRaZiDqGo1DFtvT/OHdcWxT4RQWs4O3fqKNy6DIkueP8u6dVC+NyWunw" "XD+HsdaTJb1dpg"); //Kramer Computer Services [SCqPgo#8cedjtkNakhWh#8Nd#6#7#4Ar#3#1V#0nS#4Wkq#3kw#7#9Q replaced with order 673 sl.AddTail("Bi3DkK7b/i6qeAGBzgucsI7R0D3wKFKBrLgCVqkNySTKKV6TO+mAsijYri5oEE908tuuFtST" "kqxPdHA4+RYdfw"); //EcoLighting Systems Inc HBMP#9Enlbo#7qMOa#3aK#3f#0zI#1gyOU/+U+ZSDMvIV#1zP#0 replaced with order 667 sl.AddTail("W6EBAl/ocpyromWkr+D5yGYH3xgIKxcjSlz7xWKmz04BLrMIgMmqbGMWgy6AVl9MY9g9LIJ7" "vh0hhw919NN4tQ"); //******************* Feb 24th 2003 ********************************************************* //Adtech Systems Inc. RP+djYyVZlPXJynqvwlMQsBcAB#6iWJiAcuf#0mJluo#4s - replaced with order 760 sl.AddTail("B9pBHgg9PL6vJni4ScfA2YUD0ZM7HD2wvJy52V8a1nICzRWU6tsQtdtel7+HdEYZ"); //Wilson Memorial Hospital j#5vmyDmumc#9evF/MfMBUyKNQRpyC+KW#3dofQ#4#1DO#7dI replaced with order 775 sl.AddTail("7atXZbYg727klvoBI0MsLl7h0MEwfO1+LOmim1W+OQ42y5Z098rSw+lZ7uGDaD882/HVYomq" "9DPJ3cWzGLO4ng=="); //Total Technology Integrators LLC OfyOaZ+dvBWtbjgxnQysx#1#5rL#3AsOEbAwgd#8dSdh#1#9#8 replaced with order 777 sl.AddTail("7/ZzsIbSpCOGjPyV4+dKQl4YEq2ORWFO31njaq8rpMrN0OgmScIag8iqM9l+zKlY5v1ktPtP" "664/Tzd+O01DRQ=="); //Ed's Locksmiths #6Q#7#0#6ph#9#1S#9PodWp#3#8Pg/STKGlMtcO#4rGgn#5EyqoRA#4 replaced with order 779 sl.AddTail("EctgtDWZBX1/cR5cRH8UkssbaBbuxv4BH+Yx1qpsD1X5Kn2GovwTFL373N9lBX2KA0ZjrIVj" "CHWuG7YDAqbUZw=="); //Ohmart/VEGA Corp. dnqhYyR#7G#5Xy#8#3#5BqiWrVeT#1Kwm#3me#8PJ#5#8uAjE#4/#3Y replaced with order 780 sl.AddTail("YbnUcS7LPd0wH6S2/dX2lzK9aGLidQyiIvCtvzoSAW4gcunHXl4vV7dN2j6S4qqwn/TF5Ej+" "o+jAbIE4CnUZmQ=="); //Frank's True Value Hardware Co. hDB#0gpfCUZSPi/zCYc#6MUKQzld#3lxD#2/fYJ#9kqzMJwg requested refund on order 759 sl.AddTail("hqvn36VX5SY+JqQsvXkd8bs9Lediy/ntYGMbz+LHiA7MOW2ypy0up1x39GYFDFCLtQBiWvOb" "o1QiPbrKmII1pg=="); //previous order Certified Solutions #9NqyXCXVoEWFHbeZ#8TngSDDNibbL#9#4U+yCCdflzzF/g replaced with order 784 sl.AddTail("1kM2fMP5bYwZxhpgsWRQgn68wTj+lJsu5tnvrCrGKg/EbrAgAZuKjuceOzt7SZQz"); //previous order Paul Labute, Inc. #7#0imEWy#5GkutkejuJS#1WoIx#4/#7qu#4#2aTsvHYPxCQYXs replaced with order 789 sl.AddTail("eNaYFh5GbE97gtmjJWJ+weThrd9eqnb6JZ6+Xlp5CrJfmKkoeEK5R7b1fliWIhEcRs7agiRe" "dWs+sQMSjjqIUQ=="); //previous order Comp-U-Help Computers, Inc HW#9+UlZzcM#7IXTa#6#2pa#5yslJ#6hf#2T#9Mz#9aq#4YLWoQjs replaced with order 802 sl.AddTail("Z3XPSSOPET7hDCiu+906+8eVFRf+FW7VyQ+OLI5DL9IXhHdgIco8NAG+MtZnJiir6lQFouym" "4TZlZYrJH1mG3g=="); //previous order ServiceCentret ApS CfEYp#5#9qcj#5mQqkCgcoD#2TOKFWumcA#3+cnTn#9eBqV/E replaced with order 818 sl.AddTail("fhmjCgxIu22wVCp8j5X3jjJSb9bxAbXxshLTCPWWrtB4RV36bzK0WL4zpR8DEOXnJ8W8xU9/" "aayNGXjYHZq1Fg=="); //combined orders Wizard Enterprises WfPPvuL#3mohNMjk#8lGIcOG#3L#1piAqzcAvwvINL+ImOE sl.AddTail("/I90xJXJYEHbRHfZuVoLGndWMebuKfUzn2MnyuL1jqa+kWoA0S/k8oEK4a1JSIso"); //combined orders Wizard Enterprises G#0hDCyCMe/g#4#1gGwmnvP#1mrlsGmOGVa+d#1BsoemMYqw sl.AddTail("TldyPAapGIUc+oRO3FvCZC7bl/STqdSq8exn/j0X1jToLPN2+rKRYdRhTumq1sQ5iI0YF8wW" "MJyVP/VbJeBb6A=="); //previous order Symasys iRUW#8jElfWBwMemwdAcTPXGaDUeg#7S#0/NcNox#0#7oPdQ replaced with order 825 //UPDATE June 24th 2003, they did not pay for the replacement key so re-instating the original paid for one //and zapped the new one that replaced this, see below //sl.AddTail("nJq4xbtRkW+bOhei5uZruuC735gHUyHoA7DoQE/6jOac73R7KUJu27kGaqSweTwUVAw4BUK1" //"4bgbBeVyy+lW1w=="); //previous order Motorola Hong Kong #5#4MGTZZBdr#9eo#3mERZ+JG#7#0rnBZyaKVTzIBFvbu#7#3#4Q replaced with orders 845, 846, 847 combined sl.AddTail("HKo6GZlogrrHy0ZdE9SR4QN/DQgWBz872Ae8AyD4WZU8JwsImCuLnjeHvKCNabKhjb0u837r" "+CWP8kpeSdnbiw=="); //Certified Solutions #9NqyXCXVoEWFHbeZ#8TngSDDNibbL#9#4U+yCCdflzzF/g on Feb 26 2003 as they purchased and than decided afterwards it did not meet their needs sl.AddTail("1kM2fMP5bYwZxhpgsWRQgn68wTj+lJsu5tnvrCrGKg/EbrAgAZuKjuceOzt7SZQz"); //replacement [Ace Hardware/The Tool Haus] Activation key: [] replaced with order 890 sl.AddTail("PcMraG1a7nwVsRKqmVOy/SlY8RNcq9zEn/I3j3i1kWSVvQMf421Jaom4CVfzfTGk"); //replacement Registered to:[Motorola Hong Kong] Activation key:[Trt#2cpxTCYA#3xoYUfTKJQ+DjWID+pMlcbhOLZ#5h#2o#8E] replaced with order 896 sl.AddTail("nnyRluZgMNwIxhLJdXzp9r5qRl2EVIVTcp8WdkdVHJ0DTgfvQcJHEyM+jNI/iEXT9QcrU9aU" "K1SYvxs4i4gNyA=="); //replacment Innovative Systems of Virginia p/f#6d#5EPoBGzXv#7LP#6JK#1ETVyyYv+dPv#4Fw#9ExvKado with order 900 sl.AddTail("3Z1/rGnazenqgXclNvstxMOkM4Z9/UrA03Es4dTDn2EU3R/VtbLAv62vYcmZP0rC1z1MWjJU" "Sqc5XZrH7LWEoA=="); //replacment Registered to: [Motorola Hong Kong] Activation key: [tecludkt#2R#4JEY#1ec+qmGgq#4TYrlX#2NMytMT+Sbd#0b#4] with orders 899 & 898 sl.AddTail("xhp20X6EzKTrOgeplGf+5OV1XFVjHvXhs9ECuAWa1THTq0iei5LCRjxiWkXd/Z4TFKRBWoES" "zhX80GL9rgHbQQ=="); //replacement DATAKOM ReaVLKnMRAfJHV#1vIBdCxSA#1nsEi#1SG#9bXDaFN/GmkQ sl.AddTail("E/eNrG/GxggnGCHb/bgbjTuIihnQlqseKSAUYeuRSqDIP2+ybFXfyQkoGa8oM9dS"); //replacment DATAKOM gjog#8D#6nOZ#0#8I#6kjHMMx+lyGb#1Q#8F#5tYNBIl#6lIWZmM sl.AddTail("JuYwXYnrU5HTXTsZ8T87zCV+LFsU/MKguuUxcmxxcpC7Mz/Qpoq+fBm/lgvtXJQxz0zpHrAm" "/pgUbB/y0giB8g"); //replacement DATAKOM SIA rg#9FNLJ+#9JbWEBWhfq#2r#2U#6#7qNxYOUFZhhhXtHJlTE#0 replaced with order 908 sl.AddTail("Ceijwl4eFBACDKtBBGCtHDy6alWuXZL2lAwrjLnluqvJPyqmMIaFuav54kiN11Fr944tnJxl" "xkQzVVc8esBCxA=="); //replacement [Motorola Hong Kong]Activation key:[ctSQ#9XaW#8laxqbySlnhd+pbbegsVmcfQqi#9qJLl#0I#7#4] sl.AddTail("RsZ+vZS1y8VZ3u6hapEEmDGJmF7KoGHc9uVoAp1xWIxGXu9geVSE0Zb2j04Xx6SeWz4+zteG" "P8W+A+WoggG3YA=="); //replacement Motorola Hong Kong [V#8AozQr#0W#8Gextv#6JQNF#9rZEE#7tUNkPVdOmFB#8hXK#6c] sl.AddTail("qOkbROxBNl4JbHZ5Qx+GQveAThxf3soDxT5jkKDGqTbm3Nebe6OLzhJ7QCkaRSkImzz1YdLA" "Tmb9gzKdOWQLpw=="); //wrong name [Adam Steele] Activation key:[G#0jrlyEkMW+lh#0AbMCcs#1+uw/XgyNBZBYM/n#4ixY#9z#0] sl.AddTail("sYzwH4zkEKNCYhIFWh402gueIe0tCX7TuQhh7Uj/YPV2DqmTOshjc57Fq8KxnlQI9+ZBO3SK" "ghAv2WJFOl1Tdw=="); //name change [Pete Miesen]Activation key:[p#2swAcPp#5+CE#8IesoE#4z#0Hquh+rlbEVDvjLQ#0k/RoAE] sl.AddTail("e1wIqeKUoEvtL3+8HGZfGrmb3Am4yvJb7bOffMROR20tPxXM2ZlgijtD1kogpeHOsprPhAYU" "V03M8cUhGji9Ig=="); //replacement Convergent Technology Services Activation key:[hgnBEy#8#0bXlAhT#8s#9SVqjpuPPG+txAcurEORTlRdUVg] sl.AddTail("aj97r+b+09vZ7ut4aB9p26Dik3Y1HG0HCuAAEOl0S5UoWlAeCpegKl0kj8VUm3OU"); //replacement Pro Security Products [XtDkrmuEukVdqX+#3ESg#0STRCBBafQHKCCzPROEnICBA] sl.AddTail("+Dp1CjCWQonsL2DRpNLq+OP0/DVFjW58Nxj0dyK7RyIKALb+SWMiUv3HyuCzDA9O"); //replacement Alpha Mechanical LLC [#5Brlkr#5lTjsybQMnCkouwPZjEX#8rEH#8/uNouDqq+J#9A] sl.AddTail("l+l0sw2BUGdcdUufwQF4ffvAGjcDvnLHDhf8WzfbItNVhGFKMMr4CDhENtqch9nUy3yRTpx3" "zIa9+ghGuik/0Q=="); //replacement [Alpha Mechanical LLC] Activation key: [#4dVHt#9Nhb#5Y#7L#5qVaVXBITbtbQxVK#1Z#5rqfMZcHjqkU] sl.AddTail("PmcNVq9VkfSb0eVvA1HGIUVvpQ3sTImBA3ecVQCHBcXGVhxBVuPiqjQre263tQmuJEuSG8OT" "Xk/n7ZR0W2kMUg=="); //name change Registered to:> [Apha Medical Equipment N.Y., Inc.]> Activation key:> [M+Z#9JODlk#6#7#0GpJE/HSGmdea#5p#7#9W#7aBd#3#0nZSbv#7#0I] sl.AddTail("iHK/gMMg7qgsfD9XW8USBQS7a2b8ttIZXEcjj426yN5wGvGQgZMgmqW6OkeHvxZu9I4AZayl" "8/EmCin/es9boA=="); //replacement [RODIN Computers]Activation key:[#9g#2VwZ#3fXoFPg#1z#1L#9Zp#6EQCWRHFxev#1yLiGC/W#6#1RE] sl.AddTail("KVn7IKnLqlGwrOhRYiS3jnoewhD6GbELvTGncR3xf2xn122KTfE69NT/r+dA4jA7XAB11Ae9" "8cEiX2Pd7VFdaA=="); //replacement WS Electrical & A/C, Inc. Activation key:[FrcBH#0yd#5yobFfj#6BdEnPerFCDoS#8TVR#1vNQLfM#1AFU] sl.AddTail("IzyuQz79AbwLK8v2vxjKerhYaIdIdFhVYFEGOxiiugqGBVUNsrAFyrssMvZtCchua7WRhM+p" "jqLUQYI6u/lneg=="); //replacement Computer Services Group #9FMSvqcal#8BSoP/m+W#7a#4qPlPflLbM#5#1gukjCeL#1jSM sl.AddTail("1+ggd945GxRvx4TDtofocmVAwNuGOTYKhnXPg7S0hdubiIkbtwyPFfBsoq9Ghte3YyhcjRIe" "BcRKTTuRoaAMFQ=="); //replacement CRS Technology #8CaGL#2bvRkOpy#0SWQDyiExcxz#2tsTwPv#2GGL#7Fet#0M#4 sl.AddTail("VRWl9vGnX3cMCnvK8/EfcSkS3beQ+B0cciVAdseCVHOdRA4DbQZoDzvHu0w/G2N0oGxtmR4T" "Z05qQUr30yxk+g=="); //replacement Nova Biomedical UK #7SE#8g#9xtNSzNPzTe#6zxmDi#0#4sHbV1CVtYqmuAkxVPd#8 //sl.AddTail(); //replacement key [Beech Brook]Activation key:[HiWQ#6dFXvXyxzeIlB#0tYlHuEbCZB#5Js#9Yx/MD#8E#3m#4M] sl.AddTail("ojWxebwZWlS+93Sp48BJdqZwsaIIdPlW4sr77odY4LI9vbMIkcsl5v5VNTtd9HNqKCsOgT7x" "IkvToz9q2SEoKg=="); //replacement Beech Brook Activation key: [qYK#7pU/#8e#2VufpADaWy#1JpYCBXGCcMA#1EUyYDuAe#5kM] sl.AddTail("GehU8q87DsEM/QjVtb8e0uzR4Uj646UuBtMisaWzY1HAGl5rAkH7Y98iIokQlA3p6JLZcleb" "vCNfYdW9h2Vmgg=="); //replacement ASUC-auxiliary Activation key: [jzJkmdWx+wk#5#7#5gNz#9tw#0MZ#8q#9#0nYdke#6#2#4#6TpRV#4/Q] sl.AddTail("YSuyIG6Tb/mepCrmqrwO0zAmGhDXq8OG8G+QeG2XgulWL6wvH5b8qsh5t5se2FeBEIj8uj41" "3uiGMn1Cl7zrgw=="); //replacement Nova Biomedical UK #7SE#8g#9xtNSzNPzTe#6zxmDi#0#4sHbVlCVtYqmuAkxVPd#8 sl.AddTail("rERvtVvDAL9eP9yRNnMDOXmIsBogHbV5/YSi9xhERbmgcJ7+ZOeZ3ZZGn5pPK21ofPw9DubS" "oxKTSWuGahkhMA=="); //replacement Seamless Solutions Activation key:[oSX+Z#6ZvmNyhJXixFd#6KFHiwqbmvcSYxq#0Z#1b#5DGUe#4] sl.AddTail("CGFuHyt0xD9natbL6ZGscrhWZJeJljJu/WAA6j76sp/VXJzpb0qZC3m/r018YtRvOQZ8e6jW" "9S8qENzgb6Zzdg=="); //replacement key Midwest Networking, Inc. RaOYOKFCeyXqRWy#4aOlRgBuMYasOoq#5QOXCnLdhyXp#4 sl.AddTail("drrNU/OwvW/wWR2KXDIMaHcNI3w3uiAsNDuGQWdKOa6UlRBHPLXIQM1ujOKD2jLA"); //replacement key Aspire Technical Solutions [L#1MR#6NqFg/hJVdPyzQyDlWuPqn#3vAh#5b#0P#8mibgPc/k] sl.AddTail("DZByDVaQ2iHzuN/cK4xsMTov42+8+fEk5jx5s4IsJ6DZkOi4yz6Q1yGVMUoGM2pjnVTA7Ulr" "hHP8boLzH0TVmQ=="); //replacement key Area251 Activation key: TGQBNPX#0mRIBJucdt#9#4+tKIS#2ZLNnW#8YbqEeQOdAZKs sl.AddTail("3WTPUov4dWc88VBYemVYFO3eCEkJ7dDrCxe81OM3GpmvrIfeGHoBSrKLRF8yLR5kFEE53xFC" "FynmAZhwkvBRMQ=="); //replacement key ViableLinks Inc. prr#3kzLKaEue#2aLJ#8KgsI#8PISfscxctrSgX#8#8r#3WAFg sl.AddTail("oan9HUZJ+IpX2OZjVjsJalJMABwSMwfBcokbMUpUzEwbq0nYw5jeCC051PFJJbIUusB2W7d5" "+O+3X87nvtDTKA=="); //replacement key OneUP Technology IS#0a#0#3gxZX#8w#6UAzqHZluLN#5E#3#2#0r#0Nr+wwFbS#7HLDU sl.AddTail("6QuM3G7IVs6Sre6vk+XF41dJujdCUFu5SIq2F74tt3ra3qMk8XtjCK9BcnlpwOue1MYmUWgq" "uOiO1B52l3jUtw=="); //replacement key Second City Computers [igN#8#6ugudYZ#8JHDmHzQZPWTLggYN#7iTu+#7MHpTuUz/s] sl.AddTail("lBsZueX+tq9eCUj4nLr6BpYyjWLu5PN7iP214oUcOGenB8Tqmy1NlQC052ruBAY7aIrYzpVk" "FHZjY57i32VcoA=="); //purchase order not paid for - Symasys WAaIXt#8pAVceRHPXeO+hLU/b#1Gj#6kkQuKTHpHhwBjc#4 total 6 licenses - 3 on this purchase order //re-allow previous order Symasys iRUW#8jElfWBwMemwdAcTPXGaDUeg#7S#0/NcNox#0#7oPdQ which is for total 3 licenses only. sl.AddTail("iudEoN0hzPbg/0Pnvu7JpkHSR3GYNVHUYW7LZCAjc/A0MWqGKiQMxC/imTLIcD+Q"); //purchase order not paid Furello Services Company Activation key:[zwq/YH#6cUmq#5siDLVH#3#2r#9RWheFM#1#8jCflvEgkUUe/E] //ARAS purchase order not paid ARAS license = [O#7eep#9hATm#1x#9#9#0ApB#7CCPt#7BTJ+#7WpMDiYD#2K#3c#5HE] for Furello Services Company ShareIT ref#2774793 sl.AddTail("ATbm/+utHUIAyaAEPlejOtRiNa+iIaHBT4L1CvXianLt0Ooc5f2HRkQsqKJpsYwH4OGFfXxS" "dGs/TPaM4xcFYg=="); //purchase order not paid [Geek to the Rescue, L.L.C.] Activation key: [u#6oQ#9P#8jsiVkJx#0pHrQK#8UcZt#5w+ESHKHNqv#1kZvPMM] sl.AddTail("3Qr4gGpHDpwAjgj5Xts9P6bIaAaw/KUunKamaEx6wd06ClWsPbTtCvOq8QIdRZF3q/TY4Sm0" "Anw8TYT0P8zvKA=="); //order cancelled [University of Rochester] Activation key:[QHeyyXlcjLOQtJDOO#1AETWx#1OT/NOc+CiLu#1f#0QxN#4k] (this was the screwup order sl.AddTail("+qetf4mnkk1BN0/fA30EeepAoeWcEbv4SYPbSkLuAZo2GqLHcmBK1rFLW5roPVDSy3WtnGjr" "UUwumsTWygqcSA=="); //replacement key sent for [University of Rochester Medical Center]Activation key:[+#5dMQC#7t#4DjVR#0VGzaaNmCcHEwvW#2mCqRz#3/xhzFr#3#4] sl.AddTail("QE80GTWQ1bpVtgMDSM+7L83ufmjZIWtVZv4ylRayaP2lVCk6tSi1YMgw4OhfKCMCgD2EInSK" "TCO2fesJQIs20g=="); //Zappage of original 5 user AyaNova trial key //Evaluation 3aI45wVc+c90DYMyOlfxUeEAiqlpfa9Gw39cryvo3jY sl.AddTail("QG8m8huOPZScC5ouosfpCZkiT6Pxk3prz2DVFfuP/uoLu0hIrXtTYbfS/t4k8MAf"); //Zappage of newer 15 user AyaNova trial key //Evaluation IN3X6ZeCycn3lrsJgw4cTkNfjMSkKLwLEVj22VYwViE sl.AddTail("WSc+ABFLu8aBdflkmwiFRmJDnT6XutUd+65IjqO7Q4zCzWsD7aJgkBE/OJdmFsOx" ); //replacement key [Motorola Electronics Pte Ltd (Singapore)] [VtCZbMxFNem#1rsN#3#7#1ugCPqpLLhdWi#8WJnJZRJQzQhI] sl.AddTail("9I5p02wWofDdmsFvRYTg8jXlouRg+fWPUDgMbCXQ4GjNe8RH3sZiABG4GyChkiKS90wpT8f1Khl77WpNt4NzXg"); //replacement key Vicom Australia Pty Ltd Activation key: [xDpxXuws#9XYwxSOXKYIlq/IIUkNj#4iCUTxJ#7WxlLf#3Q] sl.AddTail("5i6FaH5zA6bMLFFJKRy3W7s+GmNlnOKxlffC/HQnezlyyQ/y3KdCAdBAK8SXHXIu"); //replacement key Archer Integration L.L.C. #8cGX#0Mvv#2/fCfMekzxOIw/DKmD#5DeceD+#0hQEB#9hc#1#8 sl.AddTail("/kEmZJPN1kZ9Q14KFXdODViAJF3SIEBoapoEFnFK1y+OjNX+68VKFUutbq+ghZZWsovQexWd" "oy9Smcoi2sOsvQ=="); //replacement key Logical Solutions dOE#2XiAoANsRWwM#4HcdCWsgzdxM#9VxlW#9ZUoQRE#0yIY sl.AddTail("Yx/p/e5I8ve0iTa4JnJYQNRHyuZiQKxh6VGTklcPc9cMMeqhjev7qNvfh3uKAcoCEldm19BL" "hM+OTJbqJPimPw=="); //replacement key Bloodhound Solutions, Inc. [HvpmjQDA#8isghjDi#4AhYKZ#1vkqLRqqkz#0#9IUe#6#2mjXk] sl.AddTail("j1p8r+BdzpVneRrioQzh+tH37MFyi0kQuZmENuY/r4U+MmaCxKMyS33Zd97kIWtkWmgXYWmy" "ZMKMA9DsJ/ZGHQ=="); //replacment key Bloodhound Solutions, Inc. [OVgs#4jGRHAzshk/UmeYfca#4AaIIKroSNZmFuYXIdFQo] sl.AddTail("oO0NrgLxyDNrww0phBE2kS4fjaGoZ9LJc1VQQ7fBFXMvg/oN/YH/j8x96bnWGd5+"); //replacement key Turner Technical Services, Inc. QM#1#9JLzN/YkrfQ#7Ihwte#5IxttkdcXc#5xZanUitEhX#8Y sl.AddTail("eudgkwXJ8dC2AbxBhkZsuKgHnd20oUjfKsuKj3/9unxQV4ep7+zgMRY2r2CdDeQ8bjgwb/s1" "F/AlRGX09X80/A=="); //replacement key Chicago Cash Register, Inc. [gmiFPAzpYtqhdo+I#5TdPBhgP#9Luki#9uuqspz/LkNI#1#8] sl.AddTail("yyM9iY/jH8CZ27sqkVpnvF62wGNb/TlbavOJiMiz6tZef4/b44vuJXG8Q4uFqAvJmbIjEilc" "tg3nVNfYfIEKZA=="); //replacement key I Fix Computers, Inc. #5neU+a#4EL#0HkYwEIk+L#0#4b#1#8dmmfLfSjBhQo#0AuBuAU sl.AddTail("hLaRQQ6RgD1LSnnC7prfC350zcX1o6Wt58Yi+bn2DsAsbZPvXkzNOoBST5ellYgVdpBlHrBD" "AWt7bR0/7i8XWw=="); //replacement key Lanier Health Services [ZgcuYr+qVktHx#4HE#4HfRdzoh#1PWzArKGoyfYl#0ZNp#5M] sl.AddTail("4PehIUoYSkpHpPJb76PQKWOIwW4pXXbQevYsG5DW9YUFiuBe8jbdDfwW8xe839nAYRRl/aHT" "ZFoiaMo5LDgKhA=="); //replacement key Spartan Oil Corporation [npUlQhAmeo#3T/wdfkWli#6x#6GrOeoUKOvd/CcQh#0OIUE] sl.AddTail("jtIzza66+Lc43ABHBYcszr0JcVcIP+Y+F7EBwbt92OLOcVM+0cOiWIPxQfKEUJfV"); //replacement key [ESM, Inc.] [JuSl/oQLViBoP+#0bmyFrez#7lyI#6kyPUpsMOuRD#3hTto] sl.AddTail("KgizuGQ/j8VNl4mJsXH7MdK9B7YQmRR09Ok+q46X6SX2llrAZJHrftJV/1KZtU7p"); //replacement key Kramer Computer Services fh#9#6F#1#4lpMt#7#9#7dS#7nyP#5rYmiedRgbjaFgZSXZuGPOU sl.AddTail("bz5wqevmSk5XLO+7178Aey0kwrUJm+4nGeXZcDT1K3wf+G94bTBYronpgNOlAB7zJ2DrnER0" "VVXqFVtUu+CjBg=="); //replacement key Gator Technologies h#9XJrzTZ/o#0AoYBtV#1dodZVsGADGnUpOkaqstO#5bs#1E sl.AddTail("Qo/6lAhaES3f5B/Jx/2FLMFRrxslhMdBJeumMxCNgOq4vgrbTszT5VPIK3pidzdL/LKNPdV1" "04hr5Gk7L1HRdA=="); //Gave away keycode on the internet Team ESD laq#2fD#5UIfyMpP#2FKqEZKToiJV#1ih#3Pk#4NSEgI+B/Ew sl.AddTail("HrUoTrNTFq0S7QRjoVhc4cGUR4hznPSpkZdAnOEvK65dhiW8J9mPr8Sk3nCP7c0EHuXRQpTO" "IyZyJ9vEfVbDqw=="); //refund because she's dumb - NETTEKny [#6#1EETlTrCvTYAFfRJFaq#6UKqeJKwiYUxZ#0+l#5hTaSwY] sl.AddTail("6d8mg2tYLFOT187jmjyH/86+ZmP/z7kO3vkfESEc9XXpGF/g5S/dueVhvw1oWRWG3MyGmw0y" "nlt/ed/we0vNqw=="); //replacement key CNK Computer Solutions, Inc. rhF#2#4jFh#0XlHshC#6IlmBvvqtFzKTaWCELd#1UHh#4HavE sl.AddTail("JH7ZbYvXYaF/a/rGRdaWF7g2F5DABCU+lBPFjXnev49Ee/k+BVeHCUID+fn7EEpGRY0HEPP8" "FyS3yDfUGCGPXA=="); //replacement key MIAD Systems Inc. gvmz#3ZxR#7VpS#7hlk#1ay#5r#8hmjok#2Z#4+z/TYmUy#7#2#5dE sl.AddTail("umxnJQngWmNmUbhYGoQHv7F8EF8QAw5rPd422x0xCrsv5zpnh8RsMIy2JSenJnGh9ijWn1+X" "nJV0AeFG0AmyKg=="); //replacement key Matt-A-Mar Marina QUrLX#1ImHCHQPMTuArsE#2fpgFe/jSpyabdEqBnim#6y#4 sl.AddTail("NBPSA9jLY7DdCW+7hzGlTES7vXIY9N1RKJWkBGMVSzD0Tc/exv3l2SbHS9xGL6Bc"); //replacement key Absolute Sound /l#2/nzVro#3XgsKmz+ZfF/U#4+C#8B#5XWoyEclEvHaXuO#4 sl.AddTail("BQ0zmVOt48hb06kBloPpYRd+T6c8lcievKSNSG/zITtZmkNfy0SOfBkvWGxOvy5qEem51/jt" "Be6QgmUoJIR/dg=="); //replacement key Universal Tel Data Inc. maLfNc/#9#0AkK#3HDotfnVHa#2BozsweyNeiBVFIZEnISo sl.AddTail("NwofMQ75rWYzDUjxnBFcwUWjrG0nxYg2vdfk8TjekDHkEDbKoweKlWRk7b3UfacT"); //replacement key Hans On Systems zG#6jM#4XeBWjPRAIxJL#6cjSn#4qtwoWtUwKj/nsGSc#0gk sl.AddTail("1D3TMditPzxYRUj1FohuAk8hY2fiadQKrTjQzQTrdIQlY0ildko6nY4eGd1mkD8aInqMRrq2" "vAPjebeZNzWkww=="); //replacement key allendale machinery systems [wDtimzl#6Tz#1MddyG#0H#5#4FctJkdvFFKEaPGPRKF#5#9jSo] sl.AddTail("NYLqsafDvIFpXvaf+KxZFvLUr6sHGqzeexSZYIooGMYOPJu24VXPdwGLMZ2b2cCxRkSXrvUf" "SwIu9dMPnfTBYw=="); //replacement key Voda Computer Systems fFlVCUNVJK/rBRt#1rvKSaEjecfLBgF#6zeQSn#5#9Z#8ang sl.AddTail("Ix2R4nAb3xVRTi1CvyYhuhmSUKXcUoFgaWPykfRXapNVwv/BMu0hVxInZYfxLqPjktmYezr/" "ZUGBvGjJKB3bRQ=="); //replacement key Aspire Technical Solutions Yy#5eT+z#8#8uze#0#0#8GCOsw#2mFpuR#0UZxemLphFABZf#6#3Y sl.AddTail("L3dfN46qiJ1IVfBq7twoTPPIcJvPg1yMYJAD4ICDs915ILvw9qYGYItlCXPZ8clbNqP8Li9Q" "8fVYiWKpGOKeGQ=="); //replacement key DATAKOM QS#6YzqZ+tQhos#3/Ji#6#6WDUPhjKYqHyQLlJoQxLbMVm#8 sl.AddTail("MgX7n0fYEd0pwZA1BGdttWO2zbGhm98VAYibWtdtI+HR5Rrnu/djb88s+zxb/F0PSiibjbRO" "Jb87fUmhnpiD/g=="); //replacement key McMinnville Access Company Z/#4#2ji+XoQQHp#9#3AL#9Mnak+hzU#1szXlGBw#3zXxSaEkI sl.AddTail("mYewMcWBYYJapid09pxmCrohET/ZORI9MtCSYUeHOSucOYl9b2w+uD+OM7mi+/XlrI61A484" "fY+amWlWRd4w1Q=="); //replacement key Motorola Australia HE#5zX#2PW#0tM#3z#6SANGwZrvxaqTFkMIzhnWeAW#3#7#8Z#9A sl.AddTail("1fPn+N2EXjl9Y1kIdpZe3ML3cQizpxsMhrx8IwcEhUvHimuV3AjqSSDPnisTE+CE0C4nIa6r" "WhNtJr+kaAkBUQ=="); //replacement key CRS Technology [cFHN#8sGppPWZ#5#5yfMck#4sabe+dBXiDeUMkc#4OEbA#2#6Y] sl.AddTail("ROkvdyiFPsQQ0kciwF7v5W7tYLPkIpwsdoFH/WZuu1Qoe0cNMirR+l3EAy59fekrBqMxk3Ks" "ZhzTEwcn5Y5ysw=="); //replacement key Computer Concepts of Louisiana, LLC [jiJf#5fiSya#6pH#6ChcVsVV#3es#5#6#0sD#6FY#1gROD#4pfJuI] sl.AddTail("ETrw18NWgyQh4ZshbKFdgg0gRiXKYNqncUhbe5vm6N2bDIuYB9reCN7wOxsq4uwmVROarrTb" "Wkglmw1t2GG9WQ=="); //replacement key [Tekworks] Activation key:[RNlhqq#6Y+CMVoNDkG#7#3#5JDRWQZWPH#5#1#4#7rZC#3iAfszI] sl.AddTail("910g49XAPIy+fem3xHrUnshH4WkgYNp28QxdNEnxah4QijjPkBbj7QXE0Qc5zOOQnNOygRJf" "3ycBZyDHA2j/LQ=="); //replacement key Absolute Sound TH#6hpDbNKQXZeYB#3ffSwUeiYBg#7ArTqY/ayf#6#6aR#9#3#4 sl.AddTail("TkwkTEILY/Kx5+d4tY3ooaTfk74UrsIFo2cSTQMJXsvsqJ3AWb0mah2VzpbvaMkoSPfAnu5a" "Httap5wIPuSrOQ=="); //you had sent this out a long time ago - TESTONLY Activation key:[jdnxoeVjN#2KZaf#6SHCSjkVBRc#9QllH#3UYITzvEukc#9E] sl.AddTail("KxjH+4aPqZNpqFuE/12gC3Im4f1WH8qMVlQKM+lgsCUpFHbVKyqvHAUXuPcNC7i4BMQ/DW0U" "LLs3UFru19DVvA=="); //replacement key Vicom Australia Pty Ltd ePB#5XPvlHPfRsui#6#1w#8IqM+Nnt#6zb#4#9Kv#9BtaPqk#7#6A sl.AddTail("fPWWNsq0UYDJSG0jPFjC12rBB12t03VjnzFO5qSolpsUunNGRcGv3UeKX0mzU3WEKvl93qBl" "qW8dbggEVsqtcw=="); //replacement key Microland Computer Center b#0HXVeQSy#9ETRTy#2ZqZB+dukB#4Kn#6#6nL#2maiUgc#1#6rQ sl.AddTail("thabxTFNSCststK9I87C0OSMQSXW+rIE25sZFrWdqQHS+58pDoZ9NY7l5Mqyys+cRcF/7vH9" "Vc9EnRCr+e9tww=="); //replacement key ITnorth.ca [S#7evuYSwQLIDlgpyZVwx#9/JxZVYfiqq#3qS#6yccPTuJQ] sl.AddTail("6kWgduLhdD0qIP5jD1DngMJ7+SLnjFIew6kdveRzKHRlB/HJ5Ovo8UQGWEI5K3IM"); //replacement key ViableLinks Inc. LJtj#6#3m#8bknXITle#3#3xSlH#2lFYOUGz#3hJGAUqxjkLAQ sl.AddTail("27JekL2YpkitiPCbf0Q+0y3iczjfDEqUvzGHZOXj+wLebskOjYFTaMeb97OCHAlmwvcQdJ9r" "0qH5D15X6tXbeQ=="); //replacement key Nicholson Manufacturing [#1shNELGaSU#0qljnrh#7#4/xYSgFQQF+JwmZAmuLV#5#1tz#0] sl.AddTail("k4lLy7xZCG1ybhgADXmtQfR6o+ZKJ4hR/0MfoicQLORTu6VygJlfjDrurJ+XJyZeHDY5yXQY" "Vf6lot/q2emRfQ=="); //replacement key Halant Group T/A Whyalla Computer Centre [wo#7tbpf#7V+X#8yadvqXeGxPTVVr+E#8NfKNfeVlxii+DE] sl.AddTail("CAD2fksIXNnw1YvfNJyXiofSxLts62kqRnu6OVBeFx3Df46sHOKyS6rXLMGEZ5sh"); //replacement key Int. Food Services Corp. [Fk#0MDUhKv+HrYrYLX#5q#7#9GM#9bof#9#3Rh/F+DvTvf#9PAQ] sl.AddTail("CDB+JXTSbOayx0ynmZa7n05llHP4/RWALyXM2DJLQcdusDPj7o7aHi0qhzc6DNLosHC45tUS" "Zl2S6XDvhFoArA=="); //replacement key United Business Communications jMgWTMDDuPX#9OVRrlN#3MfUHsZQ#0nRfStezrrmvvHtGA sl.AddTail("tzIvEGIA/opMOdfbCxvcoVAu5RjCVxWdcWayh+ZY9e8aqsFmex6nnXusCjrpDuvk"); //replacement key Mechanix Wear #7LyZBTJMNY#5theb+MtglplA#6HRj#6#5FbffShYuCWNl/w sl.AddTail("zyLsARf1wFnkmAawXRUIf6r0LcG/iAruJ7hQNYNMLtsqmGuawQEmBDGvPkeRI/RIAPX12W5D" "oxGUcHajAvgA4w=="); //replacement key Speltec RmSlkJaQDRqDzHy#8#2SXngPxN#9u#2#6oWFnLJGrHt#1l#4CU sl.AddTail("Tvm7fG+GpFgTCrYu54xevUmYlQQU+1f4UHT8Fw1qWIUVRJZ9n5pOVq7zjXXNySWJnowrXBRW" "v58kXezAdNxwFg=="); //replacement key PMES, Inc. xFvN#6z#0FNZNNFAp#3L+#7#0OKhR#3#2Wbx#3xS#1D#4ZN#7#7su#1w sl.AddTail("hts4TbGx65bsFsKNGcbfgg8BsvUNjqw4x7HsuhgJ7BxoB86ls9+dSs3RtIQgTAtUoNZbI5Yi" "/qFno8de8XMZ4Q=="); //replacement key PMES, Inc. PKuwcarP#8/#5HOS#9#1ejVsbwg#7KSt+#7Imk#6L#5BAW#4RUkE sl.AddTail("pew3Pk74wXfHJzsGf+QSD1SwscSK0HtOSvivoc1KqqO9vZsZB3UH8TXVYrujM987v/NIJ4dn" "oTZWUflyZDua3Q=="); //replacement key Aspire Technical Solutions lYItLugO#0hASCElUlOO#9DVN/nsitQClDGR#8r#3#5QndKg sl.AddTail("2bH8FuBkTzWLvURCTz8uNQ4ox3W+NSLowz5EeM6Y2NBv7gPEW0AQR9WaPAer+WJtksW8ZhFO" "5NUSiQFBx3oXHw=="); //replacement key Hiller Systems, Inc. opZn#4dRwkZXz+Irc#2ShYi+gaGepGnica#8#5hRQbIxM#8M sl.AddTail("iJslXpoUZbZwcMZmoJZntbyZ91pgrP6BpOQxEvB1oBuOqhuYt3nXIIFq4TQiOdjLBT8ESArP" "JO7tD3hP30x8kQ=="); //replacement key Ideal Stainless, Inc STMH#0#8#8sItxtoh#2fe#5v#3LE#1/#1BtNDCAAGapMWBH#6xFs sl.AddTail("fejWGOQ01+u0SqNN0c6ZFruqyV77Q2eoipCL6tj5DUH/sITNoWzw2MvD8JrBfcGqFKBuJ3UO" "JjY0Piy/drIr6Q=="); //replacement key Kubota Manufacturing of America zeKTwSXfZWllqttObLWGPaW#0#3FP#7Oj#0lGUr+CCZbef#8 sl.AddTail("oG+3tqIn4IEOZyCGoCD105La4kCGrwGBwEL9ga8KkX8ymCiFRx+v8zveQ9xiCNM+hf06O4G3" "UchFnzfA32cUcg=="); //replacement key New Age Electronics +SfTAnM//eXLGvrWBATmBn#4e#1j#4c+XPHOnB+dhwqw#0Q sl.AddTail("aHppxVFA/wcQ5O/BX+VHtYAXLasc/l3FEc5/z5SDvXRXZgrWvY8RMuYzP8zDOQ3t"); //replacement key Odyssey Networking, Inc. qoX#2DFo#2D+#6ojRDpo+gcMdGRNwEw#1L/PP#5#1fHEb#2#3#9I sl.AddTail("LA3i3tosR4unRM57ozSu7rG9f02Je4Q6CuPPhzk8Q6JrfeTUXoo0aw+l5pVNwtgmPGXWbzjW" "eyM8r+Z5mQZygw=="); //replacement key OneUP Technology n#1f#2ArSvFFVF#7#3asdUNKC#3vZL#5EGoj#4Lk/n#8Mo#2q#9Sk sl.AddTail("pUoFGWnbVVQ0B/H8NPJe1/Gmqs/lVvTqOPf30WOLkscGQlG7eVtSRUFEig4oLbZxyGDLTcfh" "6/9ArNrY/DPVnw=="); //replacement key Cartel f#8kf+QEbzlLpRe#9XvaD#2Dyylb#3CF#0+BTM#8MKNCww#7#0M sl.AddTail("/zDy8639PSoifsjWi9KYZ7GnEZ9VhIzlfIOaWnmTaSRV9HVQ2Gf5YM17UyZuzhZOso99CiAC" "783avc3k3cC4Yw=="); //replacement key Certified Printer Repair, inc. #0T#2DVN#9#8#4O/Nm#3+Oet#2#8#0JBCuo#6x#7mT#6KmI+Vr#9fwnc sl.AddTail("t3xyZAk+EtivQRwN95HQGWzR5wN2bugvhtqfQhsiBj8SgymKUMQH+jLaSPBCuCvBRsEZDauH" "sZQup5zah7uavw=="); //Joyce entered the following August 9th 2004 //replacement key ITnorth.ca Network & Consulting Service LTD. Rhru#0+XR#1hoNLT#3+xPwO#7RwdQXlRdfXhY#5#7QP#5gsYvw sl.AddTail("XUpHHEf5/xYcst/L/ckgJcbUyGJuDANoNWeEf2EuEihWCRUChFWlzSxjHZQ7Y/170/IU4bGO" "bTU4QY3TbCXg/A=="); //replacement of key Interactive E-Solutions LLC F#1TTVNb#6AhfxkMsFqxUy#9v#8QeThuFQ/ORxBoHBIX+AU sl.AddTail("dwT2tBpzRdp6gkojRFhm7qO5qEZE6fun43hxqDn8Y6RihsnNZPswIB+DzcoV5bgZ"); //replacement key Net/Complete, LLC h#8RsjqG/UTniy#7c#0IpX+#2#6rUhGskpYpjY#9DsXaEAspo sl.AddTail("pUnSBoDAUsoVl11A9GGkSVyz4b+KIP3IlaRcBeCr40HTspE1tQDoisObqacDNb2U+IU5mL3X" "FCMaoVfyTQopuw=="); //replacement key Seamless Solutions #0Cws#4l#2yUnhkEdX+lGqJCtnMtStFO#8zaWuvVQO#6v+O#4 sl.AddTail("9VZ8ssOtRa1Rc4tftgwx8SzzkHduyL8rrXzK+dU3ynyPZaP9hddc4IwpQGSxMWbHjQTartet" "zQ4iscUdINGNxw=="); //replacement key ITnorth.ca Network & Consulting Service LTD. V#6s#8#1/eBZFI#5oI#7+C#4CZxI#4Tzk/pxvIoyICY#7Tj#5#3aY sl.AddTail("KEVYVeZum5HDi2BGdKBjJTGZ7otVMDASDjRvVfRntAnupqJ9lsasSeDTr0McLi3EfQXVWHx0" "6xXLxA76DzDXzA=="); //replacement key Security Watch Inc. lgQUFQYzJHHXS#8ye#6U+bhstHqllWBQurIY#3A#0#5fbY/#4 sl.AddTail("dGVIUQH/Wx6NTaHM9/j7u+793iFTuuxBGGB3oHM3szZutpu+XPCH7efhmvJZyaitrFqJ58i2" "FO+5JJItn+zirQ=="); //replacement key Smart Home Wiring Y#1#7AJD#2XryWPm#0kLSBgE+so#4Ivt#0s#9V#4cIG#8#4MUdjPg sl.AddTail("WZuN+ntBt2eIsB3z90xM1ESYjtnibUnNXe757KJMy78KbsoB89uK8PC7LsSxouTgSNRwiVhx" "l9tof+Zp9L1e4w=="); //replacement key Lutheran Social Services of Mid-America +QTBQLA+WkgihxvSx#3DM#5AMULXu#6sJhj#8hll#1pFnYm#8 sl.AddTail("bbnQZ1dd/qk8t/dVDkzTtprpcr4XnmL2yIZADDLsVRsRn2zEJ0ehLq/tRHyG0slGsRc+3z6N" "GwGpIS76yPperA=="); //replacement key VPRO, inc. a#2FK+VzBYv#1RIiuKV#9CBw#8a#5yEIoaFenX#0vaQvNfDq#8 sl.AddTail("JGpAXrON83gaEIbYcOdfBakEglmG26pC15REiqx5KWDkrUqkh6R4m0hLgUurlXpB3L0mET9C" "LxMELsmENN4oqQ=="); //replacment key Northeastern Security fLvWghG#6CEgRZ#3t#3W#7bhes+#4yNGAcRRThdSUTWhb#8Z#8 sl.AddTail("Gw68n78UDEMtvOvf23nUeP8WKYMGsVNeKbXz+lgqU/Hd9QncYcT+kbI3slqyCUICQa1Sg5XT" "v8ipc3ZUypXPKQ=="); //replacement key Halski Systems, Inc. MnY#3#4LuvCOK#2iHnwctR/xpS#8VU+n#5qNjz#8xeT#3dWTbE sl.AddTail("02IjQGIBv3+faD2/9ORxciJw5R/mGUCgMVY3RAjp1NYPK2fBbNiktL5nlDgR3h5mUNK4T6UA" "3y4QxFp9f+aVyA=="); //replacement key Lanier Health Services ErkZ#7S#3ZmKYQTM#5NHYe#7#2#8tFg#1llam#4c#7#3hk+g#5#0SXw sl.AddTail("X9ZvIzVoVf/Qx9yMLE03/ig/19v5frt/ttZFf8vxEoHvm8P6v+kR7wYHA1s79y1YmhMhrPQy" "VEyd2nMe3vL25w=="); //replacement key Decypher Technologies TaI#9wJCmH#4#4m/MRqSY#8rPEkRVKRGPdX#8#4#1UELhVKR#4M sl.AddTail("t6wVtysZRFz+aJ1AEzCxVYJzzinpyZJQFvq5VkaqAAjhRkqVKy+Ur5g+r2eH6QPHY/Qv/L/Z" "hLgMw/MGgsOOdw=="); //replacement key Turner Technical Services, Inc. MDO#2BivlsP#3zKWoHi/kHdSt#1qD#6EK#0XXJMnQLE#3S#7qg sl.AddTail("K9HQpOO/18FWXTzc0KtQsC27hbmw77h8EjpaZYvT+Lcd7SOM9DHl+5vSNihkf8gTptTa8A7Y" "/72UBHzjhFGO8Q=="); //transfer of ownership Cardinal Communications Corp. #0bUJcIDqU#3lnayxCXTCdwm#3Zhc#3Y#7IfUh#8/zeioEbLM sl.AddTail("UxacJ4PoJ+rh8ywYiA2JGsDXAL76GFuB3qJbcPa0Fvi//GcafghyUsSPhlhCyewb07PbgOyK" "07KC7jrJJFI3OQ=="); //replacement key TS TECH Enterprises, Inc O#1ieUhhCNMWJZUpzjiooWmBjZiIDvrzlHyF+RSeZVw#8 sl.AddTail("xFCPydsJkcnWfG8PEzgN0L1LSd/rAkY/V+4E4Ft5MHusa0B5cNc4ik9o/Ix8dhhx"); //replacement key RODIN Computers NYIHF#7DTQqXFgxbEujY#5PvGdEQK#9OiN+NALIeWvbEa#8 sl.AddTail("0vk0vgGx7vpejdh9O4fG0O1JeLzZMnSkHN5pr8POK1Kq7QixRVVgrVAzAkVhchsh"); //replacement key Wired Up Cafe /GtLK#6yflA#9//#3PKUK/goKyWGduRPgb/nBBk#7nIBjS#8 sl.AddTail("T+QnoItTvIcbQfzThqefubh3opyEtUvN1tloGSfKIZu2JU2tv2jHBp6dRZ7dpa8WJvFNdVHL" "FX3vGVWYtjJARw=="); //replacement key cmx computer services hy#0HXbk+#1V+lgV+petVMAN#1Elx#5jRSIySE#2#8KH#5uW#0Y sl.AddTail("w2wuYBkoK5Mp+Ke30QLvN/Qk+wZRQJV+1ZU+/vWFsrYTb9GqCI4BSmgozPiA7IcF/Rfht6vR" "edjmFiRz8mWnCA=="); //replacement key Omnor Technology Solutions #4rzWZHLZLpt#3hJdDY#2Dw#7kPrVEDm#5lwQre#3ONc#8DWIg sl.AddTail("TjmIrX/a0NDDtplwt1XJ5nBj0YqXGGKwyyuvwsvzNhkrAUB7yDzrtBg0QmTykQOyqbNUlN92" "YcWYPa9bvAf2CQ=="); //replacement key Voda Computer Systems NMaaMXRnuHECunBDam#2#7QXYn#5KArLlEUKXcV#1uqh#7TA sl.AddTail("t4nYCwOwUQBmeFJcsJPEnJMyu6ZmiugEYMay1oISm0s2iL2dyBpIaOHmpun32NLU97TsaqKd" "WmJdXrLpskQ9XQ=="); //replacement key Symasys iRUW#8jElfWBwMemwdAcTPXGaDUeg#7S#0/NcNox#0#7oPdQ sl.AddTail("nJq4xbtRkW+bOhei5uZruuC735gHUyHoA7DoQE/6jOac73R7KUJu27kGaqSweTwUVAw4BUK1" "4bgbBeVyy+lW1w=="); //replacement key TS TECH Enterprises, Inc #2aQLjdeyyTZIZXNs#4YsExew+#8FVJIOPIDBtCv#3#8oFB#4 sl.AddTail("u0/I/+2RTPJKsN1UILB9dZl01TPsJAGirzT2dEVS4Mk/vS4rorUX+32MXqto73jWUXEJVqAw" "/avzj4cKc9E5hg=="); //replacement key ITnorth.ca Network & Consulting Service LTD. lpCDp+#7Fl#5xU/baqDLqMaIQ#3uVfzYUN#9NVXMuic#5#5#3A sl.AddTail("H/AHtO7Xdd4Ua9EIM1DAVJzZV/ZEd735Cp1eRNbFqRZrnZCF5aNQR9JpL7cYAY6OcyANMQyw" "SBF4Xf8pudRAQw=="); //replacement key Decypher Technologies BdGIxj#2fGmmQSQbcA#9SgtFK#8#1bg+LGlYK#6#3MnlCSJaY sl.AddTail("4iAn//k7mKljnc5pS0Y2AhO9VJdhKOUJ5mAYQmZroxEIV0M3wpkwDXxfdNcF5A7Cr9H6huDe" "0ZH6gz8mFXeZ6w=="); //replacement key Ansutek Commercial Ltd Btsd+QvbLJdw#4VmhqLz#9lgdY#9TVerEdfZGMMLM#2eELQ sl.AddTail("/drXnuMtBGmxEKltbTV19buOXl61/P3cP+K2uV+c4O4agyKaeb0Oz/Q14ObOEL6q"); //replacement key Interactive E-Solutions LLC Wam#3TfsqhIuJRviE#3H#9#0MjoHPoDqagCjPkgnIVbvgzk sl.AddTail("iMJXjp4Pa+vD2VebhJC32QTcQff5CJwMjSvmZClnusSU57M1hlnkabJl9qTgZ0zL"); //replacement key RADCOMP Computers A#0SmbWnX#9#9Fpdy#3OonjOcpQC+/nqQn#9HWywJvDRafrk sl.AddTail("LOanLUNCDpqp9RXlc271gsCxEb47z2byrJnXbMKnIK7CTCjUqv1kQvwrhwKHfLnuf1/ZThux" "85j0dhiG9c0iEA=="); //replacement key The Computer Hut, LLC AugZy#8YA#9#9Nudi+w#9XgokVONZVTiMZllWrY#2aloNBKs sl.AddTail("FdmSAzwgWYjUE994zxYlTY7yML08SJIoQHOr5iU0fJ9p8ZzMJ6Iyeogn8B3iwJof96b8fOS7" "URVkB0keikXQmA=="); //replacement key Steel Systems & Design YJFoERRwNxkwf#2sbZjTJh#1#1DsDZwce+VmVSBVZgeDFo sl.AddTail("vyxMCPuBcmwViK1lTK1Iv5Trp0ZaUaK7S1DFYMAK44C+yVX5bAJAc2ZmLGY+NQAJ"); //replacement key Catek #0RyQb#9#3S#1QetxCCezY#8YKK#1#3JMjfy#2FWIFLK/Q#4J#9Mc sl.AddTail("+1EcyrH5f6ubd6QV8+hDW3t2DpPtR/ip9pzaW9A0kEuxRie1OBWsY6UfNBhgPLJxxabO8T0z" "A97HaB4s3CG5Rg=="); //replacement key Gator Technologies GcD#3Yzq#6uYytCkJqRUxxfCuijHEtoxNnbvPaZOo#3MU#4 sl.AddTail("/veXxWrHuYOhzyY8GRp/Kl8fZ78A2CJ5tRVkHzL19Xn66abgqyuvtwru3M9yjt9x"); //replacement key cmx computer services fYBiwzVyLGxBAMm+#2y#4Xo#1txo#0ZaGGTgYRt+k#5#7#9ORo sl.AddTail("3ppFp1cwFdc649hVKxRsn22Cz9GHBS50GLM+POIi9T4DR4vyQqXSz/ciJ+MKBwjsgqNuBalO" "9TDARfELv7UaCQ=="); //replacement key Halski Systems, Inc. aiHfM#1#7#7NSkjmWsCCOn#8PlOYY#3XPdn#5ufAUwrziZGOc sl.AddTail("PfFGN1uyVXX0cYZHoOlY5j3Ikl4qO/W1e8a/m0UI9rovbsSC/TgMDjMlc3D2zWFZuCkKzHsp" "BH5BP51I1kcKCA=="); //replacement key Innovative Computer Concepts #4IsWKo#4VYfAWfWIc#0CsM#0W#0KNVqKlPr#9FDrmMm#7iu#9c sl.AddTail("B5+8SjioML+SFMYs2PA6pyHAeZ9pH5I4LlPkwoHJDaJbVWiBxC7OrMZsyYuaV0bhjuVdwztQ" "sZiBxltfv55/+A=="); //replacement key romteck grid UeEQwF#7qmI#3#0kLro#0JbHzexBiLWDVGfEXPv#0f#3#4GZX#8 sl.AddTail("6Am3Uz7ZF1IOnhN/o4XmCgiljKzy3yJZvYQIO9u9Zd1LziwW7iWajedzUyL7Oox8T9rjuHiP" "LKhqNdiyk/y3vw=="); //replacement key Total Technology Integrators LLC vZ/f/dmlt#0fGVLOfjGxI#2L/+eDQTRiYqjbb#9#8g#3HjUE sl.AddTail("knnL6UU/MEZhffYOACZ6qYp0+mmWVEqUicuuJyK2f9ZNjqhkwcS5r2899nYGlAA8l9SN035/" "9oIlP0edxuCG+Q=="); //replacement key West Coast Network Servics cC+uyzhj#2#9bxDYLDS#7NHQqfYm+x#2yu#1mppk#5ZMH#3EWA - note the spelling of Servics for this key is supposed to be like that for that key sl.AddTail("dXSVFFjf715XpJXCBnIeJ22hvFT1WA1f9JxMc4/iOmB6y5y21gfplHabf7iL7rvWoxePbql7" "IXTLuvnxmxPRrg=="); //replacement key Golden State Networks, LLC KY#4Ky#8XSOiGPFhPIf#9RzoVhSrNo+rbq/Ho#7#4zIGqUpk sl.AddTail("gqTH5qJidxNthuXoYGk366ZjEn6KiUUGiqQAJE3sfJsFt4CDQ5Nx/HJA31NKAUjnPtS21UGu" "/fAmbUnwnQw+cQ=="); //replacement key Entry Guard Systems V#0S#8liJlE#0PFJ/flycVYW#7sdqdSrlpDvlOLFqtz#3eEc sl.AddTail("KnDC6mJ76PVAaZ4o5YhjmRIzoipeCCSpm5cjNGy5INp2cFE+ydnZzOvyK9I5VkTJ4gE7PXoT" "xndU7ERvBJ0x1g=="); //replacement key The GroundsKeeper, Inc. y#7dqENDcemILx#0m#0PgYTaCeGD#1#0qN#5lZE#6+IReSx#5WM sl.AddTail("cew3tEi1gZhie/FfAuynzzQYa9laCAQp4ALcu6icaXHnXxLQ1uS9lo6TxF45WHwBDGeON0/0" "17/eWr1eYmWe1A=="); //replacement key Blessey Marine Company DQH#2OZntNhH#1CrXPzFcZgbtfwYeWS#9lxgL/#4#4QeVc#5s sl.AddTail("Z5mRMZ8nlb2G04t+0i6cpmoHJmOH1dzZa5gNVNWlszUFKb/0zf8Tt1p66YV5nnKpmfXov4UT" "/G2E1a+0tct5xw=="); //replacement key Decypher Technologies t#5C#8iqOIuV#9#1gtWBHMBGJP#6PzBKuNQNjfDjdsfi#0zgw sl.AddTail("TdDXHeDTX0SSyg93NI2M21Y0d863WGdjyt33OiKYeLkSdQII5lkMWkM7Zr9BxVwbX5CY10J5" "5VugzcggKNv6UA=="); //replacement key Mori Seiki Mid-American Sales, Inc. XlSH#3tnYpaDzQe/fnCqwPtjv#9fJu#6k#9B#3WGcxbc#2c#6o sl.AddTail("HJ0aVSgtpEPp/HX8LJOlXnDdQU1ywSBT5umwbhRhUclWlJZEzzDg9nB+Bw0n7IemB7dapQT9" "Nv0ZUzu+nesdjg=="); //replacement key Footsteps Computer Services, LLC dBfeLJ/+d#2P#1zEe#0Yed#7tnY#6Lmvat/f+YZdmXwurXxI sl.AddTail("x2118RnpAoh3iwTQo5Q86EBcHUqjNOwSjvGLipwt9hBOSqR2F0zOQs52ICFucHM1GX5kEnit" "Vi4hKaCcAKEGqQ=="); //replacement key Computer Fellows Inc zG#7GAFrJuv#8cRedkzIVH#4j#1#0xWJfjEi#1BPP#6YSaOF#0E sl.AddTail("zYa089tAMoZWI0mscVCoarLg4VRan23Vi+DtSIVVHF22UKm+uw+RJszKovYfpaK5g+3m/JLe" "1WfWo7XQggPk9w=="); //replacement key iTek Connect, Inc. #0zzSBzOWJxIggKh#3fXC#2eiqL/xbRHt#9FpGXt#2#3/CDYM sl.AddTail("oLocvrmD1hRki5517KxIj1H3n/tABFtsFCYULKGLuRD6TCKUHvvCZhA9j690JUHnL8ooRVjF" "Y1jqdVdIwsamOw=="); //wrong order Eldorado Chemical #4#0f#6#5#2Jraj#3K#9F#2#2bftZxvtzNLkKs#5/oDUrGHMMrPhs sl.AddTail("w3+yLKZSc/3k3C709YT1fMgTjNeWY2ES88LjM1aPyjzHYD1Mo+3wBTGoVqGgfF6QF/SKm97I" "IDln5QGtGdoZ7Q=="); //replacement key Filterworks USA FUcGal#3mrdaMHwpAScoYTdRMUHJkibwNIl#2XOkWfcNg sl.AddTail("EBJ7wG+79Z6sRIoj+liCHuU+uT2Qdy2ITv1nXAAcsLDyc49Z9emqeflqLVH2nE8Q"); //replacement key Enable Technology NPHX#7cosbFEMmOXEycvRw+G#8vf#7cMp/#9oGVnU#7#7VK#5s sl.AddTail("5P5euheqFscHKxCojhxnIMwYO8jY10rv/+x65eZEttqwrxmHSn+bT+7twj5+tCNvrc9RbmXS" "weVqE6a9j8RqeA=="); //replacement key Networking Technologies VFQgtSMhPDNTc/ybyQxWCsFez#2bXgrZpGtnFztTBNMY sl.AddTail("5BQESiuKoPg5RmWMhuZncyYRWIF7Y05H2+gLJY48OVlbzzhd7s/b79LECfhbfNWq"); //Joyce entered the above August 9th 2004 //replacement key Interactive E-Solutions LLC #9bPUClw#3#2xVw#9#8ev+x#6c#0vQ#7hRWuDEgZ#6kT#0#1F#9#3CDc sl.AddTail("k3JAr2ceI9N7lvrkRtXk6pXo+vUPRhNDP4gC4bQ3LYPt5+1buU2pRgPnxsoJ/YEsj/3IZ+CU" "ReBteFyD1meVpQ=="); //replacement key INFOSYSTEMS On Demand Activation key: #4OfqMVGXsBbGAXy#0+F#3#0#7d#9s#4xiqjW#2w#7sCQ+gjxB#7s sl.AddTail("0G/Lsj1eVU4C1tqCTqCI/PzYk+RcGKie0qJaaXQbix/WaG7lHigD+IXT26cKBRJlDuOlCZT6" "19a0M9ZCA/0RZQ=="); //replacement key Earls Saw Shop Activation key: CrqH#2ka#8MbyBq#0UQ#0GXbDXJvrgnqjMwl#8FuaExEaeC#0 sl.AddTail("q1T3EH2hluBoKHEKpNCwRBoKkTk9S8ABQcqYf73s9/Z55idAxdOhcTx8z1r+n7Ap+C02wTT7" "zxXfI3qmG3zMfg=="); //replacement key Mason Technologies Inc. TJODRHX+OSaamis+#0CTUKJuo#2zvUELJ#9OWk#9MWyWe#0U sl.AddTail("pXMI+Zr+exSO58zuYKNy+OmSXtJ1z+951dJOuOQ0/0ds8WX/sFUPSjOgTzzNBabRbsoAcBR1" "D9oLQ7vMD6dJmA=="); //replacement key HardSoft Systems Ltd yQGzYwIOMTg#4#8MYdc#2Al/R#3RGoSwVs#5kUDpQszYfn#1M sl.AddTail("tvpslE5L9zzNmVYA2W8MeNuWVCoKiP2kU7WE2zdZARd5rsR9r/pJPC5GvdnW2E3kPnbylqst" "78UXCRR6T3HV/g=="); //replacement key NetSolutions fSFARrfYc#4e#6awrjPA#1/Q#7n#5uAGykXeC#9biSzlSqdhA sl.AddTail("nBiNiUF4jvIpVHx9M7v3R/ehpkQRCENYycdM0nlNY/3+/ApVbWjrA8BHVI7tw1DiEvEZn7hZ" "YNuBYt09V4WGoA=="); //replacement key Voda Computer Systems e+TYLPebMD#0lMNexUGlvzBoDTgmCH#5ncgX/GZcAKcZI sl.AddTail("SZZclhzUCadCviRXDbKHiVHgjs4UHCD0Lmgdgk8wCEgpt2ZXo8W9FqiTatsMDQkW"); //replacement key Computer Maintenance Alternatives #6aPbmBA#7xCqG/uWq#8vhkma#7OuQy#3AgArzZc+Czw/ZN#0 sl.AddTail("3J5kkbHRmGLJlHPGXvFnIDLuSVlvaKC6+uh6eb6cHfw7L87Rj3ZXNMEIClK1uRV4y5J+wmH0" "VoA3P2tkZo+TwA=="); //replacement key NII, Inc. #2nV#7zII#8#1//#7KVO+#9mWwF#1MdjGSHvGcA+k#0mkiHW#5jo sl.AddTail("fpIaFGHjAvlHKZadoOFXrJPUuiEYwxYeCWEE4qO4B15mrAB7DgQMvhQoMxjBaRHRXuqOG8Ju" "A4gUgh1Dql6wbw=="); //replacement key Johnson Communications, Inc. FjmCvkOth/YMqAgDOR#2CUOWn+IQOmAXXo#4#6zHXUOZN#8 sl.AddTail("9DbKgx49k/Rfqeud/aL+MXkBhDSVlDT1aWDn1Ed5r/pibzL6D6TxPWSiYxNVTlxr"); //replacement key Tech360 DN#1pO#2f#8X/lxsGCkkoq#1eyTA#5r#0oYrlh#2#4hM#9z#0Ng#5Y sl.AddTail("8LJi5e8LFIg18O9ybC9oyVz4n7+IX3owHskUjiGx67etafBPl9qJhce5Lmomv9h2rQTohjV/" "DvmC5daY9T3+hQ=="); //name change ISYS Canada Inc. - Calgary eoLNFxuJZrTvrplXU#3Ez#5yoqIf#1hVSorH+#5KE#3dU+dY sl.AddTail("UMID4zY3J+dWUVUOPmeGhpo5ZMB4L0nSXJ081rvfaWQpQir7PsZ741naVvj8OPmwsbu+U46I" "fUgpQuzyRFc05g=="); //replacement key Komsaff Ltd uZ#8GzLCN#7#8#9G#1+dK#7PgDbPn#0a+IHk+e#0kxuHaqRVMcY sl.AddTail("WcMbn4Y252+i94MP+dbBwVf3T1DXKgMVD5psnymiJ0w/s+ErocoMD4lL998TlAQj3dbxpAgO" "IyLW9azIuYBIrQ=="); //replacment key Motorola Australia Pty Ltd oRtjqsxNk#2OqO#0#0u#3roRBtRiOuQoUA#9AA#3Q#5I#0jfiZs sl.AddTail("oLLfRv9vTRNwEUY6EGgfJw8OpOEwW4mzbDPtUE1Z6Hmf2zR5pqApqFljzR9AY3cprvHeV5oC" "syCePb58Z/ffGQ=="); //replacment key Motorola Australia Pty Ltd #8wyshdN#7#8#3bU#3FZDDOWUD#1G#2#8#0mSKVMmBEewDTkZexE sl.AddTail("cUe0S+XmgObQJu+jQZ2PpCWuo5YYGWh0R+BlbB1hp3Jd57yoq6mK2qPuQJ7pCoiepsU9ADHM" "KBQNw/LFJTc4/Q=="); //replacement key Motorola Australia Pty Ltd D#1ed#4SQ#8MpIlWI/Q/OUmvasT#4F/s#1awkq#9#1+olmTiNE sl.AddTail("ACMeL6hLH9etMm0Mo26l1xHpYTSp3R2J5dd98XXVuafMMrFL2mMCEFZd410bwVTR4N6qcRy0" "XzSCzncW7obEBQ=="); //replacement key Motorola Australia Pty Ltd NoAcKmActl+peSmt#4BGqF#1#2xaoRATO#6lobi#2JJOgS#6A sl.AddTail("kpToOUSOzMmT9LJUiiCmbm0rnrSU8/IVvYxk94iY8lJYsVTFLwUtpUyitxvapBEJ86YvAdZ8" "84QjYTunrMp29w=="); //replacement key Motorola Australia ZiwBf#5wy#2m+D#1YPZ#1HEYEUZGLy#9C+fgVGFm#0J#3C#6Zto sl.AddTail("xtzdvJh/EiWV9+VPqajCTxSqiM/gauYhfP1lVvotVT9PNjs4uZ0w6W7aHRSgzwCV/F6s41Eo" "//7vuGcPUoMzog=="); //replacement key Motorola Australia rDHba#9+OLqx#5XzkvQi#9fS#1WNCEo#0+uFcnNmjMjka#0b#0 sl.AddTail("HSS0AD6OSvowjdqaGlOGomtwuuJfOS3vSf626NOE8EDpp3piH4xQegbW6Gd+PtPQnN+n0qm2" "zkzfxSWzw6FpjQ=="); //wrong name Computer Troubleshooters - West Ryde sFR#7#6+#9Fdjtmy#0TOv#7Sd#1wQzXqjCGDpBAW+XC+KiJiI sl.AddTail("Ez0jvs0WtrfmRGU3Tc/cleYskxDUZyvcic/awiv6RoRT8gwheplQYcGHWpMPTjw5giay88QW" "20KbuIyhx6Nbmg=="); //replacement key John D. Marcella Appliances #7EAbnISuj+M#1ggGvLRbsB#1luwKhSXtRArp#8MnkWC#3gs sl.AddTail("8zacBl5Q6UY8dVfzr2HRlwv1u8uJNiSUYfUuaIFOxYgM1SrzPlNuPBxurUV5phutlTZqy+bk" "WQOc2R97wR48NA=="); //replacement key WaveOne Technologies Yo#6mfjnJho#0#2w#2T+NqoVrtrW#5HnQXoDTocpQ#7FYX#1#0#8 sl.AddTail("TFN+wUk3xizg1G4nGE6oB4ijRXd+un1OraozKhyaVoO3cNu/AB1eFO2+f0OILMaqU28i3env" "3nyFxF4ALSJTUQ=="); //replacment key ITnorth.ca Network & Consulting Service LTD. cHQCxdlUJf#1WA#6CUXWt#2AEjLA#0mbRuBXtH#1yqTNJMdg sl.AddTail("k0pAUailJ2QoDUFkK4Z0B7MFvgmjI9MnOLrQS7AmxTMI0QQwiDz8TIaOOSfAoKlGr/NCap7I" "SO1Rdyd6r311ew=="); //replacement key Motorola Australia eMW#7/T#3ZU#9gFFso#3IWAc#4s#3DdWMCITHxtaDDGv+d#6Kk sl.AddTail("yGd2M/TVXg59F149h7EugyE6wvsDyMIfDAijubpbElXh8QWhwGXRr7asAzXHSUGeYwVYLVBD" "Gsp5NucDvazPeQ=="); //replacement key Computer Troubleshooters - Ryde uFTagUIldfk+yz#0#1o//umdDQGkYcWD#7vpGDsJWg#6pfA sl.AddTail("gp97zdDIc96XV5+YatQcVbnmQn0Bmr9F4ePHMNFIHw5TtT28q6Cj5vNoM3OBLhbF"); //replacement key Outback Electronic Services Ns#4vEIUNpVELNWv#4TpEOEY#2OfphnTRE#0KEnPuhRR#6ag sl.AddTail("yVegbuVT5Xqd8J0dsUrzTofDjPL1z0jgZ+FYDSvsVXuq6U+SWuHzY4TPY408+uoGkrrR57vL" "ht2XM1CYy4ZZMw=="); //replacement key ITnorth.ca Network & Consulting Service LTD. LXbiCtrPTNQY/ugajzSYmVYIruedsFjZkdPCGUnk#5tY sl.AddTail("oX8arqCe1C97UigLz5wkjrpJynYDIFEk8dKeWtAcLgPmQJTpRzu8mLGmDxYtYCyN"); //replacement key Sage Technical Services eVt+#6fod#7M#7#3z#5ozoImHrVAZjFNjWGKugeJYFvD#0FvY sl.AddTail("93AaCmwZTNQXmsqP9oLv9IXEQO3R+s6iNk02ejHZbOBSqR1+TDaz+k1NnaV8A95bY+6Iafi1" "SnPJqV9BGKbG5g=="); //replacement key ThinkTankIT LLC /A#7WbecEjpGiiweNSuMlgjabW#4A#3Lv#2/McOkIrPbL#3I sl.AddTail("kqS0uDuK8hcyrSQYBklzDw7vwlJQbasF6u6mJa4iXu82FD0C1ea483dsnTjR/hR40Su96rIm" "9Om/r0TaAep2HQ=="); //replacememt key Norlan Integrated Systems yl#5IEBqsYUyFVrI#4OZQxp#6iKnUoUlTb#1T//#9VnZeNY#4 sl.AddTail("GtYcN8Lao6qQVV3YVMf8ImuroEqwhv4qWRMCJ7LXm2bNCVzOkWcQyYfP+6n2bxUdgHj+8Yz+" "VFcpPC9hb3UNnw=="); //replacement key MIDWEST BIOMEDICAL SERVICES hPK#6#8HPoSWbrpCvtC/AtiackgUlLr#7ruyWN#4#8+elBX#8 sl.AddTail("RKgc6vPsgqqEBk5rzE7/Mk3y52uaEi+omVkzLQkrPouRTBt4ltKc3TiW8AIs4JCsye8kQFt2" "BkwASEXzKe5Bag=="); //replacement key Motorola Australia V/glr#6AoV#8Oxnv#6Xacz#0p#6x/ITzMbxQlKIHClIHj/Bg sl.AddTail("QLK/BNAsl5s+WruHiQzSIWzt2mHHK2SU0ZsN4XjMFaqamT7noiMH/mxZrJcvYnMTUxPkKQdM" "rrzSqZES/xqzOg=="); //replacement key CNK Computer Solutions, Inc. TCkqrbKQdBnXmYECBkIeXpSDv#5g#7#8KJjdxXDm#1zB#9YM sl.AddTail("J8NJS+aaoZuanEmH/yjWbZOkXACKy/nNsoL3SgLbUix0rx91fWpM1tgi57v9ievZiTbMCFFh" "rJC88cnCWgPKVw=="); //replacement key Lexsys qU#3mxJI+G#6TVkKEqjtyLKci/sQr#1#9/bOcWyQ+JZPc+Y sl.AddTail("QTGksFcBCbnrEpXM3ArlftYaRE0lrE+ZXhAzFtBH27RunJb2oNHgQ79N/scH1SFw"); //replacement key midwest networking BxcFIlytY#8oi#9gJ#3RNvZ+#3HyUyqs#8jKo#3cMf#1B#2HleA sl.AddTail("22iAhv1IQAdfLN3iCckrznU+Ju6Hx8OsXbo5t+1khipIRaI1lbSuq5i99Hf7JZ375tFkVa4N" "l86dPKaDOMYNNQ=="); //replacement key Halski Systems, Inc. #1PY#2Bvw#9AsFYr#3zF#4Id+#6cmlMaomEZF#2#2v#4YysPwU#0o sl.AddTail("5XB4vmUWe+oCSCEgz4B7dsZveT8ExtxSTLMY6hIf8UGoIVXrJ1AFNw0sVee++9uRg450iglW" "RCKC+56oPYJAmQ=="); //replacement key allendale machinery systems +fJQ#4sX#9TP#3nsg/KmDtSy#7QGRlLcAAOqtL#2nh#2kFWHs sl.AddTail("SZYkwWJnlDuEcXqkmhl+eeOyEeV/LSgayjMpVFCKN/r1vSnR+kr4rU/7ncmbV+656cnShBDS" "xVsioVM3ErQDog=="); //replacement key TS TECH Enterprises, Inc SVLkziQt#6ursRbucn#7k#5YcOVUgpdlwEWgqTMynBkYjw sl.AddTail("2tBucL6H6oPRquyVk8FxSq30Xdgtsf1MquDrzrQBk7TApS8rYmsdux6icGgv2ndG"); //replacement key PC Universe #2ZWAbGPg#2KBZeR#5pBxdVO#2E#0lZdGDvEQ#1#3mfyG#3XQHE sl.AddTail("jHdih4P7irQFtCblMh92EF7/rjoqM+LJMb2pEr4jxGk4R/aejuTSyGYi+LFQ7uF8ng+W5wYi" "XnguPoCuVp7g5w=="); //replacement key Southern Tier Graphics wdMDriPatgu+VACN#6#4WdXvJ/OqF#8tBSfqcuFsmQTrN#4 sl.AddTail("7Toh2DjgbYDhHJ73vqrVl3ZBcfuqntBlRhv2uggBn/a/GcFrseCV4gojK29dkojG"); //replacement key East End Computers LLC RZPfUkj#4I#7lC#9nseLWW/CO#0#7CNo#4Z/mrloc#6OyDRxik sl.AddTail("K/SWtYK4XhaJkp1fEjmvQiI7Ry37DximAK3IkJn1Cp3w+s+eA096/iThxQ5IH10K2fp485t7" "dXSP6iWX4ponIw=="); //replacement key E.B. NetworX Inc q#9htW#7#2D#5bz#6dAZI#7PH#5tqJjxmzc#6/YQBYVpN#7cN#6GY sl.AddTail("tsiVwZmJLEzj2rL4qZ8mFHt/89ZgXqMcAb7j/sKtfwUIn929v6t4tNlNVB4CfP2zDpF4ZaOo" "d/yWhLZbr+8l6w=="); //replacement key N.W. Air Solutions, Inc. t#3h#8fGtPaKmEKrAd/IK#6Sm#8#9F#4ej#6#0Z/bgBqaRhMsWc sl.AddTail("7pdebGAK9bfrnnZ0/lYGNefMyiCKk86vh8liwFwzEgjFKxs8A7l2OlWVVOwPb8qPLI0pjSDA" "QLaSGgNmel7LHg=="); //replacement key Ansutek Commercial Ltd sD#7QssY#1h#5bMJFl#0cBYp#8uMP#7RPf#6#0I#2cZf#7#2tT#2#7SY sl.AddTail("7efizFXjDsciJB0aq9xSZgLh5rxDSMs/34lU4L+TBC9RWm9G27PBS6C6XZ3aCSvpYAY0TP+/" "1u/etzfiKeJIQQ=="); //replacement key Ohmart/VEGA Corp. #4UfNLljOvBrp#7BzrPiH#1vGWKfdEFIOFhR#9eQNznQOZU sl.AddTail("qqZwReBFv5pSHbZTp3Wile+SygaAwAbXmzDgSt1FURVMrCuptz+Ma81uVNz0hvYb"); //transfer of ownership Kubota Manufacturing of America VK#1P#3usuOjgPlfZKzTBR#6OeTdwwMAIXClYktRoEjW#7Y sl.AddTail("qNxIK1pR7yYK95MXn5pU4QET3cpwt1UDcp915AxcYuDRf5AafTBuTYrLqcsQZQUo"); //replacement key (add kubota's keys to) Halski Systems, Inc. A#1aR#1yFZhMu#3pfeJMr#9DKJ#3s+rYRAP#5ezjw#1D#3VVV#1w sl.AddTail("KzKbOTDDzyPnHysccUJ+X1Ol2MkambX5M9+5QL4OmPSmUBRAC7IGc7Pj1wuFDZWlBdCGzqef" "j7CHMthuVwULWg=="); //replacement key Braintek, LLC lKuu#7h//qSHEHi#6h#6ULddYokvgHt#2#0LwblQOtOaZp#0g sl.AddTail("5w8eRzbpx0Sl3VaZy3xelXxjGX70lxdM2d0OZLtz+cxkZ0LoCIdW0irv04DiAqAkmAJ4QMPE" "XxHPvmk1PyMGQg=="); //replacement key US Biometrics xGKLp#3X#2JWdHsh#3DCEHpwrcoEjMlHq/chn#9YvVlWTy#4 sl.AddTail("Sy0GNltCT9YMLFV0fK+X7RGHH+9b1353EqbwUQhwrxLGNMFfwp8q0s80HShWiP8JIwb7Itkq" "WU/rt9dE1BdQXw=="); //replacement key Visy Technology Systems gbEUjIJ#3JX#3YKRF#2#6w#9#3BMYBvaIDv#5yrT#8cKf#2cLSMY sl.AddTail("pny9XeRJoSlNknyetGrPCRajiW7GhjHH35ILX6Yn1YdLZZJszo2OfCRou1sqfQWcqIVQEAHF" "VNgN5wLPWoijOw=="); //replacement key Odyssey Networking, Inc. d#9dQX#8lSFsW#0#9gch+bC#0lyl#5wU#3+Ad#1nHn#7wH#5wXsfU sl.AddTail("Oth5Y30AFzbwdqVHCaj1O8o7ejtlclqXxVGVIljQy+lr9LayLK9C87MNGExVlnFPHcAPT/50" "NRjirLGB3oytVw=="); //replacement key ESM, Inc. aMC#0wfTIVuVam#7nKHyZgEAv#9Dxg#2FWwtLLCrmIx#5t#5s sl.AddTail("DK/7NCnLg5uTmnTEyHNLLwTkpXMc6rWs7X7VriMVqHhwATdHoR7i7IU/8+GMvSl5UYAeT3DG" "CgFm18TZ2KzQHQ=="); //replacement key C S Tech xhWBBSOGtOpsi#1OY/JJCLe#0rcJ#4jaJ/ghsBzA#6Mg#4#0w sl.AddTail("cqj9pBh4o/pTXBgbZDdaUm+nlOe1FAskZ5mYibf/re3aDEPedwwikWtWuFg8eDAyo7UjZPRN" "hwzjRxoIG02Ihw=="); //Joyce entered above Dec 16 2004 //keycode being used by non-licensed users info@securitygate.com - Universal Heat and Air TkWQWgYLyWsnMaJgJXnivCW#3Go#6LmXb/#4oqASBw#9iRg sl.AddTail("lPLdPBzwLjjLrUlghfpYa4MCxq9+cY/NHOMyH1fuBnEsEzf95EPd4Xg9OvdlKJlU"); //replacement key C S Tech QQ+Y#2#3E#3f/BhFxYtR#6aNmQ+#0n#8xW+Qr#8PWzhUMVO#3Hw sl.AddTail("IlPbYKaGMSdnYeOP2V7KM7KvxeSbP94YPfivbqdpXUGdJAITMyJa+vPjYJqR0oMRzQzvqcUL" "BvBU4tQTIbvjGQ=="); //replacement key Combined Communications Inc. RIsn#2oDr#5z#4XPr#6ulBVh#3d#7WpGWJtT#7#7mMUZiAyRCAQ sl.AddTail("bzey5Zyv1c7/YIuEFd6F7e6goZvW716Ky9JWlLA5D04M/BSDtKGGUablcQ4o/AJ0yDatsOWy" "cRZhKO93fsinZg=="); //replacement key Chiron American Inc ZlCnTuf+axnJCItrC#8sUmGrpHo#8dZzDD#3NUZh#1Erk#0g sl.AddTail("+dcat9R4A7ziUPvi05QEzjKTlZbtr/RLaWPNttBfcNKeWoG+Y70ejgANG33PXGUxbmFXvMV3" "b2rQRjeqpyP2JQ=="); //replacement key AGJ Systems & Networks Inc. bHlYgQxhyUWGVJUTXx/#9iQptGEzvhRBXxUjvGw#6v#7#1M sl.AddTail("wPSVLzf1X2Idove64i9dVY5ifWN8G5mgHbWDacqib1FSk1a2RO9Z97y+aCAybwMg"); //replacement key Cirritech Corporation gDdNvpydeqdvk#8SvIQmYf+#8#8kCsfvKHHUogJLoP#2#1#3o sl.AddTail("h3+aeDETfStioiWHAXjBqaJrsW0boFBoCZEfgWRc/yrCFV9JzeFmWFqeh+KMF+2hPnu6lT8X" "6IZybtftlDqkOQ=="); //replacememnt key Laser Systems iKfp#1/#0qpjh#5ToLXUSnmvsSqUkiOt#6#3CyFRBsMkw#8mk sl.AddTail("Bqs+m9XhRf47OXrfP03BBWy7qroP+R05ptICn6Hg8FTVdjIoyqOkCAwLFPIEi7+qojOx3sIS" "i1HFlHoVWQWjyA=="); //replacement key Nordson Canada WPicleEd#0Yh#1CTW#4VwNatnoJyzsH#7JTOCqosoc#0/HIw sl.AddTail("on7oDh8kAgo2mq7Dl8NnBbSjL9JUykhMTUHxX0NDmBF0rhWfhg0g78YTffhNTNGEnu120Plp" "plOUhCq0TDMWjw=="); //illegal use of refunded ARAS - Sheridan Property Management #1e+QAOEiH#8s#1JHJieox#3rWEgdrNonzddx#8EIHy#6#0PDo sl.AddTail("QJj7wyjIbOrOXZJ3t3U0c6TLu+yVE23MAFApyF+A1RN/d+lGw+f2YFbnY9bP9/DPbCItD7h/" "vLeegB3QGkThCg=="); //replacement key [Golden State Networks, LLC] Activation key: yIsfkBm#9cfYY+IVYhKe#8R/#9lr#7izfjz+jecDm#7CPFiU sl.AddTail("/lPZ6GnQFn57ehUpwj+/IeMNTYLvtqr304C0LFGebPftQF1n5U07OHVd9ZCU3vy74HY1NfKW" "VdypH5zQyV4G9Q=="); //replacement key [Southern Tier Graphics] Activation key: x+ybolDWEylIvVxp/wFRulHy#7EkWIfdbCOJ#6agNTiyw sl.AddTail("a1Rtwy7P/LZrTABpVWj9KqQFRY1HsuWu91f9dgMJJwMoYizqe89CZNzIk3zzpJFU"); //replacement key Diversified Communications Inc., DBA DI-COMM] Activation key: #1#1H#6jIzn#8#3mQ#5W#2HYlQ+NDB#9#3mPyXfyv#4YwfPgo#2zMg sl.AddTail("sCM5hltcH8WRiBI6XfZTZSa3GLUMGGiZP/yGJrR/LpKrj98raAyMkReTSjNXBMvb9ObNGwa3" "+Jdl//4VC4fM+Q=="); //replacement key State of Nevada Legislative Counsel Bureau Activation key: #9k#5b#0xD#3Rn#1#2xd#0JMO#0#3x#8wRkGXRxt#6#2#4#5RcwLjp#7#9A sl.AddTail("hSw7wHj0lZrunEbhQplIMwrkR7oVLEAv6X+8hr+znM6wSWx2gz8zgcbd4ssrpXpWH8Y+MhCZ" "nL3w7zmf/m/luA=="); //replacement key [AGJ Systems & Networks Inc.] Activation key: idvHalhbmqDI#2jYHq#6woW#8OLvnwAws#5wLvEyMaZdtt#4 sl.AddTail("vRW9EQz3jyTaCvQx0kSzTGtzldlmwmXmc6PHzglTmH5WIK67nMfGdjtOAVjbVbZvx3DkZYfJ" "mW6xrLIygfP+6g=="); //replacement key Crossland Equipment of Houston EXpNDUf/tX+Rbi#2ga#3ENO#5NyALcx#6S+EWGaxAB#7#4#7IY sl.AddTail("24IiBgY9EhyGa7XPB0Eux9EQyehrrMa7ResQgato+6+cnrAc2WWFttgBukhV7LvlaN8l+Kt3" "eQlkC/fLGb5Qgw=="); //replacement key Access Washington HoFSdHJOgYrh#0v#4w#9P#5XQKGT#6uOcPzcBr#5#1RWxHfRTY sl.AddTail("zAFG5ItzGyO5nTNqzoChlAeC6+7NZnYzd07b7JDWQbOqUI+mpmw84lDzF8v6PpM3llHQPFbR" "nPCfRVKxChN46Q=="); //replacement key [Pace Technical Services] /zD#8#3L/v#5b#0pQIzdp#4WAKxcaT#5AhrrBuM#8cjPj#5y#9AQ sl.AddTail("9mJg+uK+ZXCoF/IPkg0DpGo0fe0QTsIfcEzfNcfTTwJ/t+f3Twebg6TOVYLxr0WccRrtN4ke" "vge1N9s0Z9ws6A=="); //replacement key [Sage Technical Services] mcvr#0+YFr#1#3ALX#2afnRu#8XTacB#8Rxkh#2LtsqdKd#5Apk sl.AddTail("SzY7fzixJVx4JuA5zc7uBYuuD/AhfLzGhhyCz4lb7D8503ggeJXFgWG+Rx8k88Qi+Lr/x2Dm" "GYveaqKR2ESk6g=="); //replacement key ITnorth.ca Network & Consulting Service LTD. os#9a#4okZQJRWLMzOus#3#1kKFCE/K#2BVm#3VZfLIbjvRmU sl.AddTail("pC1c1dZM6tTpY3DDMmw5D0nJYxGXBXhWm8ha8phfkfXwrLVeFGWyt+FtXfZCaNkrnEG+5ffc" "iQ2VGz27JL2liA=="); //replacement key Alphacomm Sales & Service lnjYUlN#6kiDZ+NMOFw#8zS#7#0LZ#8#3U#0McLssDwK#4p#8hZw sl.AddTail("kqXmGflNXajH6bP3FsFSW0+b24Agog0J8pQh1F71REFkq+kBMK2WkA2CqBVp6aqQtlyDBmnG" "jiFo5mNONJDkVg=="); //replacement key [TS TECH Enterprises, Inc] /nrHSsGyZkjdgijnFtPKzPbMasmuYls#5CFZ#1d#7Ir#1#7M sl.AddTail("RlZ9Z70PL1c9C2ctd+PfeFhYhJqWjowg8Wtwnv4odUnaV/IeQUoNJjJXVGQ2HZEoLGS7b3tE" "sEMacQYYabIiaw=="); //replacement key [Sage Technical Services] hCMW#4HHeeD#7gKRraIfjGm#8BbmXJT#2GMXwoSj+vPNmGw sl.AddTail("9/DfikoAyvZuCYvtzTnpeGCI8f/454fafdCDkr+N5C67uXFx3tv/XYHaqlvkWNAh"); //Joyce entered the above March 18 2005 /* // sl.AddTail(); */ /* // sl.AddTail(); */ for(int x=0;xEx(k.InLineDecrypt("gR3jWcuUWuSOJYVmhT88M/7v+kys87i4FDB/fSlJv1DMuiccVg6QQPOPbIxgWVpqIU2e1eUD" "4DS2HUVF+xOC/w==")); //display warning AfxMessageBox(k.InLineDecrypt( "nQtTQpiy/QvLCShodMi0c75R6oUJQyOQPRuoWekODUK9mEw/MI9qTGQQ1FZMSJERkhSAewtN" "kpusV75GCY8epEhqw00WHE6BS4Vt5SWNvvEf0fND7s15BwS3kiuNe4o3VYmwvyGiQyUd2agE" "WNOJrY8k1iU1l847vlK7lsUHm0P/3KuLmAWoEe5ET1QLWFyOF/S/AxaV9tfon019/TCvJIcr" "5eAwXrZNQminwG23bLJJZri9F0LoTRbly7HRHX6F4OOP0kiC3n2/D9REoFGFCG835x2A9O0k" "JKe5aiJWiPEUch9JTyZ+EXAsfzOAGT4Evxw+HOpGob4bMTxGuO0sA8q14nao+Uz4rZ3Fv05p" "m/zjNREEyV89xdo3xv26OrmksZEqxNA7HD09I2I3GKuW4Emette8/H4J7TrhWPpa438T8ski" "x1VZM8xkFUx3joqdBs04Phhghk+5ciOh0hN90OpzVbx4BCJ32fGJ/X/w++MNx8m59QAh+PVh" "xpqVyZya7rVmRUsTzWlDX62amQRMj0u5l4/7z2cKvpFqZf4DV/q0qaWh7FnR4kE59wri03J7" "TvdU0KbO+2kPIKizPFoBcSAEnmVywAaYO5UdT1FxfPhoccpJ2ggIw+dJGSOXjtVNorvLa/VT" "R2KpocPuhnZrwcJW5TRBo4e4UUDH7tBRElObGuarmaf7S/H3Kn6ICRpf" )); //exit program ::PostQuitMessage(0); } } } //WELCOME TO SC void CDBUtils::WelcomeToSC() { AfxMessageBox("Welcome to AyaNova!\r\n" "A complete owners manual is available on our web site\r\n" "Select the Help -> Manual menu items to get the manual.\r\n" "Or visit www.ayanova.com\r\n\r\n" "You can also access context sensitive help for any screen\r\n" "by pressing the F1 key from that screen.\r\n\r\n" "In addition to the online help and manual, \r\n" "we provide full no-charge technical \r\n" "support to trial version users such as yourself.\r\n\r\n" "We encourage you to take advantage of this and email us\r\n" "at any time if you should have any questions at all about this program\r\n" "Send your questions to support@ayanova.com\r\n" "Our response will be swift and thorough.\r\n\r\n"); EvaluationDatesAdvance(); } //used to move all dates in evaluation data //ahead relative to the reference date and current date void CDBUtils::EvaluationDatesAdvance() { COleDateTime dtNow,dtRef,dtData,dtDefault; COleDateTimeSpan dtSpan; long lDays; CString q,strDefDate;; dtDefault.SetDate(1968,03,12); strDefDate=dtDefault.Format(_T("%m/%d/%Y")); rs->QueryReadOnly("SELECT refdate FROM defaults;"); rs->FetchField("refdate",&dtRef); //get the difference dtNow=COleDateTime::GetCurrentTime(); dtSpan=dtNow-dtRef; lDays=dtSpan.GetDays(); //buzz through all the tables fixing up the dates //PROBLEMS TABLE q.Format("UPDATE probs SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE probs SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //LABOUR TABLE q.Format("UPDATE labor SET start = DateAdd(\"d\",%d,[start]) " "WHERE (((start)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE labor SET stop = DateAdd(\"d\",%d,[stop]) " "WHERE (((stop)<>#%s#));",lDays,strDefDate); rs->Ex(q); //MAIL TABLE q.Format("UPDATE mail SET deliverydate = DateAdd(\"d\",%d,[deliverydate]) " "WHERE (((deliverydate)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE mail SET mail.date = DateAdd(\"d\",%d,[date]) " "WHERE (((mail.date)<>#%s#));",lDays,strDefDate); rs->Ex(q); //NONCLIENTS TABLE q.Format("UPDATE nonclients SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE nonclients SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //PARTS TABLE q.Format("UPDATE parts SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE parts SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //PMHEAD TABLE q.Format("UPDATE pmhead SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE pmhead SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE pmhead SET nextsrvdate = DateAdd(\"d\",%d,[nextsrvdate]) " "WHERE (((nextsrvdate)<>#%s#));",lDays,strDefDate); rs->Ex(q); //PMITEMS TABLE q.Format("UPDATE pmitems SET schedate = DateAdd(\"d\",%d,[schedate]) " "WHERE (((schedate)<>#%s#));",lDays,strDefDate); rs->Ex(q); //PROBS TABLE q.Format("UPDATE probs SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE probs SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //PROJECTS TABLE q.Format("UPDATE projects SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE projects SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //RATES TABLE q.Format("UPDATE rates SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE rates SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE rates SET expires = DateAdd(\"d\",%d,[expires]) " "WHERE (((expires)<>#%s#));",lDays,strDefDate); rs->Ex(q); //RENTALS TABLE q.Format("UPDATE rentals SET dateout = DateAdd(\"d\",%d,[dateout]) " "WHERE (((dateout)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE rentals SET datedue = DateAdd(\"d\",%d,[datedue]) " "WHERE (((datedue)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE rentals SET datereturn = DateAdd(\"d\",%d,[datereturn]) " "WHERE (((datereturn)<>#%s#));",lDays,strDefDate); rs->Ex(q); //SRCHKEY TABLE q.Format("UPDATE srchkey SET srchkey.date = DateAdd(\"d\",%d,[date]) " "WHERE (((srchkey.date)<>#%s#));",lDays,strDefDate); rs->Ex(q); //STATUSVIEWS TABLE q.Format("UPDATE statusviews SET woentrydate = DateAdd(\"d\",%d,[woentrydate]) " "WHERE (((woentrydate)<>#%s#));",lDays,strDefDate); rs->Ex(q); //SUBREPAIRS TABLE q.Format("UPDATE subrepair SET sent = DateAdd(\"d\",%d,[sent]) " "WHERE (((sent)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE subrepair SET eta = DateAdd(\"d\",%d,[eta]) " "WHERE (((eta)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE subrepair SET received = DateAdd(\"d\",%d,[received]) " "WHERE (((received)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE subrepair SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE subrepair SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //UNITMODELS TABLE q.Format("UPDATE unitmodels SET discodate = DateAdd(\"d\",%d,[discodate]) " "WHERE (((discodate)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE unitmodels SET introduced = DateAdd(\"d\",%d,[introduced]) " "WHERE (((introduced)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE unitmodels SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE unitmodels SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //UNITS TABLE q.Format("UPDATE units SET purchasedate = DateAdd(\"d\",%d,[purchasedate]) " "WHERE (((purchasedate)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE units SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE units SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //WO TABLE q.Format("UPDATE wo SET closed = DateAdd(\"d\",%d,[closed]) " "WHERE (((closed)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE wo SET starttime = DateAdd(\"d\",%d,[starttime]) " "WHERE (((starttime)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE wo SET stoptime = DateAdd(\"d\",%d,[stoptime]) " "WHERE (((stoptime)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE wo SET created = DateAdd(\"d\",%d,[created]) " "WHERE (((created)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE wo SET modified = DateAdd(\"d\",%d,[modified]) " "WHERE (((modified)<>#%s#));",lDays,strDefDate); rs->Ex(q); //SCHEDULE MARKERS - Added 09/18/2001 (last item for 1.7.2.0) q.Format("UPDATE schedmarkers SET startdate = DateAdd(\"d\",%d,[startdate]) " "WHERE (((startdate)<>#%s#));",lDays,strDefDate); rs->Ex(q); q.Format("UPDATE schedmarkers SET enddate = DateAdd(\"d\",%d,[enddate]) " "WHERE (((enddate)<>#%s#));",lDays,strDefDate); rs->Ex(q); //TURN OFF FIRSTBOOT FLAG rs->Ex("UPDATE defaults SET firstboot = False;"); //cleanup rs->Close(); } void CDBUtils::OnBtntest() { CString q; int x; for(x=1;x<12001;x++) { //insert 12000 clients q.Format("INSERT INTO clients ( company ) SELECT \"%i\";",x); rs->Ex(q); } AfxMessageBox("Done clients"); //insert 1200 parts for(x=1;x<1201;x++) { //insert 12000 clients q.Format("INSERT INTO parts ( partnumber ) SELECT \"%i\";",x); rs->Ex(q); } AfxMessageBox("Done parts"); } void CDBUtils::OnBtnexport() { CXferDlg d; //TO DO: close tables here? d.m_bExportMode=true; d.DoModal(); } void CDBUtils::OnBtnimport() { CXferDlg d; //TO DO: close tables here? d.m_bExportMode=false; d.DoModal(); } BOOL CDBUtils::OnHelpInfo(HELPINFO* pHelpInfo) { WinHelp (0x00020000 + IDD_DBUTILS_FORM,HELP_CONTEXT); return TRUE; }