使用 amd 和 requirejs 在 knockout spa 中进行错误处理
error handling in knockout spa using amd and requirejs
所以我有一个基于 Steve Sandersons SPA template 的相当大的单页应用程序。自定义绑定处理程序、验证等一切正常。
我们需要使用 XMLHttpRequests、Session 和 Local 存储以及其他一些没有普遍支持的库(jquery 2.0 等)。我有一个处理身份并公开一些服务的核心模块,这两者都依赖于这些功能。这是在用户第一次访问页面时加载的。
我对旧版浏览器有一个问题,其中 a) 它们不支持正在加载的某些模块,因此它们在调用 onload 函数之前抛出错误,或者 b) 它调用了 onload 函数但它们没有不支持浏览器功能,所以我需要自己引发异常并以某种方式处理它。
示例:IE8 抛出“对象不支持 属性 或方法 'addEventListener'”(jquery 错误)并且 IE9 不支持我需要的一切,所以我抛出一个自定义错误。
define('core', ['jquery', 'browser'], function($, browser) {
if(!browser.hasFullSupport) {
throw new Error('Update your browser');
}
// aload of gubbins that requires sessionStorage etc
return {
identity: identity,
serviceA: serviceA,
serviceB: serviceB
}
}, function(err) {
// doesn't catch the ie8 error here
});
我试过设置 window.onerror 但它在不同浏览器版本中的工作方式不同,在某些浏览器版本中我无法正确捕获错误消息,我只得到 'Script Error'.
我知道我可以为模块定义添加错误事件处理程序,但它不会捕获我遇到的错误。
我见过有人用
requirejs.onError = function(err) {
// something here
}
但是我正在使用 requirejs gulp 捆绑器,我看不到这个对象会暴露在哪里(如果有的话)
var require = {
baseUrl: ".",
paths: {
"modernizr": "bower_modules/modernizr/modernizr",
"browser": "app/browser-detect",
"crossroads": "bower_modules/crossroads/dist/crossroads.min",
"hasher": "bower_modules/hasher/dist/js/hasher.min",
"jquery": "bower_modules/jquery/dist/jquery.min",
....
// gulpfile
var requireJsRuntimeConfig = vm.runInNewContext(fs.readFileSync('src/app/require.config.js') + '; require;');
requireJsOptimizerConfig = merge(requireJsRuntimeConfig, {
out: 'scripts.js',
baseUrl: './src',
name: 'app/startup',
paths: {
requireLib: 'bower_modules/requirejs/require'
},
include: [
'requireLib',
'components/nav-bar/nav-bar',
.....
gulp.task('js', function () {
return rjs(requireJsOptimizerConfig)
.pipe(uglify())
.pipe(gulp.dest('./dist/'));
});
有很多 components/pages,每个都可能引发错误,但我很想解决这个初始核心组件加载问题。我想区分错误(可能是浏览器太旧或不是由浏览器太旧引起)和我事先检测到它们太旧之间的区别,是否有一种使用此模板模型实现此目的的优雅方法?
我不想偏离模板太远,因为我不太熟悉 requirejs / gulp 等,但我愿意接受建议。
你自相矛盾:
We require the use of the XMLHttpRequests, Session and Local storage as well as some other libraries that don't have universal support (jquery 2.0 etc)
但是:
IE8 throws an 'Object doesn't support property or method 'addEventListener'' (jquery error) and IE9 Doesn't support everything I need so I throw a custom error.
您不能使用适用于较新浏览器的库和 HTML 5 功能,并期望旧浏览器仍能正常工作。不支持 IE 8 等旧版浏览器的库不会优雅地失败,因此您无法很好地处理失败。即使您找到了以某种方式规避这些错误的解决方法,您仍然需要定期在旧浏览器中测试它们,这违背了仅支持较新浏览器的意图。
所以我推荐你两种方法:
- 要么决定完全不支持旧版浏览器,只在最新的现代浏览器中测试该应用程序。您可以使用不再支持旧浏览器的现代版本的库,而完全不用担心旧浏览器。这取决于您的用户群的状态。或者:
- 将库降级为支持最低要求浏览器的版本,并继续使用它们开发应用程序。测试应用程序并修复旧浏览器中出现的所有错误。使用 polyfill,通过仿真在旧浏览器中启用 HTML 5 个新功能。
所以我有一个基于 Steve Sandersons SPA template 的相当大的单页应用程序。自定义绑定处理程序、验证等一切正常。
我们需要使用 XMLHttpRequests、Session 和 Local 存储以及其他一些没有普遍支持的库(jquery 2.0 等)。我有一个处理身份并公开一些服务的核心模块,这两者都依赖于这些功能。这是在用户第一次访问页面时加载的。
我对旧版浏览器有一个问题,其中 a) 它们不支持正在加载的某些模块,因此它们在调用 onload 函数之前抛出错误,或者 b) 它调用了 onload 函数但它们没有不支持浏览器功能,所以我需要自己引发异常并以某种方式处理它。
示例:IE8 抛出“对象不支持 属性 或方法 'addEventListener'”(jquery 错误)并且 IE9 不支持我需要的一切,所以我抛出一个自定义错误。
define('core', ['jquery', 'browser'], function($, browser) {
if(!browser.hasFullSupport) {
throw new Error('Update your browser');
}
// aload of gubbins that requires sessionStorage etc
return {
identity: identity,
serviceA: serviceA,
serviceB: serviceB
}
}, function(err) {
// doesn't catch the ie8 error here
});
我试过设置 window.onerror 但它在不同浏览器版本中的工作方式不同,在某些浏览器版本中我无法正确捕获错误消息,我只得到 'Script Error'.
我知道我可以为模块定义添加错误事件处理程序,但它不会捕获我遇到的错误。
我见过有人用
requirejs.onError = function(err) {
// something here
}
但是我正在使用 requirejs gulp 捆绑器,我看不到这个对象会暴露在哪里(如果有的话)
var require = {
baseUrl: ".",
paths: {
"modernizr": "bower_modules/modernizr/modernizr",
"browser": "app/browser-detect",
"crossroads": "bower_modules/crossroads/dist/crossroads.min",
"hasher": "bower_modules/hasher/dist/js/hasher.min",
"jquery": "bower_modules/jquery/dist/jquery.min",
....
// gulpfile
var requireJsRuntimeConfig = vm.runInNewContext(fs.readFileSync('src/app/require.config.js') + '; require;');
requireJsOptimizerConfig = merge(requireJsRuntimeConfig, {
out: 'scripts.js',
baseUrl: './src',
name: 'app/startup',
paths: {
requireLib: 'bower_modules/requirejs/require'
},
include: [
'requireLib',
'components/nav-bar/nav-bar',
.....
gulp.task('js', function () {
return rjs(requireJsOptimizerConfig)
.pipe(uglify())
.pipe(gulp.dest('./dist/'));
});
有很多 components/pages,每个都可能引发错误,但我很想解决这个初始核心组件加载问题。我想区分错误(可能是浏览器太旧或不是由浏览器太旧引起)和我事先检测到它们太旧之间的区别,是否有一种使用此模板模型实现此目的的优雅方法?
我不想偏离模板太远,因为我不太熟悉 requirejs / gulp 等,但我愿意接受建议。
你自相矛盾:
We require the use of the XMLHttpRequests, Session and Local storage as well as some other libraries that don't have universal support (jquery 2.0 etc)
但是:
IE8 throws an 'Object doesn't support property or method 'addEventListener'' (jquery error) and IE9 Doesn't support everything I need so I throw a custom error.
您不能使用适用于较新浏览器的库和 HTML 5 功能,并期望旧浏览器仍能正常工作。不支持 IE 8 等旧版浏览器的库不会优雅地失败,因此您无法很好地处理失败。即使您找到了以某种方式规避这些错误的解决方法,您仍然需要定期在旧浏览器中测试它们,这违背了仅支持较新浏览器的意图。
所以我推荐你两种方法:
- 要么决定完全不支持旧版浏览器,只在最新的现代浏览器中测试该应用程序。您可以使用不再支持旧浏览器的现代版本的库,而完全不用担心旧浏览器。这取决于您的用户群的状态。或者:
- 将库降级为支持最低要求浏览器的版本,并继续使用它们开发应用程序。测试应用程序并修复旧浏览器中出现的所有错误。使用 polyfill,通过仿真在旧浏览器中启用 HTML 5 个新功能。