83

在我的 Angular.js 应用程序中,我正在运行一些异步操作。在开始之前,我用模态 div 覆盖应用程序,然后一旦操作完成,我需要删除 div,无论操作是否成功。

目前我有这个:

LoadingOverlay.start(); 
Auth.initialize().then(function() {
    LoadingOverlay.stop();
}, function() {
    LoadingOverlay.stop(); // Code needs to be duplicated here
})

它工作得很好,但是我更喜欢像这个伪代码这样更干净的东西:

LoadingOverlay.start(); 
Auth.initialize().finally(function() { // *pseudo-code* - some function that is always executed on both failure and success.
    LoadingOverlay.stop();
})

我认为这是一个很常见的问题,所以我认为可以完成但在文档中找不到任何内容。知道是否可以做到吗?

4

4 回答 4

164

该功能已在此拉取请求中实现,现在是 AngularJS 的一部分。它最初被称为“always”,后来改名为finally,所以代码应该如下:

LoadingOverlay.start(); 
Auth.initialize().then(function() {
    // Success handler
}, function() {
    // Error handler
}).finally(function() {
    // Always execute this on both error and success
});

请注意,由于finally是保留关键字,因此可能需要将其设为字符串,以免在某些浏览器(例如 IE 和 Android 浏览器)上中断:

$http.get('/foo')['finally'](doSomething);
于 2013-05-23T14:23:10.133 回答
7

我正在使用 Umbraco 7.3.5 版后端和 AngularJS 1.1.5 版并找到了这个线程。当我实施批准的答案时,我得到了错误:

xxx(...).then(...).finally 不是函数

然而,起作用的是always. 如果使用旧版本 AngularJS 的其他人发现此线程并且无法finally使用此代码,请改用此代码

LoadingOverlay.start(); 
Auth.initialize().then(function() {
    // Success handler
}, function() {
    // Error handler
}).always(function() {
    // Always execute this on both error and success
});
于 2016-02-25T13:12:25.193 回答
2

对于那些不使用 angularJS 的人,如果您可以捕获错误(不确定 .finally() 是否会这样做),您可以使用 .catch().then() 来避免重复代码。

Promise.resolve()
  .catch(() => {})
  .then(() => console.log('finally'));

无论如何,catch() 最终可能对日志记录或其他清理有用。 https://jsfiddle.net/pointzerotwo/k4rb41a7/

于 2017-07-19T16:00:36.297 回答
1

我会使用 ngView 来呈现页面的内容,并在 $viewContentLoaded 事件上触发删除你的模式。有关该事件,请参阅http://docs.angularjs.org/api/ng.directive:ngView和有关 $on 事件侦听器的http://docs.angularjs.org/api/ng .$rootScope.Scope。

于 2013-04-17T08:31:19.097 回答