【问题标题】:render 404 page without redirecting in angular js渲染 404 页面而不在 Angular js 中重定向
【发布时间】:2015-03-26 03:03:06
【问题描述】:

我在 AngularJS 中使用 ui.router 和 ngResource,我的问题是:

如何在不重定向的情况下呈现 404,例如,用户键入 http://www.example.com/wrong-page-name,他应该只看到 404 页面,并且 URL 不应该改变。

目前我是这样做的,但它会重定向

    angular.module('app')
   .run(['$rootScope', '$state', function($rootScope, $state) {

            $rootScope.$on('$stateChangeError', function(event, toState, toParams, fromState, fromParams, error) {
                if(error.status === 404) {
                    $state.go('innerPages.page', {slug:"not-found"});
                }
            });
    })
    .config(['$stateProvider','$urlRouterProvider', function($stateProvider, $urlRouterProvider) {

            $stateProvider.state('innerPages.page', {
                url: ':slug',
                views : {
                    'content@':{
                        templateUrl : '...',
                        controller : 'pageController'
                    },
                    'pageHeader@' : {
                        templateUrl : "...",
                        controller : 'pageController'
                    }
                },
                resolve:{
                    page: ['pageService', '$stateParams', function (pageService, $stateParams) {
                        return pageService.get({slug:$stateParams.slug}).$promise;
                    }]
                }
            });

        }]);

感谢您的帮助!

【问题讨论】:

标签: angularjs http-status-code-404 angular-ui-router angular-resource


【解决方案1】:

为什么不直接显示 404 模板?

<any ng-view ng-class="{'hidden': notFound}"></any>
<div class="not-found-template hidden" ng-class="{'hidden': !notFound}">
  <h2>Not Found!</h2>
</div>

对于 css:

.hidden
{
  display: none !important;
}

并添加错误处理服务(可选)

 angular.module('app').service('Errors', function ($rootScope) {
  this.handle = function (error, status) {
    // not found
    switch (status) {
      case 404:
        alert('Sorry! the page was not found.');
        // This is the required line for showing 404 template
        $rootScope.notFound = true;
        break;
      case 500:
        alert('Sorry! Error connecting to server.');
        break;
      case 403:
        $location.path('/login');
        break;
      default:
        alert('Sorry! Error connecting to server.');
    }
  }
});

【讨论】:

  • 为什么需要添加.hidden类?为什么不使用ng-show
【解决方案2】:

我想添加一个推荐的、更有条理的答案:

使用了$httpInterceptor 工厂记录的here(参见拦截器段落):

用于全局错误处理、身份验证或任何类型的 请求的同步或异步预处理或 响应的后处理

在通过您的应用的所有 HTTP 请求中。
更改 responseError 方法,如:

'responseError': function (error) {


  //hide any showing loader spinners
  loader.hide();


  // handle errors by type
  var status = error.status;
  switch (status) {


    // here you can show 404 templates and go more further
    case 404:
      $rootScope.flags.errorCode = 404;
      break;


    // here I check if error has messages or it's an internal server error
    case 500:
      try {
        if (!error.data.success && typeof error.data.data.message != 'undefined') {
          Notification.error(error.data.message);
        } else {
          $rootScope.flags.errorCode = 500;
        }
      } catch (e) {
        $rootScope.flags.errorCode = 500;
      }
      break;


    // authenticating for actions that un-authenticated uses can not do, like staring or commenting
    case 401:
      Popup.show('login');
      break;


    // showing notification for any other error types
    default:
      Notification.error('Sorry! Error connecting to server.');
  }
  return $q.reject(error);
}

关于上面的代码:

  1. Loader 是我的自定义服务,用于显示 loader-spinner,可能有 overlayonElement 和任何其他必需的类型。
  2. Notification 也是一个自定义服务,用于通知客户端请求的结果。
  3. 可以使用固定到$rootScopeflags 对象控制任何错误模板。

【讨论】:

  • 这不是一个好的解决方案。您不想在从服务器获得的每个 404 响应中重定向到 404 页面。在某些情况下,仅显示错误消息就足够了,具体取决于未找到的资源。
猜你喜欢
  • 1970-01-01
  • 2015-03-03
  • 2020-07-01
  • 2016-12-24
  • 1970-01-01
  • 2010-12-06
  • 2018-02-07
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多