Merge branch 'dmp-refactoring' of https://code-repo.d4science.org/MaDgiK-CITE/argos into dmp-refactoring

This commit is contained in:
Sofia Papacharalampous 2024-06-06 13:48:34 +03:00
commit e9a59671ea
7 changed files with 49 additions and 6 deletions

View File

@ -308,4 +308,14 @@ public class ErrorThesaurusProperties {
public void setImportDescriptionWithoutDmpDescriptionTemplate(ErrorDescription importDescriptionWithoutDmpDescriptionTemplate) {
this.importDescriptionWithoutDmpDescriptionTemplate = importDescriptionWithoutDmpDescriptionTemplate;
}
private ErrorDescription duplicateDmpUser;
public ErrorDescription getDuplicateDmpUser() {
return duplicateDmpUser;
}
public void setDuplicateDmpUser(ErrorDescription duplicateDmpUser) {
this.duplicateDmpUser = duplicateDmpUser;
}
}

View File

@ -768,7 +768,9 @@ public class DmpServiceImpl implements DmpService {
this.authorizationService.authorizeAtLeastOneForce(List.of(this.authorizationContentResolver.dmpAffiliation(dmpId)), Permission.AssignDmpUsers);
if (!disableDelete && (model == null || model.stream().noneMatch(x-> x.getUser() != null && DmpUserRole.Owner.equals(x.getRole())))) throw new MyApplicationException("At least one owner required");
this.checkDuplicateDmpUser(model);
DmpEntity dmpEntity = this.entityManager.find(DmpEntity.class, dmpId, true);
if (dmpEntity == null) throw new MyNotFoundException(this.messageSource.getMessage("General_ItemNotFound", new Object[]{dmpId, Dmp.class.getSimpleName()}, LocaleContextHolder.getLocale()));
@ -812,6 +814,20 @@ public class DmpServiceImpl implements DmpService {
return this.builderFactory.builder(DmpUserBuilder.class).authorize(AuthorizationFlags.OwnerOrDmpAssociatedOrPermission).build(BaseFieldSet.build(fieldSet, DmpUser._id, DmpUser._hash), persisted);
}
private void checkDuplicateDmpUser(List<DmpUserPersist> model){
for (DmpUserPersist user: model) {
List<DmpUserPersist> duplicateUser = null;
if (user.getUser() != null){
duplicateUser = model.stream().filter(x -> x.getUser().equals(user.getUser()) && x.getRole().equals(user.getRole()) && Objects.equals(user.getSectionId(), x.getSectionId())).collect(Collectors.toList());
} else {
duplicateUser = model.stream().filter(x -> x.getEmail().equals(user.getEmail()) && x.getRole().equals(user.getRole()) && Objects.equals(user.getSectionId(), x.getSectionId())).collect(Collectors.toList());
}
if (duplicateUser.size() > 1) {
throw new MyValidationException(this.errors.getDuplicateDmpUser().getCode(), this.errors.getDuplicateDmpUser().getMessage());
}
}
}
@Override
public Dmp removeUser(DmpUserRemovePersist model, FieldSet fields) throws InvalidApplicationException, IOException {
this.authorizationService.authorizeAtLeastOneForce(List.of(this.authorizationContentResolver.dmpAffiliation(model.getDmpId())), Permission.AssignDmpUsers);

View File

@ -97,4 +97,7 @@ error-thesaurus:
message: missing contact info for this user
import-description-without-dmp-description-template:
code: 136
message: Error creating description without dmp description template
message: Error creating description without dmp description template
duplicate-dmp-user:
code: 137
message: Duplicate Dmp User not allowed

View File

@ -34,6 +34,7 @@ export enum ResponseErrorCode {
DmpInactiveUser = 134,
DmpMissingUserContactInfo = 135,
ImportDescriptionWithoutDmpDescriptionTemplate = 136,
DuplicateDmpUser = 137,
// Notification & Annotation Errors
InvalidApiKey = 200,
@ -116,6 +117,8 @@ export class ResponseErrorCodeHelper {
return language.instant("GENERAL.BACKEND-ERRORS.IMPORT-DESCRIPTION-WITHOUT-DMP-DESCRIPTION-TEMPLATE");
case ResponseErrorCode.InvalidApiKey:
return language.instant("GENERAL.BACKEND-ERRORS.INVALID-API-KEY");
case ResponseErrorCode.DuplicateDmpUser:
return language.instant("GENERAL.BACKEND-ERRORS.DUPLICATE-DMP-USER");
case ResponseErrorCode.StaleApiKey:
return language.instant("GENERAL.BACKEND-ERRORS.STALE-API-KEY");
case ResponseErrorCode.SensitiveInfo:

View File

@ -12,7 +12,7 @@
<app-dmp-user-field-component [form]="formGroup" [validationErrorModel]="editorModel.validationErrorModel" [sections]="selectedBlueprint.definition.sections" [viewOnly]="false" [initializeUsers]="true" [enableSorting]="false"></app-dmp-user-field-component>
</div>
<div class="col mt-2">
<button mat-raised-button *ngIf="hasValue()" (click)="send()" type="button" class="invite-btn">{{'DMP-USER-INVITATION-DIALOG.ACTIONS.INVITE' | translate}}</button>
<button mat-raised-button *ngIf="hasValue()" [disabled]="inProgressSendButton" (click)="send()" type="button" class="invite-btn">{{'DMP-USER-INVITATION-DIALOG.ACTIONS.INVITE' | translate}}</button>
<mat-error *ngIf="formGroup.get('users').hasError('backendError')">{{formGroup.get('users').getError('backendError').message}}</mat-error>
<mat-error *ngIf="formGroup.get('users').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
</div>

View File

@ -19,11 +19,14 @@ import { takeUntil } from 'rxjs/operators';
import { DmpBlueprint } from '@app/core/model/dmp-blueprint/dmp-blueprint';
import { HttpErrorHandlingService } from '@common/modules/errors/error-handling/http-error-handling.service';
import { HttpErrorResponse } from '@angular/common/http';
import { FormService } from '@common/forms/form-service';
import { DmpEditorService } from '../../dmp-editor-blueprint/dmp-editor.service';
@Component({
selector: 'app-invitation-dialog-component',
templateUrl: 'dmp-invitation-dialog.component.html',
styleUrls: ['./dmp-invitation-dialog.component.scss'],
providers: [DmpEditorService]
})
export class DmpInvitationDialogComponent extends BaseComponent implements OnInit {
@ -32,6 +35,7 @@ export class DmpInvitationDialogComponent extends BaseComponent implements OnIni
formGroup: UntypedFormGroup;
dmpUserRoleEnum = DmpUserRole;
selectedBlueprint: DmpBlueprint;
inProgressSendButton = false;
readonly separatorKeysCodes: number[] = [ENTER, COMMA];
constructor(
@ -43,8 +47,8 @@ export class DmpInvitationDialogComponent extends BaseComponent implements OnIni
private uiNotificationService: UiNotificationService,
private httpErrorHandlingService: HttpErrorHandlingService,
private dmpService: DmpService,
private userService: UserService,
private filterService: FilterService,
private formService: FormService,
private dmpEditorService: DmpEditorService,
@Inject(MAT_DIALOG_DATA) public data: any
) {
super();
@ -55,10 +59,15 @@ export class DmpInvitationDialogComponent extends BaseComponent implements OnIni
ngOnInit() {
this.formGroup = this.editorModel.buildForm();
this.dmpEditorService.setValidationErrorModel(this.editorModel.validationErrorModel);
}
send() {
this.formService.removeAllBackEndErrors(this.formGroup.get("users"));
this.formService.touchAllFormFields(this.formGroup.get("users"));
if (!this.formGroup.get("users").valid) { return; }
this.inProgressSendButton = true;
const userFormData = this.formGroup.get("users").value as DmpUserPersist[];
this.dmpService.inviteUsers(this.dmpId, {users: userFormData})
@ -85,6 +94,7 @@ export class DmpInvitationDialogComponent extends BaseComponent implements OnIni
}
onCallbackError(errorResponse: HttpErrorResponse) {
this.inProgressSendButton = false;
let errorOverrides = new Map<number, string>();
errorOverrides.set(-1, this.language.instant('DMP-USER-INVITATION-DIALOG.ERROR'));
this.httpErrorHandlingService.handleBackedRequestError(errorResponse, errorOverrides, SnackBarNotificationLevel.Error);

View File

@ -69,7 +69,8 @@
"DESCRIPTION-TEMPLATE-INACTIVE-USER": "This description template contains users that are not exist",
"DESCRIPTION-TEMPLATE-MISSING-USER-CONTACT-INFO": "This description template contains users that don't have contact info",
"DMP-INACTIVE-USER": "This plan contains users that are not exist",
"DMP-MISSING-USER-CONTACT-INFO": "This plan contains users that don't have contact info"
"DMP-MISSING-USER-CONTACT-INFO": "This plan contains users that don't have contact info",
"DUPLICATE-DMP-USER": "You can't invite authors with same role and plan section more than once"
},
"FORM-VALIDATION-DISPLAY-DIALOG": {
"WARNING": "Warning!",