I recently upgraded an application from version 8 to version 11. This is a script that was originally created through the help of Scott Emerick and Dr. Peter Wayne way back in January of 2004. After 6 hours of troubleshooting, I was finally able to get this script working again.
I have an invoicing set with a header table, two child tables and six grandchild tables. When viewing the form, the user runs this script to duplicate the existing invoice. When clicking on a toolbar button, the script runs allowing the user to select which line items of the invoice they wish to duplicate. After selecting the items, the script runs creating a new invoice and copies the selected child and selected grandchild items to the new invoice. The original invoice form is closed and a new form is opened showing the duplicated invoice.
I have a function named "AddRecords()" which does all the copying of records. This is the code which Scott and Dr. Peter Wayne helped with.
This function is run from within a while...end while. When the function fails, there is no warning messages. For some reason, the while...end while terminates and the code continues until finished.
I traced the cause of the failure to timing issues within the AddRecords() function. I ended up having to add numerous xbasic_wait_for_idle functions with a time value of .3 to get the code to run. I created a variable called vdelay to change the delay value in just one place. The variable value is used in seven different places.
I haven't tested this across a network yet, but this is now working on a Win7 i7 machine. The problem was discovered on an older WinXP machine running across a network.
I'm disappointed that this has happened especially since this code has been running for the last 9 years. I know this script is very long, but could someone give a quick look at the addrecords() function and see if there is something that could/should be changed. All these xbasic_wait_for_idles slow the script way down.
Thanks,
Ron
I have an invoicing set with a header table, two child tables and six grandchild tables. When viewing the form, the user runs this script to duplicate the existing invoice. When clicking on a toolbar button, the script runs allowing the user to select which line items of the invoice they wish to duplicate. After selecting the items, the script runs creating a new invoice and copies the selected child and selected grandchild items to the new invoice. The original invoice form is closed and a new form is opened showing the duplicated invoice.
I have a function named "AddRecords()" which does all the copying of records. This is the code which Scott and Dr. Peter Wayne helped with.
This function is run from within a while...end while. When the function fails, there is no warning messages. For some reason, the while...end while terminates and the code continues until finished.
I traced the cause of the failure to timing issues within the AddRecords() function. I ended up having to add numerous xbasic_wait_for_idle functions with a time value of .3 to get the code to run. I created a variable called vdelay to change the delay value in just one place. The variable value is used in seven different places.
I haven't tested this across a network yet, but this is now working on a Win7 i7 machine. The problem was discovered on an older WinXP machine running across a network.
I'm disappointed that this has happened especially since this code has been running for the last 9 years. I know this script is very long, but could someone give a quick look at the addrecords() function and see if there is something that could/should be changed. All these xbasic_wait_for_idles slow the script way down.
Thanks,
Ron
Code:
'Date Created: 12-Jan-2004 04:33:25 PM 'Last Updated: 30-Oct-2013 01:00:34 PM 'Created By : Scott Emerick, KEYTECH 2000 'Updated By : Ron ''check and see if this invoice has been posted DIM SHARED vcPosted AS c vcPosted = left(parentform:Sjinv_no.value,1) if vcPosted = "S" then ui_beep(UI_CRITICAL_BEEP) DIM SHARED vDlg_Title as C DIM SHARED vMsg as C vMsg="This Invoice has Already Been Posted. Are You Certain You Want to Duplicate This Invoice?" DIM SHARED varC_result as C DIM XDialogStyle as P XDialogStyle.AccentColor = "Off White" XDialogStyle.Color = "Yellow" vDlg_Title="Posted Invoice" dlg_text = <<%dlg% {Windowstyle=Gradient Horizontal} {font=Arial,11,B}{units=F}{xmargin=4,4}{ysize=.3}; {image=$sys_Error}{sp}{sp}{sp} {text=%H=R%50,2vMsg};; {line=0};;{justify=center,Center} <12,1.5Yes> <*12,1.5Cancel> %dlg% varC_result=ui_dlg_box(vdlg_title, dlg_text) if varC_result <> "Yes" then end end if end if parentform.Commit() UI_Yield() tbl = table.current() 'idx = tbl.update_production_index() 'Get 'Value' property of 'Transno' in Form 'MInvoices' . DIM SHARED vCurTransNo AS c vCurTransNo = parentform:Transno.value 'Create an XDialog dialog box to prompt for parameters. DIM SHARED vMItems as C DIM SHARED vVerify as C DIM SHARED varC_result as C auto_list_vMItems = table.external_record_content_get("msquawk.dbf",\ "Itemno+\" \"+F_UPPER(Desc)+\"|\"+transno+\"|\"+SwkNo","if(len(alltrim(Itemno))<4,padl(alltrim(Itemno),4,\"0\"),Itemno)",\ "Transno = Var->vCurTransNo") Tryagain: temp_count = w_count(auto_list_vMItems,crlf()) DELETE a_vMItems DIM a_vMItems[temp_count] as c a_vMItems.initialize(auto_list_vMItems) heading_string = "Selected Items will be Moved to A New Invoice" ok_button_label = "&OK" cancel_button_label = "&Cancel" varC_result = ui_dlg_box("Select Discrepancies to Move",<<%dlg% {xmargin=5,5}; {font=arial,10} {region} {text=115,1:heading_string}; {endregion}; {region} [.120,37vMItems^$$a_vMItems]; {endregion}; {region} <*15,1.5=ok_button_label!OK> <15,1.5=cancel_button_label!CANCEL> {endregion}; %dlg%) if varC_result <> "OK" then end end if IF vMItems = "" THEN ui_msg_box("Warning","No Discrepancies Have Been Selected",UI_STOP_SYMBOL) goto tryagain END IF 'Duplicate Invoice with selected discrepancies 'Count the number of squawks to be duplicated dim kount as n kount = 0 FOR each foo in vMItems kount = kount + 1 NEXT vVerify = *for_each(foo, word(foo,1," ",2),vMItems) vVerify = alltrim(vVerify) vVerify = stritran(vVerify,crlf(),", ") vVerify = word_wrap(vVerify,76) 'Displays a message box (style:'Yes, No Buttons', image: 'Question symbol', id: 'vChoice'). DIM SHARED vChoice_result as N DIM SHARED vChoice_YES_Button as L DIM SHARED vChoice_NO_Button as L vChoice_YES_Button = .F. vChoice_NO_Button = .F. title_var = "Do you want to Copy Selected Discrepancies to a New Invoice?" message_text_var = vVerify vChoice_result=ui_msg_box(title_var,message_text_var,UI_YES_NO+ UI_SECOND_BUTTON_DEFAULT+ UI_QUESTION_SYMBOL) 'Test to see which button on the message box was pressed.... SELECT CASE vChoice_result = UI_YES_SELECTED vChoice_YES_Button= .t. goto moveon CASE vChoice_result = UI_NO_SELECTED vChoice_NO_Button= .t. end END SELECT moveon: dim msg as C msg = " Duplicating Selected Items to a New Invoice" dim shared curfile as C = "" PleaseWait15(.t.,msg) 'strip the Item and Description from the select items, add the field = statement, trim 'leading and trailing spaces and replace the crlf with .or. vMItems = *for_each(foo, word2(foo, 3, "|") ,vMItems) dim vFilter as C vfilter = alltrim(vMItems) pct=3 'PleaseWait Funtion ui_modeless_dlg_refresh(msg) ui_yield() dim tz as P tz = table.open("tmp_msquawk") tz.zap(.t.) tz.close() pct=6 'PleaseWait Funtion ui_modeless_dlg_refresh(msg) ui_yield() dim tbl_source as P dim qry as P tbl_source = table.open_session("msquawk",FILE_RO_SHARED) query.order = "Transno+swkno" query.filter = "Transno = var->vCurTransNo" qry = tbl_source.query_create() tbl_source.fetch_first() WHILE .not. tbl_source.fetch_eof() IF word_exists(vFilter, tbl_source.swkno, crlf() ) = .T. THEN result = tbl_source.copy_record_to("tmp_msquawk") END IF tbl_source.fetch_next() END WHILE qry.drop() tbl_source.close() pct=12 'PleaseWait Funtion ui_modeless_dlg_refresh(msg) ui_yield() 'Create a new header and add the correct number of squawks dim mm as p dim mc as p dim tmp_t as p dim i as n dim old_mm as b tmp_t = table.open("tmp_msquawk") mm=table.current(1) 'Minv_hdr2 mc=table.current(2) 'Msquawk g1=table.get("mfix") g2=table.get("mlabor") g3=table.get("mparts") g4=table.get("mship") g5=table.get("mosw") g6=table.get("mmisc") pct = 15 ui_modeless_dlg_refresh(msg) UI_Yield() mm2=table.open(mm.name_get()) mc2=table.open(mc.name_get()) g11=table.open(g1.name_get()) g22=table.open(g2.name_get()) g33=table.open(g3.name_get()) g44=table.open(g4.name_get()) g55=table.open(g5.name_get()) g66=table.open(g6.name_get()) 'First, the header record gets copied old_mm = mm.record_data_get() mm2.enter_begin() 'note: in the table the transno is an autoincrement field. A new transno is assigned 'by the field rule which overrides the Xbasic record_data_set() mm2.record_data_set(old_mm) mm2.enter_end(.t.) kount = count(msquawk->transno,GRP->minv_hdr2) '(Msquawk->transno,GRP->header) pct = 18 ui_modeless_dlg_refresh(msg) UI_Yield() ''Now the child records IF kount>0 THEN on error goto broke dim vItemno as C dim i as n i = 1 mc.fetch_first(1) 'squawks WHILE .not. mc.fetch_eof() vItemno = mc.itemno result = exist(padl(alltrim(vItemno),4,"0"),"tmp_msquawk","Itemno") if result = .T. then ' msgbox(mc.itemno) AddRecords( i, vItemno ) end if i = i + 1 mc.fetch_next(1) END WHILE END IF pct = 92 ui_modeless_dlg_refresh(msg) UI_Yield() dim newinvoice as c newinvoice = mm2.inv_no pct = 95 ui_modeless_dlg_refresh(msg) UI_Yield() 'Close Opened tables tmp_t.close() mm2.close() mc2.close() g11.close() g22.close() g33.close() g44.close() g55.close() g66.close() pct = 98 ui_modeless_dlg_refresh(msg) UI_Yield() dim Origtotal as N Origtotal = topparent:invoicetotal.value PleaseWait15(.f.,msg) 'rebuild_minvoices_indexes() finishup: ui_msg_box("Duplicate Invoice",\ "Process Completed Successfully. The new Invoice is "+var->newinvoice+" !",0+64) ui_freeze(.t.) Parentform.Close(.f.) xbasic_wait_for_idle() dim Frm as P Frm = Form.load("MInvoices") Frm.find(newinvoice) Frm.show() Frm.activate() this.enable() 'enable button on way out ui_freeze(.f.) on error goto 0 END broke: on error goto 0 PleaseWait15(.f.,msg) err_msg = error_text_get(error_code_get()) err_numb=error_code_get() line = error_line_number_get() script = error_script_get() ui_msg_box("Error",\ err_msg+" Error occurred at line "+alltrim(str(line,4,0))+" in script: "+script) END FUNCTION AddRecords AS L ( i as N, Itemno as C ) dim vdelay as N vdelay = .3 'this time value give a margin of .1, .2 fails curfile = "Copying Discrepancy "+Itemno pct=20+round((i/kount)*60,0) ui_modeless_dlg_refresh(msg) ui_yield() 'msquawk mc_rec=mc.record_data_get() mc2.enter_begin() mc2.record_data_set(mc_rec) mc2.transno=mm2.transno mc2.enter_end(.t.) mc2.change_begin() xbasic_wait_for_idle() mc2.change_end(.t.) xbasic_wait_for_idle(vdelay) ' grandchild1 mfix g1_rec=g1.record_data_get() g11.enter_begin() g11.record_data_set(g1_rec) g11.transno=mc2.transno g11.swkno=mc2.swkno g11.enter_end(.t.) xbasic_wait_for_idle(vdelay) ' grandchild2 mlabor g22.batch_begin() g2.fetch_first() WHILE .not. g2.fetch_eof() g2_rec=g2.record_data_get() g22.enter_begin() g22.record_data_set(g2_rec) g22.transno=mc2.transno g22.swkno=mc2.swkno g22.enter_end(.t.) g22.change_begin(.t.) xbasic_wait_for_idle() g22.change_end(.t.) g2.fetch_next() xbasic_wait_for_idle(vdelay) END WHILE g22.batch_end() ' grandchild3 mparts g33.batch_begin() g3.fetch_first() WHILE .not. g3.fetch_eof() g3_rec=g3.record_data_get() g33.enter_begin() g33.record_data_set(g3_rec) g33.transno=mc2.transno g33.swkno=mc2.swkno g33.enter_end(.t.) g3.fetch_next() xbasic_wait_for_idle(vdelay) END WHILE g33.batch_end() ' grandchild4 mship g44.batch_begin() g4.fetch_first() WHILE .not. g4.fetch_eof() g4_rec=g4.record_data_get() g44.enter_begin() g44.record_data_set(g4_rec) g44.transno=mc2.transno g44.swkno=mc2.swkno g44.enter_end(.t.) g4.fetch_next() xbasic_wait_for_idle(vdelay) END WHILE g44.batch_end() ' grandchild5 mosw g55.batch_begin() g5.fetch_first() WHILE .not. g5.fetch_eof() g5_rec=g5.record_data_get() g55.enter_begin() g55.record_data_set(g5_rec) g55.transno=mc2.transno g55.swkno=mc2.swkno g55.enter_end(.t.) g5.fetch_next() xbasic_wait_for_idle(vdelay) END WHILE g55.batch_end() ' grandchild6 mmisc g66.batch_begin() g6.fetch_first() WHILE .not. g6.fetch_eof() g6_rec=g6.record_data_get() g66.enter_begin() g66.record_data_set(g6_rec) g66.transno=mc2.transno g66.swkno=mc2.swkno g66.enter_end(.t.) g6.fetch_next() xbasic_wait_for_idle(vdelay) END WHILE g66.batch_end() END FUNCTION FUNCTION rebuild_minvoices_indexes AS L () 'Update maintenance invoice table indexes after importing a work order. dim table_list as c table_list = <<%list% mfix minv_hdr2 mlabor mmisc mosw mparts mship msquawk %list% 'convert table_list to long file names table_list = *for_each(x,table.filename_get(x),table_list) 'check that all tables in the table_list exist check_exist = *for_each(x,x+"|" + file.exists(x),table_list) missing = filter_string(check_exist,"|False",crlf()) IF missing <> "" THEN msg = "Indexes in the following tables will not be updated because the tables cannot be found: " + crlf() + stritran(missing,"|False","") ui_msg_box("Warning",msg,UI_ATTENTION_SYMBOL) table_list = filter_string(check_exist,"|True",crlf()) IF table_list = "" THEN ui_msg_box("Error","No tables for which to update indexes.",UI_STOP_SYMBOL) end ELSE table_list = stritran(table_list,"|True","") END IF END IF tables_to_update = table_list dim count as n count = w_count(tables_to_update,crlf()) dim i as n dim tbl as p FOR i = 1 TO count table_i = word(tables_to_update,i,crlf()) tbl = table.open(table_i) tbl.update_production_index() tbl.close() NEXT i END FUNCTION FUNCTION PleaseWait15 AS C (Show = .F.,msg="") 'by using the variable 'msg' in the function, this one function can be used in many 'different scripts and have a custom message in each script. This function has a text 'line PleaseWait15 = "" IF msg = "" THEN msg = " Processing Operation" END IF IF show = .F. IF ui_modeless_dlg_exist(msg) ui_modeless_dlg_close(msg) END IF exit function END IF dim shared pct as N box_code = <<%dlg% {background=Dirty White} {font=calibri,18,i} {text=65curFile}; {'}; {font=arial,12} {sp=32}{text=4pct}%; {progress=60pct} {'}; {'}; %dlg% ui_modeless_dlg_box(msg,box_code) 'copy the next 2 lines to change the progress bar. 'Change the "PCT=" amount to move the bar. pct=1 ui_modeless_dlg_refresh(msg) box_event = <<%code% 2=2 %code% ui_modeless_dlg_box(msg,box_code,box_event) ui_modeless_dlg_setfocus(msg) ui_modeless_dlg_refresh(msg) END FUNCTION
Comment