Question

J'ai une application wxPython qui repose sur un fichier de configuration externe. Je veux fournir des boîtes de dialogue conviviales qui s’affichent s’il ya des erreurs de configuration. J'ai essayé de résoudre ce problème en encapsulant mon appel app.MainLoop () dans une instruction try / except.

Le code ci-dessous fonctionne pour le code init dans ma classe de cadre MainWindow, mais il ne détecte aucune exception se produisant dans MainLoop. Comment puis-je intercepter ces exceptions également?

if __name__ == '__main__':
    app = MyApp(0)
    try:
        MainWindow(None, -1, 'My Cool App')
        app.MainLoop()
    except ConfigParser.Error, error_message:
        messagebox = wx.MessageDialog(None, error_message, 'Configuration Error', wx.OK | wx.ICON_ERROR)
        messagebox.ShowModal()

J'ai lu une mention d'une méthode OnExceptionInMainLoop qui peut être remplacée dans la classe wx.App, mais la source que je lis doit être périmée (2004), car wx.App ne semble plus avoir de méthode par ce moyen. nom.

EDIT:

Je dois pouvoir attraper les exceptions non gérées lors de ma boucle principale afin de pouvoir les gérer et les afficher dans des boîtes de dialogue d'erreur, ne pas passer en mode silencieux ni mettre fin à l'application.

La solution sys.excepthook est trop faible et ne fonctionne pas bien avec le thread wxPython mainloop. Alors que le lien vers l’autre réponse fait la même chose, essayez / sauf d’enrouler autour de la boucle principale qui ne fonctionne pas, encore une fois, car wxPython génère un thread différent pour l’app / ui.

Était-ce utile?

La solution

J'ai codé quelque chose comme ceci pour Chandler , où les exceptions non gérées ouvrent une fenêtre avec la pile et d'autres informations. et les utilisateurs peuvent ajouter des commentaires supplémentaires (qu’ont-ils fait quand c’est arrivé, etc.) et les soumettre aux développeurs Chandler. Un peu comme le Mozilla Talkback ( de nos jours , ils utilisent la fonction Breakpad je crois) si vous voulez.

Pour faire cela dans wxPython, vous devez fournir un paramètre de redirection à wx.App. Cela va apparaître wx.PyOnDemandOutputWindow (vous voudrez probablement pour le remplacer afin de fournir une mise en œuvre plus esthétique).

Les fichiers sources pertinents dans Chandler sont les suivants:

  • Chandler.py lance l'application et définit l'attribut de redirection , ainsi que tente d’attraper et d’afficher les boîtes de dialogue d’erreur en cas d’échec du démarrage normal de l’application
  • Application.py personnalise l'objet d'application, notamment: configuration de notre fenêtre personnalisée wx.PyOnDemandOutputWindow
  • feedback.py a l'implémentation pour la personnalisation wx.PyOnDemandOutputWindow; En plus, vous aurez besoin de feedback.xrc et feedback_xrc.py

Autres conseils

Je ne sais pas si cela fonctionnera pour une application wxPython, mais dans le module sys, vous pouvez écraser l'attribut excepthook, une fonction appelée avec 3 arguments, (type, valeur, traceback) , lorsqu'une exception d'inauguration est interceptée. Vous pouvez y installer votre propre fonction ne gérant que les exceptions souhaitées et appeler la fonction d'origine pour toutes les autres.

Consultez: http: //docs.python .org / library / sys.html # sys.excepthook

Peut-être cette question pourrait être utile, il essaie de capturer toutes les exceptions.

Afficher la solution qui fonctionnait pour moi avec un problème très similaire.

import wx
import sys
import traceback

class Frame(wx.Frame):
    def __init__(self):
        wx.Frame.__init__(self, None)
        panel = wx.Panel(self)
        m_close = wx.Button(panel, -1, "Error")
        m_close.Bind(wx.EVT_BUTTON, self.OnErr)
    def OnErr(self, event):
        1/0

def handleGUIException(exc_type, exc_value, exc_traceback):
    err_msg = ''.join(traceback.format_exception(exc_type, exc_value, exc_traceback))
    err_msg += '\n Your App will now terminate'
    # Here collecting traceback and some log files to be sent for debugging.
    # But also possible to handle the error and continue working.
    dlg = wx.MessageDialog(None, err_msg, 'Termination dialog', wx.OK | wx.ICON_ERROR)
    dlg.ShowModal()
    dlg.Destroy()
    sys.exit()

sys.excepthook = handleGUIException

if __name__ == '__main__':
    app = wx.App(redirect=False) 
    top = Frame()
    top.Show()
    app.MainLoop()

L’utilisation de sys.excepthook me convient parfaitement.

Je trouve l'article suivant très utile: wxPython: Interception des exceptions n'importe où .

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top