Vn.App = new Class ({ Extends: Vn.Object ,initialize: function () { window.onerror = this.onWindowError.bind (this); Vn.Hash.initialize (); this.conn = new Db.Conn (); this.login = new Vn.Login ({conn: this.conn}); } ,run: function () { if (Vn.Cookie.check ('vn_pass')) { this.conn.open (null, null, null, this.onAutoLogin.bind (this)); } else { this.login.on ('login', this.onLogin, this); this.login.show (); } } ,onAutoLogin: function (success) { if (!success) { Vn.Cookie.unset ('vn_pass'); this.run (); } else this.onLogin (); } ,onLogin: function () { this.login.disconnectByInstance (this); this.login.hide (); var gui = new Vn.Gui ({conn: this.conn}); gui.on ('logout', this.onLogout, this); gui.show (); } ,onLogout: function (gui) { gui.hide (); gui.unref (); Vn.Cookie.unset ('vn_pass'); this.run (); } ,onWindowError: function (message, file, line) { var error = new Error (message); error.fileName = file; error.lineNumber = line; Htk.Toast.showError (_('There was an internal error')); this.notifyError (error); } ,notifyError: function (error) { if (error instanceof Error) { var httpRequest = new Vn.HttpRequest () httpRequest.add ({ 'file': error.fileName ,'line': error.lineNumber ,'message': error.message ,'stack': error.stack }); httpRequest.send ('log.php'); } } ,_destroy: function () { this.login.unref (); this.conn.unref (); } });