Merge pull request #4785 from FinnStutzenstein/historyQuicklink
Quicklink to history (closes #4777)
This commit is contained in:
commit
b71e73fe7f
@ -112,4 +112,29 @@ export class CollectionStringMapperService {
|
||||
public getAllRepositories(): BaseRepository<any, any, any>[] {
|
||||
return Object.values(this.collectionStringMapping).map((types: CollectionStringMappedTypes) => types[2]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Validates the given element id. It must have the form `<collection>:<id>`, with
|
||||
* <collection> being a registered collection and the id a valid integer greater then 0.
|
||||
*
|
||||
* @param elementId The element id.
|
||||
* @returns true, if the element id is valid.
|
||||
*/
|
||||
public isElementIdValid(elementId: any): boolean {
|
||||
if (!elementId || typeof elementId !== 'string') {
|
||||
return false;
|
||||
}
|
||||
|
||||
const splitted = elementId.split(':');
|
||||
if (splitted.length !== 2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
const id = parseInt(splitted[1], 10);
|
||||
if (isNaN(id) || id <= 0) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return Object.keys(this.collectionStringMapping).some(collection => collection === splitted[0]);
|
||||
}
|
||||
}
|
||||
|
@ -38,6 +38,13 @@ export abstract class BaseViewModel<M extends BaseModel = any>
|
||||
return this._collectionString;
|
||||
}
|
||||
|
||||
/**
|
||||
* @returns the element id of the model
|
||||
*/
|
||||
public get elementId(): string {
|
||||
return `${this.collectionString}:${this.id}`;
|
||||
}
|
||||
|
||||
public getTitle: () => string;
|
||||
public getListTitle: () => string;
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
import { Component, OnInit } from '@angular/core';
|
||||
import { MatSnackBar, MatTableDataSource } from '@angular/material';
|
||||
import { Router } from '@angular/router';
|
||||
import { Router, ActivatedRoute } from '@angular/router';
|
||||
import { Title } from '@angular/platform-browser';
|
||||
|
||||
import { TranslateService } from '@ngx-translate/core';
|
||||
@ -21,6 +21,7 @@ import { MotionRepositoryService } from 'app/core/repositories/motions/motion-re
|
||||
import { BaseViewModel } from 'app/site/base/base-view-model';
|
||||
import { Motion } from 'app/shared/models/motions/motion';
|
||||
import { PromptService } from 'app/core/ui-services/prompt.service';
|
||||
import { CollectionStringMapperService } from 'app/core/core-services/collection-string-mapper.service';
|
||||
|
||||
/**
|
||||
* A list view for the history.
|
||||
@ -40,10 +41,6 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
|
||||
public dataSource: MatTableDataSource<History> = new MatTableDataSource<History>();
|
||||
|
||||
public get isSuperAdmin(): boolean {
|
||||
return this.operator.isSuperAdmin();
|
||||
}
|
||||
|
||||
public pageSizes = [50, 100, 150, 200, 250];
|
||||
|
||||
/**
|
||||
@ -67,6 +64,10 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
return this.modelSelectForm.controls.model.value;
|
||||
}
|
||||
|
||||
public get isSuperAdmin(): boolean {
|
||||
return this.operator.isSuperAdmin();
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor for the history list component
|
||||
*
|
||||
@ -89,7 +90,9 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
private http: HttpService,
|
||||
private formBuilder: FormBuilder,
|
||||
private motionRepo: MotionRepositoryService,
|
||||
private promptService: PromptService
|
||||
private promptService: PromptService,
|
||||
private activatedRoute: ActivatedRoute,
|
||||
private collectionMapper: CollectionStringMapperService
|
||||
) {
|
||||
super(titleService, translate, matSnackBar);
|
||||
|
||||
@ -99,7 +102,15 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
this.collectionObserver = this.motionRepo.getViewModelListBehaviorSubject();
|
||||
|
||||
this.modelSelectForm.controls.model.valueChanges.subscribe((id: number) => {
|
||||
this.queryElementId(this.currentCollection, id);
|
||||
const elementId = `${this.currentCollection}:${id}`;
|
||||
this.queryByElementId(elementId);
|
||||
|
||||
// Update the URL.
|
||||
this.router.navigate([], {
|
||||
relativeTo: this.activatedRoute,
|
||||
queryParams: { element: elementId },
|
||||
replaceUrl: true
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
@ -136,6 +147,18 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
.indexOf(filter) >= 0
|
||||
);
|
||||
};
|
||||
|
||||
// If an element id is given, validate it and update the view.
|
||||
const params = this.activatedRoute.snapshot.queryParams;
|
||||
if (this.collectionMapper.isElementIdValid(params.element)) {
|
||||
this.queryByElementId(params.element);
|
||||
this.modelSelectForm.patchValue(
|
||||
{
|
||||
model: parseInt(params.element.split(':')[1], 10)
|
||||
},
|
||||
{ emitEvent: false }
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
@ -201,7 +224,7 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
|
||||
public refresh(): void {
|
||||
if (this.currentCollection && this.currentModelId) {
|
||||
this.queryElementId(this.currentCollection, this.currentModelId);
|
||||
this.queryByElementId(`${this.currentCollection}:${this.currentModelId}`);
|
||||
}
|
||||
}
|
||||
|
||||
@ -238,12 +261,12 @@ export class HistoryListComponent extends BaseViewComponent implements OnInit {
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the data source to the request element id given by the collection string and the id.
|
||||
* Sets the data source to the requested element id.
|
||||
*/
|
||||
private async queryElementId(collectionString: string, id: number): Promise<void> {
|
||||
private async queryByElementId(elementId: string): Promise<void> {
|
||||
const historyData = await this.http.get<History[]>(`${environment.urlPrefix}/core/history/information/`, null, {
|
||||
type: 'element',
|
||||
value: `${collectionString}:${id}`
|
||||
value: elementId
|
||||
});
|
||||
this.dataSource.data = historyData.map(data => new History(data));
|
||||
}
|
||||
|
@ -101,6 +101,13 @@
|
||||
<span translate>Show entire motion text</span>
|
||||
</button>
|
||||
|
||||
<button mat-menu-item *osPerms="'core.can_see_history'" [routerLink]="['/history']" [queryParams]="{element: motion.elementId}">
|
||||
<mat-icon>history</mat-icon>
|
||||
<span translate>
|
||||
History
|
||||
</span>
|
||||
</button>
|
||||
|
||||
<div *ngIf="perms.isAllowed('manage')">
|
||||
<mat-divider></mat-divider>
|
||||
<!-- Delete -->
|
||||
|
@ -504,7 +504,7 @@ class HistoryInformationView(utils_views.APIView):
|
||||
"""
|
||||
Checks permission and parses query parameters.
|
||||
"""
|
||||
if not has_perm(self.request.user, "users.can_see_history"):
|
||||
if not has_perm(self.request.user, "core.can_see_history"):
|
||||
self.permission_denied(self.request)
|
||||
type = self.request.query_params.get("type")
|
||||
value = self.request.query_params.get("value")
|
||||
|
Loading…
Reference in New Issue
Block a user