]>
Commit | Line | Data |
---|---|---|
6527f429 DM |
1 | /**\r |
2 | * A helper class for the native JavaScript Error object that adds a few useful capabilities for handling\r | |
3 | * errors in an application. When you use Ext.Error to {@link #raise} an error from within any class that\r | |
4 | * uses the Class System, the Error class can automatically add the source class and method from which\r | |
5 | * the error was raised. It also includes logic to automatically log the error to the console, if available,\r | |
6 | * with additional metadata about the error. In all cases, the error will always be thrown at the end so that\r | |
7 | * execution will halt.\r | |
8 | *\r | |
9 | * Ext.Error also offers a global error {@link #handle handling} method that can be overridden in order to\r | |
10 | * handle application-wide errors in a single spot. You can optionally {@link #ignore} errors altogether,\r | |
11 | * although in a real application it's usually a better idea to override the handling function and perform\r | |
12 | * logging or some other method of reporting the errors in a way that is meaningful to the application.\r | |
13 | *\r | |
14 | * At its simplest you can simply raise an error as a simple string from within any code:\r | |
15 | *\r | |
16 | * Example usage:\r | |
17 | *\r | |
18 | * Ext.raise('Something bad happened!');\r | |
19 | *\r | |
20 | * If raised from plain JavaScript code, the error will be logged to the console (if available) and the message\r | |
21 | * displayed. In most cases however you'll be raising errors from within a class, and it may often be useful to add\r | |
22 | * additional metadata about the error being raised. The {@link #raise} method can also take a config object.\r | |
23 | * In this form the `msg` attribute becomes the error description, and any other data added to the config gets\r | |
24 | * added to the error object and, if the console is available, logged to the console for inspection.\r | |
25 | *\r | |
26 | * Example usage:\r | |
27 | *\r | |
28 | * Ext.define('Ext.Foo', {\r | |
29 | * doSomething: function(option){\r | |
30 | * if (someCondition === false) {\r | |
31 | * Ext.raise({\r | |
32 | * msg: 'You cannot do that!',\r | |
33 | * option: option, // whatever was passed into the method\r | |
34 | * 'error code': 100 // other arbitrary info\r | |
35 | * });\r | |
36 | * }\r | |
37 | * }\r | |
38 | * });\r | |
39 | *\r | |
40 | * If a console is available (that supports the `console.dir` function) you'll see console output like:\r | |
41 | *\r | |
42 | * An error was raised with the following data:\r | |
43 | * option: Object { foo: "bar"}\r | |
44 | * foo: "bar"\r | |
45 | * error code: 100\r | |
46 | * msg: "You cannot do that!"\r | |
47 | * sourceClass: "Ext.Foo"\r | |
48 | * sourceMethod: "doSomething"\r | |
49 | *\r | |
50 | * uncaught exception: You cannot do that!\r | |
51 | *\r | |
52 | * As you can see, the error will report exactly where it was raised and will include as much information as the\r | |
53 | * raising code can usefully provide.\r | |
54 | *\r | |
55 | * If you want to handle all application errors globally you can simply override the static {@link #handle} method\r | |
56 | * and provide whatever handling logic you need. If the method returns true then the error is considered handled\r | |
57 | * and will not be thrown to the browser. If anything but true is returned then the error will be thrown normally.\r | |
58 | *\r | |
59 | * Example usage:\r | |
60 | *\r | |
61 | * Ext.Error.handle = function(err) {\r | |
62 | * if (err.someProperty == 'NotReallyAnError') {\r | |
63 | * // maybe log something to the application here if applicable\r | |
64 | * return true;\r | |
65 | * }\r | |
66 | * // any non-true return value (including none) will cause the error to be thrown\r | |
67 | * }\r | |
68 | *\r | |
69 | * @class Ext.Error\r | |
70 | */\r | |
71 | (function() {\r | |
72 | // @define Ext.lang.Error\r | |
73 | // @define Ext.Error\r | |
74 | // @require Ext\r | |
75 | \r | |
76 | function toString() {\r | |
77 | var me = this,\r | |
78 | cls = me.sourceClass,\r | |
79 | method = me.sourceMethod,\r | |
80 | msg = me.msg;\r | |
81 | \r | |
82 | if (method) {\r | |
83 | if (msg) {\r | |
84 | method += '(): ';\r | |
85 | method += msg;\r | |
86 | } else {\r | |
87 | method += '()';\r | |
88 | }\r | |
89 | }\r | |
90 | \r | |
91 | if (cls) {\r | |
92 | method = method ? (cls + '.' + method) : cls;\r | |
93 | }\r | |
94 | \r | |
95 | return method || msg || '';\r | |
96 | }\r | |
97 | \r | |
98 | Ext.Error = function(config) {\r | |
99 | if (Ext.isString(config)) {\r | |
100 | config = { msg: config };\r | |
101 | }\r | |
102 | \r | |
103 | var error = new Error();\r | |
104 | \r | |
105 | Ext.apply(error, config);\r | |
106 | \r | |
107 | error.message = error.message || error.msg; // 'message' is standard ('msg' is non-standard)\r | |
108 | // note: the above does not work in old WebKit (me.message is readonly) (Safari 4)\r | |
109 | \r | |
110 | error.toString = toString;\r | |
111 | \r | |
112 | return error;\r | |
113 | };\r | |
114 | \r | |
115 | Ext.apply(Ext.Error, {\r | |
116 | /**\r | |
117 | * @property {Boolean} ignore\r | |
118 | * Static flag that can be used to globally disable error reporting to the browser if set to true\r | |
119 | * (defaults to false). Note that if you ignore Ext errors it's likely that some other code may fail\r | |
120 | * and throw a native JavaScript error thereafter, so use with caution. In most cases it will probably\r | |
121 | * be preferable to supply a custom error {@link #handle handling} function instead.\r | |
122 | *\r | |
123 | * Example usage:\r | |
124 | *\r | |
125 | * Ext.Error.ignore = true;\r | |
126 | *\r | |
127 | * @static\r | |
128 | */\r | |
129 | ignore: false,\r | |
130 | \r | |
131 | /**\r | |
132 | * This method is called internally by {@link Ext#raise}. Application code should\r | |
133 | * call {@link Ext#raise} instead of calling this method directly.\r | |
134 | *\r | |
135 | * @static\r | |
136 | * @deprecated 6.0.0 Use {@link Ext#raise} instead.\r | |
137 | */\r | |
138 | raise: function(err) {\r | |
139 | err = err || {};\r | |
140 | if (Ext.isString(err)) {\r | |
141 | err = { msg: err };\r | |
142 | }\r | |
143 | \r | |
144 | var me = this,\r | |
145 | method = me.raise.caller,\r | |
146 | msg, name;\r | |
147 | \r | |
148 | if (method === Ext.raise) {\r | |
149 | method = method.caller;\r | |
150 | }\r | |
151 | if (method) {\r | |
152 | if (!err.sourceMethod && (name = method.$name)) {\r | |
153 | err.sourceMethod = name;\r | |
154 | }\r | |
155 | if (!err.sourceClass && (name = method.$owner) && (name = name.$className)) {\r | |
156 | err.sourceClass = name;\r | |
157 | }\r | |
158 | }\r | |
159 | \r | |
160 | if (me.handle(err) !== true) {\r | |
161 | msg = toString.call(err);\r | |
162 | \r | |
163 | //<debug>\r | |
164 | Ext.log({\r | |
165 | msg: msg,\r | |
166 | level: 'error',\r | |
167 | dump: err,\r | |
168 | stack: true\r | |
169 | });\r | |
170 | //</debug>\r | |
171 | \r | |
172 | throw new Ext.Error(err);\r | |
173 | }\r | |
174 | },\r | |
175 | \r | |
176 | /**\r | |
177 | * Globally handle any Ext errors that may be raised, optionally providing custom logic to\r | |
178 | * handle different errors individually. Return true from the function to bypass throwing the\r | |
179 | * error to the browser, otherwise the error will be thrown and execution will halt.\r | |
180 | *\r | |
181 | * Example usage:\r | |
182 | *\r | |
183 | * Ext.Error.handle = function(err) {\r | |
184 | * if (err.someProperty == 'NotReallyAnError') {\r | |
185 | * // maybe log something to the application here if applicable\r | |
186 | * return true;\r | |
187 | * }\r | |
188 | * // any non-true return value (including none) will cause the error to be thrown\r | |
189 | * }\r | |
190 | *\r | |
191 | * @param {Object} err The error being raised. It will contain any attributes that were originally\r | |
192 | * raised with it, plus properties about the method and class from which the error originated\r | |
193 | * (if raised from a class that uses the Class System).\r | |
194 | * @static\r | |
195 | */\r | |
196 | handle: function () {\r | |
197 | return this.ignore;\r | |
198 | }\r | |
199 | });\r | |
200 | })();\r | |
201 | \r | |
202 | /**\r | |
203 | * Create a function that will throw an error if called (in debug mode) with a message that\r | |
204 | * indicates the method has been removed.\r | |
205 | * @param {String} suggestion Optional text to include in the message (a workaround perhaps).\r | |
206 | * @return {Function} The generated function.\r | |
207 | * @private\r | |
208 | */\r | |
209 | Ext.deprecated = function (suggestion) {\r | |
210 | //<debug>\r | |
211 | if (!suggestion) {\r | |
212 | suggestion = '';\r | |
213 | }\r | |
214 | \r | |
215 | function fail () {\r | |
216 | Ext.raise('The method "' + fail.$owner.$className + '.' + fail.$name +\r | |
217 | '" has been removed. ' + suggestion);\r | |
218 | }\r | |
219 | \r | |
220 | return fail;\r | |
221 | //</debug>\r | |
222 | return Ext.emptyFn;\r | |
223 | };\r | |
224 | \r | |
225 | /**\r | |
226 | * Raise an error that can include additional data and supports automatic console logging\r | |
227 | * if available. You can pass a string error message or an object with the `msg` attribute\r | |
228 | * which will be used as the error message. The object can contain any other name-value\r | |
229 | * attributes (or objects) to be logged along with the error.\r | |
230 | *\r | |
231 | * Note that after displaying the error message a JavaScript error will ultimately be\r | |
232 | * thrown so that execution will halt.\r | |
233 | *\r | |
234 | * Example usage:\r | |
235 | *\r | |
236 | * Ext.raise('A simple string error message');\r | |
237 | *\r | |
238 | * // or...\r | |
239 | *\r | |
240 | * Ext.define('Ext.Foo', {\r | |
241 | * doSomething: function(option){\r | |
242 | * if (someCondition === false) {\r | |
243 | * Ext.raise({\r | |
244 | * msg: 'You cannot do that!',\r | |
245 | * option: option, // whatever was passed into the method\r | |
246 | * code: 100 // other arbitrary info\r | |
247 | * });\r | |
248 | * }\r | |
249 | * }\r | |
250 | * });\r | |
251 | *\r | |
252 | * @param {String/Object} err The error message string, or an object containing the\r | |
253 | * attribute "msg" that will be used as the error message. Any other data included in the\r | |
254 | * object will also be logged to the browser console, if available.\r | |
255 | * @method raise\r | |
256 | * @member Ext\r | |
257 | */\r | |
258 | Ext.raise = function () {\r | |
259 | Ext.Error.raise.apply(Ext.Error, arguments);\r | |
260 | };\r | |
261 | \r | |
262 | /*\r | |
263 | * This mechanism is used to notify the user of the first error encountered on the page. In\r | |
264 | * most cases errors go unobserved especially on IE. This mechanism pushes this information\r | |
265 | * to the status bar so that users don't miss it.\r | |
266 | */\r | |
267 | //<debug>\r | |
268 | (function () {\r | |
269 | if (typeof window === 'undefined') {\r | |
270 | return; // build system or some such environment...\r | |
271 | }\r | |
272 | \r | |
273 | var last = 0,\r | |
274 | // This method is called to notify the user of the current error status.\r | |
275 | notify = function() {\r | |
276 | var cnt = Ext.log && Ext.log.counters,\r | |
277 | n = cnt && (cnt.error + cnt.warn + cnt.info + cnt.log),\r | |
278 | msg;\r | |
279 | \r | |
280 | // Put log counters to the status bar (for most browsers):\r | |
281 | if (n && last !== n) {\r | |
282 | msg = [];\r | |
283 | if (cnt.error) {\r | |
284 | msg.push('Errors: ' + cnt.error);\r | |
285 | }\r | |
286 | if (cnt.warn) {\r | |
287 | msg.push('Warnings: ' + cnt.warn);\r | |
288 | }\r | |
289 | if (cnt.info) {\r | |
290 | msg.push('Info: ' + cnt.info);\r | |
291 | }\r | |
292 | if (cnt.log) {\r | |
293 | msg.push('Log: ' + cnt.log);\r | |
294 | }\r | |
295 | window.status = '*** ' + msg.join(' -- ');\r | |
296 | last = n;\r | |
297 | }\r | |
298 | };\r | |
299 | \r | |
300 | // window.onerror sounds ideal but it prevents the built-in error dialog from doing\r | |
301 | // its (better) thing.\r | |
302 | setInterval(notify, 1000);\r | |
303 | }());\r | |
304 | //</debug>\r |