如何构建 AngularJS 应用程序?
How to structure AngularJS app?
我正计划使用 AngularJS 开发单页应用程序。但是我不确定如何最好地构建它。
我想用一个控制器来包装内容。该控制器将保留用户的详细信息,例如如果用户已登录,用户名等。它将包装动态加载的 ng-view
和其中的指令。
我不确定的是如何处理异步调用。例如,如果我加载其中一个视图并且其中将有 3 个指令,则结构可能与此类似:
- wrapping controller
-- ng-view (here views are loaded dynamically). When view loaded it will contains e.g.:
--- some directive that needs information about user
--- another directive that needs information about user
--- yet another directive that needs information about user
这些指令中的每一个都需要用户是否登录的信息,因此这些指令中的每一个都必须对后端进行 $http
调用以查明用户是否登录。这意味着将有 3 个后端调用,但只有一个是有意义的。
但是,如果我将此功能移动到包装控制器,它将从后端请求登录信息并按应有的方式存储。然而,由于这个对服务器的 $http 请求是异步的,最初在页面内加载的指令将不知道用户是否登录,并且将无法正确显示自身。我可能会得到这样的结果:
- 页面加载
- 包装控制器执行并异步调用后端以查明用户是否登录
- 特定视图已加载。它从 wrapping controller 获取信息,发现此时用户没有登录(wrapping controller 还没有从后端接收信息)。指令重定向到主页。
- wrapping controller 最终从服务器接收到用户已登录的信息,但指令已将用户重定向到主页。
我希望我的解释有道理。我确信在这种情况下可以使用通用模式。任何建议将不胜感激。
我强烈建议您查看 github 上可用的经过验证的全栈解决方案,例如 meanjs. Their open-source code。
当应用程序 header 在 meanjs 中加载时,它是这样的:
angular.module('core').controller('HeaderController', ['$scope', 'Authentication',
function($scope, Authentication) {
$scope.authentication = Authentication;
}
]);
导航菜单中的控制器调用身份验证服务,并将其添加到范围。
there will be 3 calls to backend but it would make sense to have only one
实际上,您可以从页面控制器调用一项服务。然后任何需要身份验证信息的指令都可以从页面控制器继承。
任何指令都可以这样做,包括身份验证服务以获取身份验证信息。
一些指令将 show/hide 取决于用户是否经过身份验证,例如:
<ul data-ng-hide="authentication.user">
如果您使用 ui-router,您可以在路由中使用 resolve 在显示您的视图之前捕获身份验证信息。
particular view is loaded. It grabs information from wrapping controller and sees that user is not logged in at this point (wrapping controller did not receive information from backend just yet). Directive redirects to homepage.
或者您可以等到您的承诺得到解决,然后 return 提供有关用户是否通过身份验证的信息。同时,您可以显示徽标、旋转器、空白页...
我正计划使用 AngularJS 开发单页应用程序。但是我不确定如何最好地构建它。
我想用一个控制器来包装内容。该控制器将保留用户的详细信息,例如如果用户已登录,用户名等。它将包装动态加载的 ng-view
和其中的指令。
我不确定的是如何处理异步调用。例如,如果我加载其中一个视图并且其中将有 3 个指令,则结构可能与此类似:
- wrapping controller
-- ng-view (here views are loaded dynamically). When view loaded it will contains e.g.:
--- some directive that needs information about user
--- another directive that needs information about user
--- yet another directive that needs information about user
这些指令中的每一个都需要用户是否登录的信息,因此这些指令中的每一个都必须对后端进行 $http
调用以查明用户是否登录。这意味着将有 3 个后端调用,但只有一个是有意义的。
但是,如果我将此功能移动到包装控制器,它将从后端请求登录信息并按应有的方式存储。然而,由于这个对服务器的 $http 请求是异步的,最初在页面内加载的指令将不知道用户是否登录,并且将无法正确显示自身。我可能会得到这样的结果:
- 页面加载
- 包装控制器执行并异步调用后端以查明用户是否登录
- 特定视图已加载。它从 wrapping controller 获取信息,发现此时用户没有登录(wrapping controller 还没有从后端接收信息)。指令重定向到主页。
- wrapping controller 最终从服务器接收到用户已登录的信息,但指令已将用户重定向到主页。
我希望我的解释有道理。我确信在这种情况下可以使用通用模式。任何建议将不胜感激。
我强烈建议您查看 github 上可用的经过验证的全栈解决方案,例如 meanjs. Their open-source code。
当应用程序 header 在 meanjs 中加载时,它是这样的:
angular.module('core').controller('HeaderController', ['$scope', 'Authentication',
function($scope, Authentication) {
$scope.authentication = Authentication;
}
]);
导航菜单中的控制器调用身份验证服务,并将其添加到范围。
there will be 3 calls to backend but it would make sense to have only one
实际上,您可以从页面控制器调用一项服务。然后任何需要身份验证信息的指令都可以从页面控制器继承。
任何指令都可以这样做,包括身份验证服务以获取身份验证信息。
一些指令将 show/hide 取决于用户是否经过身份验证,例如:
<ul data-ng-hide="authentication.user">
如果您使用 ui-router,您可以在路由中使用 resolve 在显示您的视图之前捕获身份验证信息。
particular view is loaded. It grabs information from wrapping controller and sees that user is not logged in at this point (wrapping controller did not receive information from backend just yet). Directive redirects to homepage.
或者您可以等到您的承诺得到解决,然后 return 提供有关用户是否通过身份验证的信息。同时,您可以显示徽标、旋转器、空白页...