回文集目录:JHipster一知半解
docs目录
这个目录是最简单的一个组件,内嵌了一个iframe,显示swagger。
<iframe src="swagger-ui/index.html" width="100%" height="900" seamless
target="_top" title="Swagger UI" class="border-0"></iframe>
health目录
health.service.ts
与spring原生的management/health进行通讯,获取系统的健康信息。
值得注意的是addHealthObject(),内部还有transformHealthData()对返还的数据进行解析。
JhiHealthModalComponent组件
显示健康信息详情的模态框,对硬盘容量数据有特殊处理。
JhiHealthCheckComponent组件
根据后端数据返还值,显示当前系统状态。有通过refresh(),重新获取和showHealth()跳出详细模态框的两个方法。
refresh() {
//先修改自己的状态
this.updatingHealth = true;
//调用通讯接口获取健康信息
this.healthService.checkHealth().subscribe((health) => {
this.healthData = this.healthService.transformHealthData(health);
this.updatingHealth = false;
}, (error) => {
//如果报错,就显示错误信息
if (error.status === 503) {
this.healthData = this.healthService.transformHealthData(error.json());
this.updatingHealth = false;
}
});
}
//通过modalService弹出模态框
showHealth(health: any) {
const modalRef = this.modalService.open(JhiHealthModalComponent);
//向模态框赋值的方法要通过componentInstance
modalRef.componentInstance.currentHealth = health;
//由于只是显示,并没有额外操作
modalRef.result.then((result) => {
// Left blank intentionally, nothing to do here
}, (reason) => {
// Left blank intentionally, nothing to do here
});
}
logs目录
与web.rest.LogsResource对应,内部使用了logback的LoggerContext修改日志等级。
显示所有log,和修改的html如下:
<tr *ngFor="let logger of (loggers | pureFilter:filter:'name' | orderBy:orderProp:reverse)">
<!--利用slice管道截断日志名-->
<td><small>{{logger.name | slice:0:140}}</small></td>
<td>
<!--利用ngClass显示当前等级,默认用btn-light的样式-->
<!--每个等级都是一个按钮,点击时候触发changeLevel()方法-->
<button (click)="changeLevel(logger.name, 'TRACE')" [ngClass]="(logger.level=='TRACE') ? 'btn-danger' : 'btn-light'" class="btn btn-sm">TRACE</button>
<button (click)="changeLevel(logger.name, 'DEBUG')" [ngClass]="(logger.level=='DEBUG') ? 'btn-warning' : 'btn-light'" class="btn btn-sm">DEBUG</button>
<button (click)="changeLevel(logger.name, 'INFO')" [ngClass]="(logger.level=='INFO') ? 'btn-info' : 'btn-light'" class="btn btn-sm">INFO</button>
<button (click)="changeLevel(logger.name, 'WARN')" [ngClass]="(logger.level=='WARN') ? 'btn-success' : 'btn-light'" class="btn btn-sm">WARN</button>
<button (click)="changeLevel(logger.name, 'ERROR')" [ngClass]="(logger.level=='ERROR') ? 'btn-primary' : 'btn-light'" class="btn btn-sm">ERROR</button>
</td>
</tr>
metrics目录
显示spring提供的统计信息,与spring原生的management/metrics和management/dump交互,其中现场状态是在模态框显示的。这个还是推荐jvm自带的jvisual。
user-management目录
用户管理是该模块最复杂的一个页面,包含用户增删改查、激活/反激活、权限编辑。
user-modal.service.ts
由于用户管理逻辑在UserService中,UserModalService的作用是弹出交互的模态框
export class UserModalService {
private ngbModalRef: NgbModalRef;
//注入modalService,路由,用户服务
constructor(
private modalService: NgbModal,
private router: Router,
private userService: UserService
) {
this.ngbModalRef = null;
}
open(component: Component, id?: number | any): Promise<NgbModalRef> {
return new Promise<NgbModalRef>((resolve, reject) => {
const isOpen = this.ngbModalRef !== null;
if (isOpen) {
resolve(this.ngbModalRef);
}
//根据是否有传入Id信息,显示不同的内容,
if (id) {
this.userService.find(id).subscribe((user) => {
this.ngbModalRef = this.userModalRef(component, user);
resolve(this.ngbModalRef);
});
} else {
// setTimeout used as a workaround for getting ExpressionChangedAfterItHasBeenCheckedError
//注册页面需要异步打开。
setTimeout(() => {
this.ngbModalRef = this.userModalRef(component, new User());
resolve(this.ngbModalRef);
}, 0);
}
});
}
//内部方法,应该加个private
userModalRef(component: Component, user: User): NgbModalRef {
const modalRef = this.modalService.open(component, { size: 'lg', backdrop: 'static'});
modalRef.componentInstance.user = user;
modalRef.result.then((result) => {
//这里的模态返回就有操作了,调用路由的navigate(),进行用户信息的跳转,并且清空ngbModalRef。
this.router.navigate([{ outlets: { popup: null }}], { replaceUrl: true, queryParamsHandling: 'merge' });
this.ngbModalRef = null;
}, (reason) => {
this.router.navigate([{ outlets: { popup: null }}], { replaceUrl: true, queryParamsHandling: 'merge' });
this.ngbModalRef = null;
});
return modalRef;
}
user-management.component.ts
export class UserMgmtComponent implements OnInit, OnDestroy {
//当前账号
currentAccount: any;
//记录查询回来的所有用户
users: User[];
error: any;
success: any;
routeData: any;
links: any;
totalItems: any;
queryCount: any;
itemsPerPage: any;
page: any;
predicate: any;
previousPage: any;
reverse: any;
constructor(
private userService: UserService,
private alertService: JhiAlertService,
private principal: Principal,
private parseLinks: JhiParseLinks,
private activatedRoute: ActivatedRoute,
private router: Router,
private eventManager: JhiEventManager
) {
this.itemsPerPage = ITEMS_PER_PAGE;
//从当前的URL信息中获取路由信息
this.routeData = this.activatedRoute.data.subscribe((data) => {
this.page = data['pagingParams'].page;
this.previousPage = data['pagingParams'].page;
this.reverse = data['pagingParams'].ascending;
this.predicate = data['pagingParams'].predicate;
});
}
//初始化时候,记录当前用户,加载第一页用户列表,注册用户变动通知
ngOnInit() {
this.principal.identity().then((account) => {
this.currentAccount = account;
this.loadAll();
this.registerChangeInUsers();
});
}
//销毁时候要反注册
ngOnDestroy() {
this.routeData.unsubscribe();
}
registerChangeInUsers() {
this.eventManager.subscribe('userListModification', (response) => this.loadAll());
}
//设置激活,如果成功,重新加载页面数据
setActive(user, isActivated) {
user.activated = isActivated;
this.userService.update(user).subscribe(
(response) => {
if (response.status === 200) {
this.error = null;
this.success = 'OK';
this.loadAll();
} else {
this.success = null;
this.error = 'ERROR';
}
});
}
//调用userService查询
loadAll() {
this.userService.query({
page: this.page - 1,
size: this.itemsPerPage,
sort: this.sort()}).subscribe(
(res: ResponseWrapper) => this.onSuccess(res.json, res.headers),
(res: ResponseWrapper) => this.onError(res.json)
);
}
trackIdentity(index, item: User) {
return item.id;
}
//排序回调方法,默认根据ID排序,与sort指令对应
sort() {
const result = [this.predicate + ',' + (this.reverse ? 'asc' : 'desc')];
if (this.predicate !== 'id') {
result.push('id');
}
return result;
}
loadPage(page: number) {
if (page !== this.previousPage) {
this.previousPage = page;
this.transition();
}
}
//重新定向到用户管理页面
transition() {
this.router.navigate(['/user-management'], {
queryParams: {
page: this.page,
sort: this.predicate + ',' + (this.reverse ? 'asc' : 'desc')
}
});
this.loadAll();
}
//查询成功时候的回调
private onSuccess(data, headers) {
this.links = this.parseLinks.parse(headers.get('link'));
this.totalItems = headers.get('X-Total-Count');
this.queryCount = this.totalItems;
this.users = data;
}
//查询失败时候的回调
private onError(error) {
this.alertService.error(error.error, error.message, null);
}
}
user-management.component.html
<div>
<h2>
<span jhiTranslate="userManagement.home.title">Users</span>
<!--这里制定新建用户的弹出框的outlet为‘popup’,直接在html定义router,这样也行-->
<button class="btn btn-primary float-right jh-create-entity" [routerLink]="['/', { outlets: { popup: ['user-management-new'] } }]">
<span class="fa fa-plus"></span> <span jhiTranslate="userManagement.home.createLabel">Create a new User</span>
</button>
</h2>
<jhi-alert></jhi-alert>
<div class="table-responsive" *ngIf="users">
<table class="table table-striped">
<thead>
<!--表头,与自定义的jhisort和jhiSortBy指令配合,完成排序工作-->
<tr jhiSort [(predicate)]="predicate" [(ascending)]="reverse" [callback]="transition.bind(this)">
<th jhiSortBy="id"><span jhiTranslate="global.field.id">ID</span> <span class="fa fa-sort"></span></th>
<th jhiSortBy="login"><span jhiTranslate="userManagement.login">Login</span> <span class="fa fa-sort"></span></th>
<th jhiSortBy="email"><span jhiTranslate="userManagement.email">Email</span> <span class="fa fa-sort"></span></th>
<th></th>
<th jhiSortBy="langKey"> <span jhiTranslate="userManagement.langKey">Lang Key</span> <span class="fa fa-sort"></span></th>
<th><span jhiTranslate="userManagement.profiles">Profiles</span></th>
<th jhiSortBy="createdDate"><span jhiTranslate="userManagement.createdDate">Created Date</span> <span class="fa fa-sort"></span></th>
<th jhiSortBy="lastModifiedBy"><span jhiTranslate="userManagement.lastModifiedBy">Last Modified By</span> <span class="fa fa-sort"></span></th>
<th jhiSortBy="lastModifiedDate"><span jhiTranslate="userManagement.lastModifiedDate">Last Modified Date</span> <span class="fa fa-sort"></span></th>
<th></th>
</tr>
</thead>
<!--循环读取用户信息,显示在表格里面-->
<tbody *ngIf ="users">
<tr *ngFor="let user of users; trackBy: trackIdentity">
<td><a [routerLink]="['../user-management', user.login]">{{user.id}}</a></td>
<td>{{user.login}}</td>
<td>{{user.email}}</td>
<td>
<button class="btn btn-danger btn-sm" (click)="setActive(user, true)" *ngIf="!user.activated"
jhiTranslate="userManagement.deactivated">Deactivated</button>
<button class="btn btn-success btn-sm" (click)="setActive(user, false)" *ngIf="user.activated"
[disabled]="currentAccount.login === user.login" jhiTranslate="userManagement.activated">Activated</button>
</td>
<td>{{user.langKey}}</td>
<td>
<div *ngFor="let authority of user.authorities">
<span class="badge badge-info">{{ authority }}</span>
</div>
</td>
<td>{{user.createdDate | date:'dd/MM/yy HH:mm'}}</td>
<td>{{user.lastModifiedBy}}</td>
<td>{{user.lastModifiedDate | date:'dd/MM/yy HH:mm'}}</td>
<td class="text-right">
<div class="btn-group flex-btn-group-container">
<button type="submit"
[routerLink]="['../user-management', user.login]"
class="btn btn-info btn-sm">
<span class="fa fa-eye"></span>
<span class="d-none d-md-inline" jhiTranslate="entity.action.view">View</span>
</button>
<!--直接定义route,弹出编辑框-->
<button type="submit"
[routerLink]="['/', { outlets: { popup: 'user-management/'+ user.login + '/edit'} }]"
replaceUrl="true"
queryParamsHandling="merge"
class="btn btn-primary btn-sm">
<span class="fa fa-pencil"></span>
<span class="d-none d-md-inline" jhiTranslate="entity.action.edit">Edit</span>
</button>
<!--直接定义route,弹出删除确认框-->
<button type="submit"
[routerLink]="['/', { outlets: { popup: 'user-management/'+ user.login + '/delete'} }]"
replaceUrl="true"
queryParamsHandling="merge"
class="btn btn-danger btn-sm" [disabled]="currentAccount.login === user.login">
<span class="fa fa-remove"></span>
<span class="d-none d-md-inline" jhiTranslate="entity.action.delete">Delete</span>
</button>
</div>
</td>
</tr>
</tbody>
</table>
</div>
<div *ngIf="users">
<div class="row justify-content-center">
<jhi-item-count [page]="page" [total]="queryCount" [itemsPerPage]="itemsPerPage"></jhi-item-count>
</div>
<div class="row justify-content-center">
<ngb-pagination [collectionSize]="totalItems" [(page)]="page" [pageSize]="itemsPerPage" [maxSize]="5" [rotate]="true" [boundaryLinks]="true" (pageChange)="loadPage(page)"></ngb-pagination>
</div>
</div>
</div>
网友评论