/app
- app.component.ts
- app.component.html (hide/show: menu bar)
- app.global.service.ts (Public varible LoginSuccess:boolean)
- main.ts
/student
- student.ts
- student.service.ts
- student.component.ts
- student.component.html
/security
- login.component.ts (LoginSuccess = true)
- login.component.html
在我的Angular2应用程序中,我有一个简单的需求,我想根据登录成功显示隐藏菜单栏。为此,我创建了一个只有LoginSuccess布尔变量的服务,我将在登录组件上设置该服务,并将在app.component.html上用于[hidden]=LoginSuccess
导航标记。
我面临的问题是,即使注入app.global.service.ts
constructor
app.component.ts & login.component.ts
的{{1}}值不存在,并且每个构造函数都创建了app.global.service.ts
的新对象。
问题:如何通过服务在应用程序中保持单一值。在Angular2文档的某个地方,我确实读到了Injectable服务是单例。
答案 0 :(得分:28)
你应该在bootstrap提供GlobalService
,而不是每个组件:
bootstrap(AppComponent, [GlobalService])
@Component({
providers: [], // yes
// providers: [GlobalService], // NO.
})
class AppComponent {
constructor(private gs: GlobalService) {
// gs is instance of GlobalService created at bootstrap
}
}
这种方式GlobalService
将是单身人士。
有关更高级的方法,请参阅this answer。
答案 1 :(得分:7)
您应该app.component.ts
而不是在app.module.ts
内部进行提升,而是将服务注入app.component.ts
。
...
import { MusicService } from './Services/music-service';
@Component({
selector: 'app-root',
templateUrl: 'app.component.html',
providers: [MusicService],
...
})
export class AppComponent {
constructor(private MS: MusicService) {
}
...
这是基于当前的Angular2
版本。因此,在index.html
内,您应该<app-root>
加载AppComponent
。
现在要在任何其他组件中使用它,只需导入它:
import { MusicService } from './Services/music-service';
并初始化它:
constructor(private MS: MusicService) {
}
要点:
app.component.ts
app.component.ts
provider
答案 2 :(得分:4)
作为Saxsa,关键是在应用程序注入器中定义服务提供者,而不是在每个组件级别定义。注意不要两次定义服务提供者......否则你仍然会有单独的服务实例。
这样您就可以共享同一个服务实例。
由于Angular2的分层注入器,会发生此行为。有关详细信息,您可以查看以下问题:
答案 3 :(得分:4)
截至最终版本(Angular 2.0.0):
导入服务并将其注入provider数组中,如下所示:
import { GlobalService } from './app.global.service';
//further down:
@NgModule({
bootstrap: [ App ],
declarations: [
// Your components should go here
],
imports: [
// Your module imports should go here
],
providers: [
ENV_PROVIDERS // By Angular
// Your providers should go here, i.e.
GlobalService
]
});
答案 4 :(得分:0)
我只想补充一下,因为我在这一点上陷入困境,虽然我使用的是Singelton,但您还必须使用Angular路由策略:
你不能使用href =“../ my-route”
因为这会启动整个应用程序的新功能:
而你必须使用:routerLink =“../ my-route”
答案 5 :(得分:0)
从 Angular 6.0 开始,创建单例服务的首选方法是在服务上指定应在应用程序根目录中提供的服务。这是通过在服务的providedIn
装饰器上将root
设置为@Injectable
来完成的:
import { Injectable } from '@angular/core';
@Injectable({
providedIn: 'root',
})
export class UserService {
}