Hi, I''m using FXRuby for building a database front-end. I have quite a lot of classes now, made up of multiple methods each. Most of the time I use rescue blocks in case an exception is raised by the framemork. But doing that in every method of every class is really tedious. If an exception is raised from a method without a rescue block, the problem is that my application quits, since the application "run" method stops. begin $app = MyApp.new $app.create $app.run rescue Exception => e DbError.show("", e) end I was wondering if we could define some sort of "default error handler" for errors raised from the framework, in order to avoid both the application crash, and the "one rescue per method" solution... Thanks! Philippe Lang
Philippe Lang wrote:> Hi, > > I''m using FXRuby for building a database front-end. I have quite a lot > of classes now, made up of multiple methods each. Most of the time I use > rescue blocks in case an exception is raised by the framemork. But doing > that in every method of every class is really tedious. > > If an exception is raised from a method without a rescue block, the > problem is that my application quits, since the application "run" method > stops. > > > begin > > $app = MyApp.new > $app.create > $app.run > > rescue Exception => e > > DbError.show("", e) > > end > > > I was wondering if we could define some sort of "default error handler" > for errors raised from the framework, in order to avoid both the > application crash, and the "one rescue per method" solution...That''s a good question. I usually just try to make "one rescue per method" as painless as possible, by writing wrapper methods. Still, that''s "one wrapper per method", which is only a slight improvement. -- vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407
On 10/8/07, Joel VanderWerf <vjoel at path.berkeley.edu> wrote:> Philippe Lang wrote: > > Hi, > > > > I''m using FXRuby for building a database front-end. I have quite a lot > > of classes now, made up of multiple methods each. Most of the time I use > > rescue blocks in case an exception is raised by the framemork. But doing > > that in every method of every class is really tedious. > > > > If an exception is raised from a method without a rescue block, the > > problem is that my application quits, since the application "run" method > > stops. > > > > > > begin > > > > $app = MyApp.new > > $app.create > > $app.run > > > > rescue Exception => e > > > > DbError.show("", e) > > > > end > > > > > > I was wondering if we could define some sort of "default error handler" > > for errors raised from the framework, in order to avoid both the > > application crash, and the "one rescue per method" solution... > > That''s a good question. > > I usually just try to make "one rescue per method" as painless as > possible, by writing wrapper methods. Still, that''s "one wrapper per > method", which is only a slight improvement. >Try to centralize access to the DB. Channel all method calls to the DB through one dedicated method that handles db errors. something like this could do the job: class DB def safe_call( method, *args, &block) self.send( method, *args, &block) rescue DBError # all db errorhandling here end end there might be even better solutions -- meinrad
fxruby-users-bounces at rubyforge.org wrote:> Philippe Lang wrote: >> Hi, >> >> I''m using FXRuby for building a database front-end. I have quite a >> lot of classes now, made up of multiple methods each. Most of the >> time I use rescue blocks in case an exception is raised by the >> framemork. But doing that in every method of every class is really >> tedious. >> >> If an exception is raised from a method without a rescue block, the >> problem is that my application quits, since the application "run" >> method stops. >> >> >> begin >> >> $app = MyApp.new >> $app.create >> $app.run >> >> rescue Exception => e >> >> DbError.show("", e) >> >> end >> >> >> I was wondering if we could define some sort of "default error >> handler" for errors raised from the framework, in order to avoid >> both the application crash, and the "one rescue per method" >> solution... > > That''s a good question. > > I usually just try to make "one rescue per method" as painless as > possible, by writing wrapper methods. Still, that''s "one wrapper per > method", which is only a slight improvement.Hi everyone, Lyle, do you think it would be possible to add this feature to the FXApp class: the ability to register some sort of "rescue handler", that can intercept in the "run" method the exceptions that would otherwise crash the application? For compatitility, the default handler could simply raise the exception again, which is what the framework is doing now. This would be really useful. Regards, Philippe Lang
On Oct 9, 2007, at 9:51 AM, Philippe Lang wrote:> Lyle, do you think it would be possible to add this feature to the > FXApp > class: the ability to register some sort of "rescue handler", that can > intercept in the "run" method the exceptions that would otherwise > crash > the application? For compatitility, the default handler could simply > raise the exception again, which is what the framework is doing now.If you will file a bug report (or feature request) about it, I''ll consider it. I know that it''s sometimes difficult to work around FOX''s error handling mechanisms, since Jeroen just calls exit() on most errors; but particular circumstance may not be affected by that.
Lyle Johnson wrote:> On Oct 9, 2007, at 9:51 AM, Philippe Lang wrote: > >> Lyle, do you think it would be possible to add this feature to the >> FXApp >> class: the ability to register some sort of "rescue handler", that can >> intercept in the "run" method the exceptions that would otherwise >> crash >> the application? For compatitility, the default handler could simply >> raise the exception again, which is what the framework is doing now. > > If you will file a bug report (or feature request) about it, I''ll > consider it. I know that it''s sometimes difficult to work around > FOX''s error handling mechanisms, since Jeroen just calls exit() on > most errors; but particular circumstance may not be affected by that.I don''t think Philippe is talking about those kinds of situations (that cause Fox to call exit()), but rather situations where ruby callback raises a ruby exception, and it propagates outside of the #run call. Is there any reason why the following code won''t work? begin app.run rescue => ex if ... # ex can be retried retry end end app.exit -- vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407
fxruby-users-bounces at rubyforge.org wrote:> Lyle Johnson wrote: >> On Oct 9, 2007, at 9:51 AM, Philippe Lang wrote: >> >>> Lyle, do you think it would be possible to add this feature to the >>> FXApp class: the ability to register some sort of "rescue handler", >>> that can intercept in the "run" method the exceptions that would >>> otherwise crash the application? For compatitility, the default >>> handler could simply raise the exception again, which is what the >>> framework is doing now. >> >> If you will file a bug report (or feature request) about it, I''ll >> consider it. I know that it''s sometimes difficult to work around >> FOX''s error handling mechanisms, since Jeroen just calls exit() on >> most errors; but particular circumstance may not be affected by that. > > I don''t think Philippe is talking about those kinds of situations > (that cause Fox to call exit()), but rather situations where ruby > callback raises a ruby exception, and it propagates outside of the > #run call. > > Is there any reason why the following code won''t work? > > begin > app.run > rescue => ex > if ... # ex can be retried > retry > end > end > app.exitHi Joel, This is exactly the kind of thing I was takling about, yes, and it works pretty well, but not 100%, apparently. I''m not sure an FXApp can be "re-run" that way, without taking risks. Is that true Joeroen? In my tests, I have noticed for example that an FXTabBook, after an exception caught by your technique, has got "zombie" pages in it: the place is still allocated for a page tab, but no page tab is visible at all. I also tried that, but without success: begin app.repaint app.forceRefresh app.flush app.run rescue Exception => e ---> show error to the user retry end app.exit Philippe
Philippe Lang wrote:> fxruby-users-bounces at rubyforge.org wrote:,,,>> Is there any reason why the following code won''t work? >> >> begin >> app.run >> rescue => ex >> if ... # ex can be retried >> retry >> end >> end >> app.exit > > Hi Joel, > > This is exactly the kind of thing I was takling about, yes, and it works > pretty well, but not 100%, apparently. I''m not sure an FXApp can be > "re-run" that way, without taking risks. Is that true Joeroen? > > In my tests, I have noticed for example that an FXTabBook, after an > exception caught by your technique, has got "zombie" pages in it: the > place is still allocated for a page tab, but no page tab is visible at > all.The reason I thought it *should* work is that FXApp::run() and FXApp::runWhileEvents() are doing basically the same thing, with slightly different logic. So if it is safe to unwind from runWhileEvents and then re-enter the event loop, then it should be safe to do so with run as well. -- vjoel : Joel VanderWerf : path berkeley edu : 510 665 3407
On 10/10/07, Joel VanderWerf <vjoel at path.berkeley.edu> wrote:> Philippe Lang wrote: > > fxruby-users-bounces at rubyforge.org wrote: > ,,, > >> Is there any reason why the following code won''t work? > >> > >> begin > >> app.run > >> rescue => ex > >> if ... # ex can be retried > >> retry > >> end > >> end > >> app.exit > > > > Hi Joel, > > > > This is exactly the kind of thing I was takling about, yes, and it works > > pretty well, but not 100%, apparently. I''m not sure an FXApp can be > > "re-run" that way, without taking risks. Is that true Joeroen? > > > > In my tests, I have noticed for example that an FXTabBook, after an > > exception caught by your technique, has got "zombie" pages in it: the > > place is still allocated for a page tab, but no page tab is visible at > > all. > > The reason I thought it *should* work is that FXApp::run() and > FXApp::runWhileEvents() are doing basically the same thing, with > slightly different logic. So if it is safe to unwind from runWhileEvents > and then re-enter the event loop, then it should be safe to do so with > run as well. >... if there weren''t all those nasty side effects :P
fxruby-users-bounces at rubyforge.org wrote:>>> Is there any reason why the following code won''t work? >>> >>> begin >>> app.run >>> rescue => ex >>> if ... # ex can be retried >>> retry >>> end >>> end >>> app.exit >> >> Hi Joel, >> >> This is exactly the kind of thing I was takling about, yes, and it >> works pretty well, but not 100%, apparently. I''m not sure an FXApp >> can be "re-run" that way, without taking risks. Is that true Joeroen? >> >> In my tests, I have noticed for example that an FXTabBook, after an >> exception caught by your technique, has got "zombie" pages in it: the >> place is still allocated for a page tab, but no page tab is visible >> at all. > > The reason I thought it *should* work is that FXApp::run() and > FXApp::runWhileEvents() are doing basically the same thing, with > slightly different logic. So if it is safe to unwind from > runWhileEvents and then re-enter the event loop, then it should be > safe to do so with run as well.OK, I managed to reduce my problem to the following test program: as soon as you try to add a "buggy tab", the GUI starts to mess up. The result, you will see, is different if you start by adding a buggy tab, or if you start by adding a normal tab. Maybe I need to call some kind of "refresh" after the exception is raised? ------------------------------------ #!/usr/bin/ruby require ''fox16'' include Fox class MyFXTabItem < FXTabItem end class MyBuggyFXTabItem < FXTabItem def initialize(text, icon=nil, data=nil) super raise Exception.new end end class MyWindow < FXMainWindow def initialize(app) super(app, "Window", nil, nil, DECOR_ALL, 0, 0, 600, 350) # Menu bar stretched along the top of the main window menubar = FXMenuBar.new(self, LAYOUT_SIDE_TOP|LAYOUT_FILL_X) # File menu filemenu = FXMenuPane.new(self) FXMenuTitle.new(menubar, "&File", nil, filemenu) FXMenuCommand.new(filemenu, "&Quit\tCtl-Q\tQuit the application", nil, app, FXApp::ID_QUIT) # Content contents = FXVerticalFrame.new(self, LAYOUT_FILL_X|LAYOUT_FILL_Y) # Tabs @tabbook = FXTabBook.new(contents,:opts => LAYOUT_FILL_X|LAYOUT_FILL_Y|LAYOUT_RIGHT) FXButton.new(contents, "add tab").connect(SEL_COMMAND) do |sender, selector, data| # First item is a list tab = MyFXTabItem.new(@tabbook, "&Simple List", nil) frame = FXHorizontalFrame.new(@tabbook, FRAME_THICK|FRAME_RAISED) simplelist = FXList.new(frame, :opts => LIST_EXTENDEDSELECT|LAYOUT_FILL_X|LAYOUT_FILL_Y) simplelist.appendItem("First Entry") simplelist.appendItem("Second Entry") simplelist.appendItem("Third Entry") simplelist.appendItem("Fourth Entry") frame.create tab.create tab.show end FXButton.new(contents, "add buggy tab").connect(SEL_COMMAND) do |sender, selector, data| # Second item is a file list tab = MyBuggyFXTabItem.new(@tabbook, "F&ile List", nil) frame = FXHorizontalFrame.new(@tabbook, FRAME_THICK|FRAME_RAISED) filelist = FXFileList.new(frame, :opts => ICONLIST_EXTENDEDSELECT|LAYOUT_FILL_X|LAYOUT_FILL_Y) frame.create tab.create tab.show end end def create super show(PLACEMENT_SCREEN) end end if __FILE__ == $0 $app = FXApp.new("Attik System", "FXRuby Test") MyWindow.new($app) $app.create begin $app.run rescue Exception => e FXMessageBox.information($app, MBOX_OK, "Error", "An exception was raised") retry end end