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

This commit is contained in:
Efstratios Giannopoulos 2024-03-27 18:13:16 +02:00
commit d0ad9a8be0
45 changed files with 437 additions and 144 deletions

View File

@ -73,6 +73,7 @@ public final class Permission {
public static String DepositDmp = "DepositDmp"; public static String DepositDmp = "DepositDmp";
public static String DeleteDmp = "DeleteDmp"; public static String DeleteDmp = "DeleteDmp";
public static String CloneDmp = "CloneDmp"; public static String CloneDmp = "CloneDmp";
public static String ExportDmp = "ExportDmp";
public static String CreateNewVersionDmp = "CreateNewVersionDmp"; public static String CreateNewVersionDmp = "CreateNewVersionDmp";
public static String FinalizeDmp = "FinalizeDmp"; public static String FinalizeDmp = "FinalizeDmp";
public static String UndoFinalizeDmp = "UndoFinalizeDmp"; public static String UndoFinalizeDmp = "UndoFinalizeDmp";

View File

@ -134,4 +134,14 @@ public class ErrorThesaurusProperties {
public void setDmpBlueprintHasNoDescriptionTemplates(ErrorDescription dmpBlueprintHasNoDescriptionTemplates) { public void setDmpBlueprintHasNoDescriptionTemplates(ErrorDescription dmpBlueprintHasNoDescriptionTemplates) {
this.dmpBlueprintHasNoDescriptionTemplates = dmpBlueprintHasNoDescriptionTemplates; this.dmpBlueprintHasNoDescriptionTemplates = dmpBlueprintHasNoDescriptionTemplates;
} }
private ErrorDescription dmpDescriptionTemplateCanNotRemove;
public ErrorDescription getDmpDescriptionTemplateCanNotRemove() {
return dmpDescriptionTemplateCanNotRemove;
}
public void setDmpDescriptionTemplateCanNotRemove(ErrorDescription dmpDescriptionTemplateCanNotRemove) {
this.dmpDescriptionTemplateCanNotRemove = dmpDescriptionTemplateCanNotRemove;
}
} }

View File

@ -36,7 +36,7 @@ public class DepositConfigurationCensor extends BaseCensor {
if (fields == null || fields.isEmpty()) if (fields == null || fields.isEmpty())
return; return;
this.authService.authorizeForce(Permission.BrowseDeposit); this.authService.authorizeForce(Permission.BrowseDeposit, Permission.DeferredAffiliation);
} }

View File

@ -36,7 +36,7 @@ public class DescriptionReferenceDataCensor extends BaseCensor {
if (fields == null || fields.isEmpty()) if (fields == null || fields.isEmpty())
return; return;
this.authService.authorizeForce(Permission.BrowseDescriptionReference); this.authService.authorizeForce(Permission.BrowseDescriptionReference, Permission.DeferredAffiliation);
} }
} }

View File

@ -203,12 +203,12 @@ public class DescriptionPersist {
this.spec() this.spec()
.iff(() -> item.getStatus() == DescriptionStatus.Finalized) .iff(() -> item.getStatus() == DescriptionStatus.Finalized)
.must(() -> !this.isNull(item.getProperties())) .must(() -> !this.isNull(item.getProperties()))
.failOn(DescriptionPersist._properties).failWith(messageSource.getMessage("Validation_Required", new Object[]{DescriptionPersist._properties}, LocaleContextHolder.getLocale())), .failOn(DescriptionPersist._properties).failWith(messageSource.getMessage("Validation_Required", new Object[]{DescriptionPersist._properties}, LocaleContextHolder.getLocale()))
this.refSpec() // this.refSpec()
.iff(() -> !this.isNull(item.getProperties())) // .iff(() -> !this.isNull(item.getProperties()))
.on(DescriptionPersist._properties) // .on(DescriptionPersist._properties)
.over(item.getProperties()) // .over(item.getProperties())
.using(() -> this.validatorFactory.validator(PropertyDefinitionPersist.PropertyDefinitionPersistValidator.class).setStatus(item.getStatus()).withDefinition(definition)) // .using(() -> this.validatorFactory.validator(PropertyDefinitionPersist.PropertyDefinitionPersistValidator.class).setStatus(item.getStatus()).withDefinition(definition))
// this.navSpec() // this.navSpec()
// .iff(() -> !this.isNull(item.getTags())) // .iff(() -> !this.isNull(item.getTags()))
// .on(DescriptionPersist._tags) // .on(DescriptionPersist._tags)

View File

@ -74,7 +74,7 @@ public class DmpReferencePersist {
.iff(() -> !this.isNull(item.getReference())) .iff(() -> !this.isNull(item.getReference()))
.on(DmpReferencePersist._reference) .on(DmpReferencePersist._reference)
.over(item.getReference()) .over(item.getReference())
.using(() -> this.validatorFactory.validator(ReferencePersist.ReferencePersistValidator.class)), .using(() -> this.validatorFactory.validator(ReferencePersist.ReferenceWithoutTypePersistValidator.class)),
this.spec() this.spec()
.must(() -> !this.isNull(item.getData())) .must(() -> !this.isNull(item.getData()))
.failOn(DmpReferencePersist._data).failWith(messageSource.getMessage("Validation_Required", new Object[]{DmpReferencePersist._data}, LocaleContextHolder.getLocale())), .failOn(DmpReferencePersist._data).failWith(messageSource.getMessage("Validation_Required", new Object[]{DmpReferencePersist._data}, LocaleContextHolder.getLocale())),

View File

@ -208,4 +208,73 @@ public class ReferencePersist {
} }
} }
@Component(ReferenceWithoutTypePersistValidator.ValidatorName)
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
public static class ReferenceWithoutTypePersistValidator extends BaseValidator<ReferencePersist> {
public static final String ValidatorName = "ReferenceWithoutTypePersistValidator";
private final MessageSource messageSource;
private final ValidatorFactory validatorFactory;
protected ReferenceWithoutTypePersistValidator(ConventionService conventionService, ErrorThesaurusProperties errors, MessageSource messageSource, ValidatorFactory validatorFactory) {
super(conventionService, errors);
this.messageSource = messageSource;
this.validatorFactory = validatorFactory;
}
@Override
protected Class<ReferencePersist> modelClass() {
return ReferencePersist.class;
}
@Override
protected List<Specification> specifications(ReferencePersist item) {
return Arrays.asList(
this.spec()
.iff(() -> this.isValidGuid(item.getId()))
.must(() -> this.isValidHash(item.getHash()))
.failOn(ReferencePersist._hash).failWith(messageSource.getMessage("Validation_Required", new Object[]{ReferencePersist._hash}, LocaleContextHolder.getLocale())),
this.spec()
.iff(() -> !this.isValidGuid(item.getId()))
.must(() -> !this.isValidHash(item.getHash()))
.failOn(ReferencePersist._hash).failWith(messageSource.getMessage("Validation_OverPosting", new Object[]{}, LocaleContextHolder.getLocale())),
this.spec()
.must(() -> !this.isEmpty(item.getLabel()))
.failOn(ReferencePersist._label).failWith(messageSource.getMessage("Validation_Required", new Object[]{ReferencePersist._label}, LocaleContextHolder.getLocale())),
this.spec()
.iff(() -> !this.isEmpty(item.getLabel()))
.must(() -> this.lessEqualLength(item.getLabel(), ReferenceEntity._labelLength))
.failOn(ReferencePersist._label).failWith(messageSource.getMessage("Validation_MaxLength", new Object[]{ReferencePersist._label}, LocaleContextHolder.getLocale())),
this.spec()
.must(() -> !this.isEmpty(item.getReference()))
.failOn(ReferencePersist._reference).failWith(messageSource.getMessage("Validation_Required", new Object[]{ReferencePersist._reference}, LocaleContextHolder.getLocale())),
this.spec()
.iff(() -> !this.isEmpty(item.getReference()))
.must(() -> this.lessEqualLength(item.getReference(), ReferenceEntity._referenceLength))
.failOn(ReferencePersist._reference).failWith(messageSource.getMessage("Validation_MaxLength", new Object[]{ReferencePersist._reference}, LocaleContextHolder.getLocale())),
this.spec()
.iff(() -> !this.isEmpty(item.getAbbreviation()))
.must(() -> this.lessEqualLength(item.getAbbreviation(), ReferenceEntity._abbreviationLength))
.failOn(ReferencePersist._abbreviation).failWith(messageSource.getMessage("Validation_MaxLength", new Object[]{ReferencePersist._abbreviation}, LocaleContextHolder.getLocale())),
this.spec()
.must(() -> !this.isEmpty(item.getSource()))
.failOn(ReferencePersist._source).failWith(messageSource.getMessage("Validation_Required", new Object[]{ReferencePersist._source}, LocaleContextHolder.getLocale())),
this.spec()
.iff(() -> !this.isEmpty(item.getSource()))
.must(() -> this.lessEqualLength(item.getSource(), ReferenceEntity._sourceLength))
.failOn(ReferencePersist._source).failWith(messageSource.getMessage("Validation_MaxLength", new Object[]{ReferencePersist._source}, LocaleContextHolder.getLocale())),
this.spec()
.must(() -> !this.isNull(item.getSourceType()))
.failOn(ReferencePersist._sourceType).failWith(messageSource.getMessage("Validation_Required", new Object[]{ReferencePersist._sourceType}, LocaleContextHolder.getLocale())),
this.refSpec()
.iff(() -> !this.isNull(item.getDefinition()))
.on(ReferencePersist._definition)
.over(item.getDefinition())
.using(() -> this.validatorFactory.validator(DefinitionPersist.DefinitionPersistValidator.class))
);
}
}
} }

View File

@ -32,6 +32,9 @@ public class FieldPersist {
private List<ReferencePersist> references; private List<ReferencePersist> references;
public static final String _references = "references"; public static final String _references = "references";
private ReferencePersist reference;
public static final String _reference = "reference";
private ExternalIdentifierPersist externalIdentifier; private ExternalIdentifierPersist externalIdentifier;
public static final String _externalIdentifier = "externalIdentifier"; public static final String _externalIdentifier = "externalIdentifier";
@ -67,6 +70,14 @@ public class FieldPersist {
this.references = references; this.references = references;
} }
public ReferencePersist getReference() {
return reference;
}
public void setReference(ReferencePersist reference) {
this.reference = reference;
}
public ExternalIdentifierPersist getExternalIdentifier() { public ExternalIdentifierPersist getExternalIdentifier() {
return externalIdentifier; return externalIdentifier;
} }
@ -137,7 +148,12 @@ public class FieldPersist {
.iff(() -> FieldType.isReferenceType(fieldType) && !this.isListNullOrEmpty(item.getReferences())) .iff(() -> FieldType.isReferenceType(fieldType) && !this.isListNullOrEmpty(item.getReferences()))
.on(FieldPersist._references) .on(FieldPersist._references)
.over(item.getReferences()) .over(item.getReferences())
.using((itm) -> this.validatorFactory.validator(ReferencePersist.ReferencePersistValidator.class)), .using((itm) -> this.validatorFactory.validator(ReferencePersist.ReferenceWithoutTypePersistValidator.class)),
this.refSpec()
.iff(() -> FieldType.isReferenceType(fieldType) && !this.isNull(item.getReference()))
.on(FieldPersist._reference)
.over(item.getReference())
.using(() -> this.validatorFactory.validator(ReferencePersist.ReferenceWithoutTypePersistValidator.class)),
this.refSpec() this.refSpec()
.iff(() -> FieldType.isExternalIdentifierType(fieldType) && !this.isNull(item.getExternalIdentifier())) .iff(() -> FieldType.isExternalIdentifierType(fieldType) && !this.isNull(item.getExternalIdentifier()))
.on(FieldPersist._externalIdentifier) .on(FieldPersist._externalIdentifier)

View File

@ -218,6 +218,7 @@ public class DescriptionReferenceQuery extends QueryBase<DescriptionReferenceEnt
else if (item.prefix(DescriptionReference._reference)) return DescriptionReferenceEntity._referenceId; else if (item.prefix(DescriptionReference._reference)) return DescriptionReferenceEntity._referenceId;
else if (item.match(DescriptionReference._createdAt)) return DescriptionReferenceEntity._createdAt; else if (item.match(DescriptionReference._createdAt)) return DescriptionReferenceEntity._createdAt;
else if (item.match(DescriptionReference._updatedAt)) return DescriptionReferenceEntity._updatedAt; else if (item.match(DescriptionReference._updatedAt)) return DescriptionReferenceEntity._updatedAt;
else if (item.prefix(DescriptionReference._data)) return DescriptionReferenceEntity._data;
else if (item.match(DescriptionReference._hash)) return DescriptionReferenceEntity._updatedAt; else if (item.match(DescriptionReference._hash)) return DescriptionReferenceEntity._updatedAt;
else if (item.match(DescriptionReference._isActive)) return DescriptionReferenceEntity._isActive; else if (item.match(DescriptionReference._isActive)) return DescriptionReferenceEntity._isActive;
else return null; else return null;
@ -231,6 +232,7 @@ public class DescriptionReferenceQuery extends QueryBase<DescriptionReferenceEnt
item.setReferenceId(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._referenceId, UUID.class)); item.setReferenceId(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._referenceId, UUID.class));
item.setCreatedAt(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._createdAt, Instant.class)); item.setCreatedAt(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._createdAt, Instant.class));
item.setUpdatedAt(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._updatedAt, Instant.class)); item.setUpdatedAt(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._updatedAt, Instant.class));
item.setData(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._data, String.class));
item.setIsActive(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._isActive, IsActive.class)); item.setIsActive(QueryBase.convertSafe(tuple, columns, DescriptionReferenceEntity._isActive, IsActive.class));
return item; return item;
} }

View File

@ -34,6 +34,6 @@ public class DepositClientImpl implements DepositClient {
@Override @Override
public String getLogo() { public String getLogo() {
return depositClient.get().uri("/logo/").header(HttpHeaders.CONTENT_TYPE, MediaType.APPLICATION_JSON_VALUE).accept(MediaType.APPLICATION_JSON).exchangeToMono(mono -> mono.bodyToMono(String.class)).block(); return depositClient.get().uri("/logo/").exchangeToMono(mono -> mono.bodyToMono(String.class)).block();
} }
} }

View File

@ -114,7 +114,7 @@ public class DepositServiceImpl implements DepositService {
@Override @Override
public List<eu.eudat.model.deposit.DepositConfiguration> getAvailableConfigurations(FieldSet fieldSet) { public List<eu.eudat.model.deposit.DepositConfiguration> getAvailableConfigurations(FieldSet fieldSet) {
this.authorizationService.authorizeForce(Permission.BrowseDeposit); this.authorizationService.authorizeForce(Permission.BrowseDeposit, Permission.DeferredAffiliation);
List<eu.eudat.model.deposit.DepositConfiguration> configurations = new ArrayList<>(); List<eu.eudat.model.deposit.DepositConfiguration> configurations = new ArrayList<>();
@ -201,7 +201,7 @@ public class DepositServiceImpl implements DepositService {
@Override @Override
public String getLogo(String repositoryId) { public String getLogo(String repositoryId) {
this.authorizationService.authorizeForce(Permission.BrowseDeposit); this.authorizationService.authorizeForce(Permission.BrowseDeposit, Permission.DeferredAffiliation);
DepositClient depositClient = getDepositClient(repositoryId); DepositClient depositClient = getDepositClient(repositoryId);
if (depositClient == null) throw new MyNotFoundException(messageSource.getMessage("General_ItemNotFound", new Object[]{repositoryId, DepositClient.class.getSimpleName()}, LocaleContextHolder.getLocale())); if (depositClient == null) throw new MyNotFoundException(messageSource.getMessage("General_ItemNotFound", new Object[]{repositoryId, DepositClient.class.getSimpleName()}, LocaleContextHolder.getLocale()));
@ -210,7 +210,7 @@ public class DepositServiceImpl implements DepositService {
@Override @Override
public String authenticate(DepositAuthenticateRequest model) { public String authenticate(DepositAuthenticateRequest model) {
this.authorizationService.authorizeForce(Permission.BrowseDeposit); this.authorizationService.authorizeForce(Permission.BrowseDeposit, Permission.DeferredAffiliation);
DepositClient depositClient = getDepositClient(model.getRepositoryId()); DepositClient depositClient = getDepositClient(model.getRepositoryId());
if (depositClient == null) throw new MyNotFoundException(messageSource.getMessage("General_ItemNotFound", new Object[]{model.getRepositoryId(), DepositClient.class.getSimpleName()}, LocaleContextHolder.getLocale())); if (depositClient == null) throw new MyNotFoundException(messageSource.getMessage("General_ItemNotFound", new Object[]{model.getRepositoryId(), DepositClient.class.getSimpleName()}, LocaleContextHolder.getLocale()));

View File

@ -502,7 +502,7 @@ public class DescriptionServiceImpl implements DescriptionService {
List<DescriptionReferencePersist> descriptionReferencePersists = new ArrayList<>(); List<DescriptionReferencePersist> descriptionReferencePersists = new ArrayList<>();
if (persist.getFieldSets() != null && !persist.getFieldSets().isEmpty()){ if (persist.getFieldSets() != null && !persist.getFieldSets().isEmpty()){
for (PropertyDefinitionFieldSetPersist propertyDefinitionFieldSetPersist: persist.getFieldSets().values()) { for (PropertyDefinitionFieldSetPersist propertyDefinitionFieldSetPersist: persist.getFieldSets().values()) {
if (this.conventionService.isListNullOrEmpty( propertyDefinitionFieldSetPersist.getItems())) { if (!this.conventionService.isListNullOrEmpty( propertyDefinitionFieldSetPersist.getItems())) {
for (PropertyDefinitionFieldSetItemPersist definitionFieldSetItemPersist : propertyDefinitionFieldSetPersist.getItems()) { for (PropertyDefinitionFieldSetItemPersist definitionFieldSetItemPersist : propertyDefinitionFieldSetPersist.getItems()) {
if (definitionFieldSetItemPersist.getFields() != null && !definitionFieldSetItemPersist.getFields().isEmpty()) { if (definitionFieldSetItemPersist.getFields() != null && !definitionFieldSetItemPersist.getFields().isEmpty()) {
for (String key : definitionFieldSetItemPersist.getFields().keySet()) { for (String key : definitionFieldSetItemPersist.getFields().keySet()) {
@ -518,7 +518,11 @@ public class DescriptionServiceImpl implements DescriptionService {
} }
private void BuildDescriptionReferencePersist(String fieldId, FieldPersist fieldPersist, List<DescriptionReferencePersist> descriptionReferencePersists) { private void BuildDescriptionReferencePersist(String fieldId, FieldPersist fieldPersist, List<DescriptionReferencePersist> descriptionReferencePersists) {
if (this.conventionService.isListNullOrEmpty(fieldPersist.getReferences())) { if (fieldPersist.getReference() != null) {
if (fieldPersist.getReferences() == null) fieldPersist.setReferences(new ArrayList<>());
fieldPersist.getReferences().add(fieldPersist.getReference());
}
if (!this.conventionService.isListNullOrEmpty(fieldPersist.getReferences())) {
for (ReferencePersist referencePersist : fieldPersist.getReferences()) { for (ReferencePersist referencePersist : fieldPersist.getReferences()) {
DescriptionReferencePersist descriptionReferencePersist = new DescriptionReferencePersist(); DescriptionReferencePersist descriptionReferencePersist = new DescriptionReferencePersist();
descriptionReferencePersist.setData(new DescriptionReferenceDataPersist()); descriptionReferencePersist.setData(new DescriptionReferenceDataPersist());

View File

@ -188,6 +188,8 @@ public class DmpServiceImpl implements DmpService {
this.patchAndSaveReferences(this.buildDmpReferencePersists(model.getProperties()), data.getId(), definition); this.patchAndSaveReferences(this.buildDmpReferencePersists(model.getProperties()), data.getId(), definition);
if (isUpdate) this.checkIfDescriptionTemplateIsUse(model.getDescriptionTemplates(), model.getId());
this.patchAndSaveTemplates(data.getId(), model.getDescriptionTemplates()); this.patchAndSaveTemplates(data.getId(), model.getDescriptionTemplates());
if (!isUpdate && userScope.isSet()) { if (!isUpdate && userScope.isSet()) {
@ -210,6 +212,17 @@ public class DmpServiceImpl implements DmpService {
return this.builderFactory.builder(DmpBuilder.class).authorize(AuthorizationFlags.OwnerOrDmpAssociatedOrPermission).build(BaseFieldSet.build(fields, Dmp._id, Dmp._hash), data); return this.builderFactory.builder(DmpBuilder.class).authorize(AuthorizationFlags.OwnerOrDmpAssociatedOrPermission).build(BaseFieldSet.build(fields, Dmp._id, Dmp._hash), data);
} }
private void checkIfDescriptionTemplateIsUse (List<DmpDescriptionTemplatePersist> descriptionTemplates, UUID id){
List<DmpDescriptionTemplateEntity> existingDmpDescriptionTemplates = this.queryFactory.query(DmpDescriptionTemplateQuery.class).authorize(AuthorizationFlags.OwnerOrDmpAssociatedOrPermission).dmpIds(id).isActive(IsActive.Active).collect();
List<DmpDescriptionTemplateEntity> removedDescriptionTemplates = existingDmpDescriptionTemplates.stream().filter(x -> descriptionTemplates.stream().noneMatch(y -> y.getDescriptionTemplateGroupId().equals(x.getDescriptionTemplateGroupId()))).collect(Collectors.toList());
DmpDescriptionTemplateQuery dmpDescriptionTemplateQuery = this.queryFactory.query(DmpDescriptionTemplateQuery.class).isActive(IsActive.Active).dmpIds(id).descriptionTemplateGroupIds(removedDescriptionTemplates.stream().map(x -> x.getDescriptionTemplateGroupId()).collect(Collectors.toList()));
DescriptionQuery query = this.queryFactory.query(DescriptionQuery.class).authorize(AuthorizationFlags.OwnerOrDmpAssociatedOrPermission).dmpDescriptionTemplateSubQuery(dmpDescriptionTemplateQuery).isActive(IsActive.Active);
if (query != null && query.count() > 0) throw new MyValidationException(this.errors.getDmpDescriptionTemplateCanNotRemove().getCode(), this.errors.getDmpDescriptionTemplateCanNotRemove().getMessage());
}
private DmpUserPersist createOwnerPersist() { private DmpUserPersist createOwnerPersist() {
DmpUserPersist persist = new DmpUserPersist(); DmpUserPersist persist = new DmpUserPersist();
persist.setRole(DmpUserRole.Owner); persist.setRole(DmpUserRole.Owner);

View File

@ -4,6 +4,7 @@ import eu.eudat.commons.types.description.FieldEntity;
import eu.eudat.model.persist.descriptionproperties.FieldPersist; import eu.eudat.model.persist.descriptionproperties.FieldPersist;
import java.time.Instant; import java.time.Instant;
import java.util.ArrayList;
import java.util.List; import java.util.List;
public class Field { public class Field {
@ -43,6 +44,10 @@ public class Field {
tempTextListValue = persist.getTextListValue(); tempTextListValue = persist.getTextListValue();
if (persist.getExternalIdentifier() != null) this.externalIdentifier = new ExternalIdentifier(persist.getExternalIdentifier()); if (persist.getExternalIdentifier() != null) this.externalIdentifier = new ExternalIdentifier(persist.getExternalIdentifier());
else this.externalIdentifier = null; else this.externalIdentifier = null;
if (persist.getReference() != null) {
if (persist.getReferences() == null) persist.setReferences(new ArrayList<>());
persist.getReferences().add(persist.getReference());
}
if (persist.getReferences() != null && !persist.getReferences().isEmpty()){ if (persist.getReferences() != null && !persist.getReferences().isEmpty()){
tempTextListValue = persist.getReferences().stream().filter(x-> x.getId() != null).map(x-> x.getId().toString()).toList(); tempTextListValue = persist.getReferences().stream().filter(x-> x.getId() != null).map(x-> x.getId().toString()).toList();
} }

View File

@ -214,7 +214,7 @@ public class LockController {
@DeleteMapping("{id}/{target}") @DeleteMapping("{id}/{target}")
@Transactional @Transactional
public void delete(@PathVariable("id") UUID id, @PathVariable("id") UUID target) throws MyForbiddenException, InvalidApplicationException { public void delete(@PathVariable("id") UUID id, @PathVariable("target") UUID target) throws MyForbiddenException, InvalidApplicationException {
logger.debug(new MapLogEntry("retrieving" + Lock.class.getSimpleName()).And("id", id)); logger.debug(new MapLogEntry("retrieving" + Lock.class.getSimpleName()).And("id", id));
this.lockService.deleteAndSave(id, target); this.lockService.deleteAndSave(id, target);

View File

@ -1,10 +1,18 @@
deposit: deposit:
sources: sources:
- url: http://dev04.local.cite.gr:55330/zenodo - url: http://dev04.local.cite.gr:55330/zenodo
repositoryId: zenodo repositoryId: Zenodo
pdfTransformerId: docx-file-transformer pdfTransformerId: docx-file-transformer
rdaTransformerId: rda-file-transformer rdaTransformerId: rda-file-transformer
issuer-url: ${IDP_ISSUER_URI_TOKEN} issuer-url: ${IDP_ISSUER_URI_TOKEN}
client-id: ${ZENODO_DEPOSIT_CLIENT_ID} client-id: ${IDP_APIKEY_CLIENT_ID}
client-secret: ${ZENODO_DEPOSIT_CLIENT_SECRET} client-secret: ${IDP_APIKEY_CLIENT_SECRET}
scope: ${ZENODO_DEPOSIT_SCOPE} scope: ${IDP_APIKEY_SCOPE}
- url: http://dev04.local.cite.gr:55330/zenodo1
repositoryId: Zenodo1
pdfTransformerId: docx-file-transformer
rdaTransformerId: rda-file-transformer
issuer-url: ${IDP_ISSUER_URI_TOKEN}
client-id: ${IDP_APIKEY_CLIENT_ID}
client-secret: ${IDP_APIKEY_CLIENT_SECRET}
scope: ${IDP_APIKEY_SCOPE}

View File

@ -53,3 +53,6 @@ error-thesaurus:
dmp-blueprint-new-version-conflict: dmp-blueprint-new-version-conflict:
code: 121 code: 121
message: version to update not the latest message: version to update not the latest
dmp-description-template-can-not-remove:
code: 122
message: Can not remove description template that is already in use.

View File

@ -402,6 +402,16 @@ permissions:
clients: [ ] clients: [ ]
allowAnonymous: false allowAnonymous: false
allowAuthenticated: false allowAuthenticated: false
ExportDmp:
roles:
- Admin
dmp:
roles:
- Owner
claims: [ ]
clients: [ ]
allowAnonymous: false
allowAuthenticated: false
CreateNewVersionDmp: CreateNewVersionDmp:
roles: roles:
- Admin - Admin

View File

@ -0,0 +1,11 @@
DO $$DECLARE
this_version CONSTANT varchar := '00.01.061';
BEGIN
PERFORM * FROM "DBVersion" WHERE version = this_version;
IF FOUND THEN RETURN; END IF;
ALTER TABLE public."EntityDoi" DROP CONSTRAINT fk_doi_entityid;
INSERT INTO public."DBVersion" VALUES ('DMPDB', '00.01.061', '2024-03-27 12:00:00.000000+02', now(), 'Remove DMP fkey from EntityDoi Table.');
END$$;

View File

@ -94,6 +94,7 @@ export interface DescriptionTemplateMultiplicity {
export interface DescriptionTemplateBaseFieldData { export interface DescriptionTemplateBaseFieldData {
label: string; label: string;
fieldType: DescriptionTemplateFieldType; fieldType: DescriptionTemplateFieldType;
multipleSelect?: boolean;
} }

View File

@ -301,7 +301,7 @@ export class AuthService extends BaseService {
onAuthenticateSuccess(returnUrl: string): void { onAuthenticateSuccess(returnUrl: string): void {
this.authState(true); this.authState(true);
this.uiNotificationService.snackBarNotification( this.uiNotificationService.snackBarNotification(
this.language.instant('COMMONS.SNACK-BAR.SUCCESSFUL-LOGIN'), this.language.instant('GENERAL.SNACK-BAR.SUCCESSFUL-LOGIN'),
SnackBarNotificationLevel.Success SnackBarNotificationLevel.Success
); );
this.zone.run(() => this.router.navigate([returnUrl])); this.zone.run(() => this.router.navigate([returnUrl]));

View File

@ -43,8 +43,8 @@ export class LockService {
catchError((error: any) => throwError(error))); catchError((error: any) => throwError(error)));
} }
delete(id: Guid): Observable<Lock> { delete(id: Guid, target: Guid): Observable<Lock> {
const url = `${this.apiBase}/${id}`; const url = `${this.apiBase}/${id}/${target}`;
return this.http return this.http
.delete<Lock>(url).pipe( .delete<Lock>(url).pipe(

View File

@ -16,6 +16,7 @@ import { nameof } from 'ts-simple-nameof';
import { ConfigurationService } from '../configuration/configuration.service'; import { ConfigurationService } from '../configuration/configuration.service';
import { BaseHttpV2Service } from '../http/base-http-v2.service'; import { BaseHttpV2Service } from '../http/base-http-v2.service';
import { TranslateService } from '@ngx-translate/core'; import { TranslateService } from '@ngx-translate/core';
import { ReferenceType } from '@app/core/model/reference-type/reference-type';
@Injectable() @Injectable()
export class ReferenceService { export class ReferenceService {
@ -150,6 +151,7 @@ export class ReferenceService {
nameof<Reference>(x => x.hash), nameof<Reference>(x => x.hash),
nameof<Reference>(x => x.label), nameof<Reference>(x => x.label),
nameof<Reference>(x => x.type), nameof<Reference>(x => x.type),
[nameof<Reference>(x => x.type), nameof<ReferenceType>(x => x.id)].join('.'),
nameof<Reference>(x => x.description), nameof<Reference>(x => x.description),
[nameof<Reference>(x => x.definition), nameof<Definition>(x => x.fields), nameof<Field>(x => x.code)].join('.'), [nameof<Reference>(x => x.definition), nameof<Definition>(x => x.fields), nameof<Field>(x => x.code)].join('.'),
[nameof<Reference>(x => x.definition), nameof<Definition>(x => x.fields), nameof<Field>(x => x.dataType)].join('.'), [nameof<Reference>(x => x.definition), nameof<Definition>(x => x.fields), nameof<Field>(x => x.dataType)].join('.'),

View File

@ -78,7 +78,7 @@
<mat-icon>more_horiz</mat-icon> <mat-icon>more_horiz</mat-icon>
</button> </button>
<mat-menu #actionsMenu="matMenu"> <mat-menu #actionsMenu="matMenu">
<button mat-menu-item (click)="deleteType(row.id)"> <button mat-menu-item (click)="deleteType(row.id, row.target)">
<mat-icon>delete</mat-icon> <mat-icon>delete</mat-icon>
{{'LOCK-LISTING.ACTIONS.DELETE' | translate}} {{'LOCK-LISTING.ACTIONS.DELETE' | translate}}
</button> </button>

View File

@ -147,7 +147,7 @@ export class LockListingComponent extends BaseListingComponent<Lock, LockLookup>
return this.lockService.query(this.lookup); return this.lockService.query(this.lookup);
} }
public deleteType(id: Guid) { public deleteType(id: Guid, target: Guid) {
if (id) { if (id) {
const dialogRef = this.dialog.open(ConfirmationDialogComponent, { const dialogRef = this.dialog.open(ConfirmationDialogComponent, {
data: { data: {
@ -159,7 +159,7 @@ export class LockListingComponent extends BaseListingComponent<Lock, LockLookup>
}); });
dialogRef.afterClosed().pipe(takeUntil(this._destroyed)).subscribe(result => { dialogRef.afterClosed().pipe(takeUntil(this._destroyed)).subscribe(result => {
if (result) { if (result) {
this.lockService.delete(id).pipe(takeUntil(this._destroyed)) this.lockService.delete(id, target).pipe(takeUntil(this._destroyed))
.subscribe( .subscribe(
complete => this.onCallbackSuccess(), complete => this.onCallbackSuccess(),
error => this.onCallbackError(error) error => this.onCallbackError(error)

View File

@ -10,12 +10,23 @@
<!-- <div *ngIf="this.canEdit && !this.isDeleted" class="col-12"> --> <!-- <div *ngIf="this.canEdit && !this.isDeleted" class="col-12"> -->
<div class="col-12"> <div class="col-12">
<form class="row p-2 mt-2 mb-3 ml-0 pr-3 mr-0 new-thread" [formGroup]="threadFormGroup"> <form class="row p-2 mt-2 mb-3 ml-0 pr-3 mr-0 new-thread" [formGroup]="threadFormGroup">
<mat-form-field class="col-6 msg-input"> <!-- <mat-form-field class="col-6 msg-input">
<textarea matInput matTextareaAutosize matAutosizeMinRows="1" name="thread-text" formControlName="text" placeholder="{{'ANNOTATION-DIALOG.THREADS.NEW-THREAD' | translate}}" required></textarea> <textarea matInput matTextareaAutosize matAutosizeMinRows="1" name="thread-text" formControlName="text" placeholder="{{'ANNOTATION-DIALOG.THREADS.NEW-THREAD' | translate}}" required></textarea>
<mat-error *ngIf="threadFormGroup.get('text').hasError('backendError')">{{threadFormGroup.get('text').getError('backendError')?.message}}</mat-error> <mat-error *ngIf="threadFormGroup.get('text').hasError('backendError')">{{threadFormGroup.get('text').getError('backendError')?.message}}</mat-error>
<mat-error *ngIf="threadFormGroup.get('text').hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error> <mat-error *ngIf="threadFormGroup.get('text').hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error>
</mat-form-field> -->
<mat-form-field appearance="outline" class="col">
<mat-label>{{'ANNOTATION-DIALOG.THREADS.NEW-THREAD' | translate}}</mat-label>
<input matInput formControlName="text" required>
<mat-icon matSuffix class="material-symbols-outlined">
add_reaction
</mat-icon>
<mat-error *ngIf="threadFormGroup.get('text').hasError('backendError')">{{threadFormGroup.get('text').getError('backendError')?.message}}</mat-error>
<mat-error *ngIf="threadFormGroup.get('text').hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error>
</mat-form-field> </mat-form-field>
<mat-form-field class="col-6 pl-0 pr-0 protection-input">
<mat-form-field class="col-auto pl-0 pr-0 protection-input">
<mat-label>{{'ANNOTATION-DIALOG.THREADS.PROTECTION.TITLE' | translate}}</mat-label> <mat-label>{{'ANNOTATION-DIALOG.THREADS.PROTECTION.TITLE' | translate}}</mat-label>
<mat-select name="thread-protectionType" formControlName="protectionType" required> <mat-select name="thread-protectionType" formControlName="protectionType" required>
<mat-option *ngFor="let enumValue of annotationProtectionTypeEnumValues" [value]="enumValue">{{enumUtils.toAnnotationProtectionTypeString(enumValue)}}</mat-option> <mat-option *ngFor="let enumValue of annotationProtectionTypeEnumValues" [value]="enumValue">{{enumUtils.toAnnotationProtectionTypeString(enumValue)}}</mat-option>
@ -23,83 +34,125 @@
<mat-error *ngIf="threadFormGroup.get('protectionType').hasError('backendError')">{{threadFormGroup.get('protectionType').getError('backendError')?.message}}</mat-error> <mat-error *ngIf="threadFormGroup.get('protectionType').hasError('backendError')">{{threadFormGroup.get('protectionType').getError('backendError')?.message}}</mat-error>
<mat-error *ngIf="threadFormGroup.get('protectionType').hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error> <mat-error *ngIf="threadFormGroup.get('protectionType').hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error>
</mat-form-field> </mat-form-field>
<div class="col-auto send-msg"> <div class="col-12 send-msg mt-1">
<button mat-raised-button type="button" (click)="createThread()"> <div class="row">
<i class="fa fa-paper-plane"></i> {{'ANNOTATION-DIALOG.THREADS.SEND' | translate}} <div class="col-auto pr-1">
</button> <button type="button" class="normal-btn-sm" (click)="createThread()">{{ 'ANNOTATION-DIALOG.THREADS.SEND' | translate }} <i class="fa fa-paper-plane ml-2"></i></button>
</div>
<div class="col-auto pl-1">
<button type="button" class="normal-btn-light-sm" (click)="close()">{{ 'ANNOTATION-DIALOG.THREADS.CANCEL' | translate }}</button>
</div>
</div>
</div> </div>
</form> </form>
</div> </div>
<div class="col-12 mb-3 pt-2 gr-color" *ngIf="threads?.size > 0">{{'ANNOTATION-DIALOG.TITLE' | translate}}</div> <div class="col-12 mb-3 pt-2 gr-color" *ngIf="threads?.size > 0">{{'ANNOTATION-DIALOG.TITLE' | translate}}</div>
<div class="col-12"> <div class="col-12">
<div *ngFor="let thread of threads" class="row"> <ng-container *ngFor="let thread of threads">
<!-- Parent Thread --> <div class="row" *ngIf="getParentAnnotation(thread).protectionType === annotationProtectionTypeEnum.Private" matTooltip="{{'ANNOTATION-DIALOG.PROTECTION.PRIVATE' | translate}}">
<div class="col-12"> <div class="col-auto ml-auto">
<div class="row parent-thread m-0 h-100"> <i class="material-icons protection-icon icon-{{getAnnotationProtectionType(thread)}}"></i>{{getAnnotationProtectionType(thread)}}
<div class="col-auto pr-0 pl-0"> </div>
<div class="side-color"></div> </div>
</div> <div class="row ml-auto" *ngIf="getParentAnnotation(thread).protectionType === annotationProtectionTypeEnum.EntityAccessors" matTooltip="{{'ANNOTATION-DIALOG.PROTECTION.ENTITY-ACCESSORS' | translate}}">
<div class="col"> <div class="col-auto ml-auto">
<div class="row reply-content"> <i class="material-icons protection-icon icon-{{getAnnotationProtectionType(thread)}}"></i>{{getAnnotationProtectionType(thread)}}
<div class="col-12"> </div>
<div class="row h-100"> </div>
<div class="col-10 annotation-time">{{getParentAnnotation(thread).timeStamp | date:'EEEE, MMMM d, y, h:mm a'}}</div> <div class="row thread mb-2">
<div class="col-auto" *ngIf="getParentAnnotation(thread).protectionType === annotationProtectionTypeEnum.Private" matTooltip="{{'ANNOTATION-DIALOG.PROTECTION.PRIVATE' | translate}}"><i class="material-icons protection-icon icon-{{getAnnotationProtectionType(thread)}}"></i>{{getAnnotationProtectionType(thread)}}</div> <!-- Parent Thread -->
<div class="col-auto" *ngIf="getParentAnnotation(thread).protectionType === annotationProtectionTypeEnum.EntityAccessors" matTooltip="{{'ANNOTATION-DIALOG.PROTECTION.ENTITY-ACCESSORS' | translate}}"><i class="material-icons protection-icon icon-{{getAnnotationProtectionType(thread)}}"></i>{{getAnnotationProtectionType(thread)}}</div> <div class="col-12">
<div class="col-md-12 annotation-full-text">{{getParentAnnotation(thread).payload}}</div> <div class="row parent-thread m-0 h-100">
<div class="col-md-12"> <div class="col-auto pr-0 pl-0">
<em class="user">{{'ANNOTATION-DIALOG.THREADS.FROM-USER' | translate}} {{getParentAnnotation(thread).author.name}}</em> <div class="side-color"></div>
</div>
<div class="col">
<div class="row reply-content">
<div class="col-12">
<div class="row h-100">
<div class="col-auto">
<img class="profile-picture" src="/assets/images/user-profile-2.png" alt="profile-picture">
</div>
<div class="col">
<div class="row">
<span class="col user">{{getParentAnnotation(thread).author.name}}</span>
<div class="col-auto annotation-time">{{getParentAnnotation(thread).timeStamp | date: "d MMMM, y 'at' h:mm a"}}</div>
<!-- <em class="col user">{{'ANNOTATION-DIALOG.THREADS.FROM-USER' | translate}} {{getParentAnnotation(thread).author.name}}</em> -->
<!-- <div class="col annotation-time">{{getParentAnnotation(thread).timeStamp | date:'EEEE, MMMM d, y, h:mm a'}}</div> -->
</div>
<div class="row pt-1 pb-1">
<div class="col-12 annotation-full-text">{{getParentAnnotation(thread).payload}}</div>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div>
<!-- Previous Replies --> <!-- Previous Replies -->
<div class="col-12"> <div class="col-12">
<div *ngFor="let annotation of annotationsPerThread[thread]; let i = index;" class="row replies"> <div *ngFor="let annotation of annotationsPerThread[thread]; let i = index;" class="row replies">
<div class="col-auto pr-0"> <div class="col-auto pr-0">
<div class="col reply child"></div> <div class="col reply child"></div>
<div class="col reply child dummy-for-next-child" *ngIf="i != annotationsPerThread[thread].length - 1"></div> <div class="col reply child dummy-for-next-child" *ngIf="i != annotationsPerThread[thread].length - 1"></div>
</div> </div>
<div class="col pl-0 pt-1"> <div class="col pl-0 pt-1">
<div class="parent row m-0"> <div class="parent row m-0">
<div class="col-auto pl-0 pr-0"> <div class="col-auto pl-0 pr-0">
<div class="side-soft-color"></div> <div class="side-soft-color"></div>
</div> </div>
<div class="col reply-content"> <div class="col reply-content">
<div class="row h-100"> <div class="row h-100">
<div class="col-md-12 annotation-time">{{annotation.timeStamp | date:'EEEE, MMMM d, y, h:mm a'}}</div> <div class="col-auto">
<div class="col-md-12 annotation-full-text">{{annotation.payload}}</div> <img class="profile-picture" src="/assets/images/user-profile-2.png" alt="profile-picture">
<div class="col-md-12"> </div>
<em class="gr-color">{{'ANNOTATION-DIALOG.THREADS.FROM-USER' | translate}}</em> <div class="col">
{{annotation.author.name}} <div class="row">
<div class="col">
<span class="user">{{annotation.author.name}}</span>
</div>
<div class="col-auto annotation-time">{{annotation.timeStamp | date:"d MMMM, y 'at' h:mm a"}}</div>
<!-- <div class="col annotation-time">{{annotation.timeStamp | date:'EEEE, MMMM d, y, h:mm a'}}</div> -->
</div>
<div class="row pt-1 pb-1">
<div class="col-md-12 annotation-full-text">{{annotation.payload}}</div>
</div>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</div>
<!-- Type reply in thread --> <!-- Type reply in thread -->
<!-- <div *ngIf="this.canEdit && !this.isDeleted" class="col-12"> --> <!-- <div *ngIf="this.canEdit && !this.isDeleted" class="col-12"> -->
<div class="col-12"> <div class="col-12 mt-2">
<div class="row new-reply mr-0"> <div class="row new-reply mr-0">
<mat-form-field class="col pt-2 pb-2 pr-0">
<textarea matInput matTextareaAutosize matAutosizeMinRows="1" [formControl]="this.threadReplyTextsFG[thread.toString()].get('replyText')" placeholder="{{'ANNOTATION-DIALOG.THREADS.REPLY' | translate}}"></textarea> <mat-form-field appearance="outline" class="col">
<mat-error *ngIf="this.threadReplyTextsFG[thread.toString()]?.get('replyText')?.hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error> <mat-label>{{'ANNOTATION-DIALOG.THREADS.REPLY' | translate}}</mat-label>
</mat-form-field> <input matInput [formControl]="this.threadReplyTextsFG[thread.toString()].get('replyText')" required>
<div class="col-auto send-msg"> <mat-icon matSuffix class="material-symbols-outlined">
<button class="form-field-margin" mat-icon-button type="button" color="accent" (click)="replyThread(thread)" matTooltip="{{'ANNOTATION-DIALOG.THREADS.REPLY' | translate}}"> add_reaction
<i class="fa fa-paper-plane"></i> </mat-icon>
</button> </mat-form-field>
<!--
<mat-form-field class="col pt-2 pb-2 pr-0">
<textarea matInput matTextareaAutosize matAutosizeMinRows="1" [formControl]="this.threadReplyTextsFG[thread.toString()].get('replyText')" placeholder="{{'ANNOTATION-DIALOG.THREADS.REPLY' | translate}}"></textarea>
<mat-error *ngIf="this.threadReplyTextsFG[thread.toString()]?.get('replyText')?.hasError('required')">{{'COMMONS.VALIDATION.REQUIRED' | translate}}</mat-error>
</mat-form-field> -->
<div class="col-auto send-msg">
<button class="form-field-margin" mat-icon-button type="button" color="black" (click)="replyThread(thread)" matTooltip="{{'ANNOTATION-DIALOG.THREADS.REPLY' | translate}}">
<i class="fa fa-paper-plane"></i>
</button>
</div>
</div> </div>
</div> </div>
</div> </div>
</div> </ng-container>
</div> </div>
</div> </div>
</div> </div>

View File

@ -1,3 +1,5 @@
$mat-card-header-size: 40px !default;
::ng-deep .mat-dialog-container { ::ng-deep .mat-dialog-container {
border-radius: 8px; border-radius: 8px;
} }
@ -5,7 +7,7 @@
.form-container { .form-container {
width: 100%; width: 100%;
min-height: 14rem; min-height: 14rem;
padding: 1rem; padding: 1rem 2rem 2rem 2rem;
} }
.logo { .logo {
@ -66,3 +68,20 @@
.warn { .warn {
color: #f16868; color: #f16868;
} }
.profile-picture {
height: $mat-card-header-size;
width: $mat-card-header-size;
border-radius: 50%;
flex-shrink: 0;
}
.thread {
padding: 1em 0 0 0;
background-color: #F5F5F5;
margin: 1em 0 0 0;
}
.user {
font-weight: bold;
}

View File

@ -18,7 +18,7 @@ import { takeUntil } from 'rxjs/operators';
import { nameof } from 'ts-simple-nameof'; import { nameof } from 'ts-simple-nameof';
@Component({ @Component({
selector: 'app-start-new-dmp', selector: 'app-annotation-dialog',
templateUrl: './annotation-dialog.component.html', templateUrl: './annotation-dialog.component.html',
styleUrls: ['./annotation-dialog.component.scss'] styleUrls: ['./annotation-dialog.component.scss']
}) })
@ -139,6 +139,7 @@ export class AnnotationDialogComponent extends BaseComponent {
.pipe(takeUntil(this._destroyed)) .pipe(takeUntil(this._destroyed))
.subscribe( .subscribe(
data => { data => {
console.log(data);
this.annotationsPerThread = {}; this.annotationsPerThread = {};
this.parentAnnotationsPerThread = {}; this.parentAnnotationsPerThread = {};
this.threads = new Set(); this.threads = new Set();
@ -152,6 +153,7 @@ export class AnnotationDialogComponent extends BaseComponent {
this.parentAnnotationsPerThread[element.threadId.toString()] = data.items.filter(x => x.threadId === element.threadId && x.id === element.id)[0]; this.parentAnnotationsPerThread[element.threadId.toString()] = data.items.filter(x => x.threadId === element.threadId && x.id === element.id)[0];
this.threads.add(element.threadId); this.threads.add(element.threadId);
}); });
console.log(this.parentAnnotationsPerThread);
// console.log(this.comments); // console.log(this.comments);
// console.log(this.threads); // console.log(this.threads);
// console.log(this.parentAnnotationsPerThread); // console.log(this.parentAnnotationsPerThread);

View File

@ -55,7 +55,7 @@
</mat-option> </mat-option>
</mat-select> </mat-select>
<mat-error *ngIf="formGroup.get('descriptionTemplateId').hasError('backendError')">{{formGroup.get('descriptionTemplateId').getError('backendError').message}}</mat-error> <mat-error *ngIf="formGroup.get('descriptionTemplateId').hasError('backendError')">{{formGroup.get('descriptionTemplateId').getError('backendError').message}}</mat-error>
<mat-error *ngIf="formGroup.get('label').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error> <mat-error *ngIf="formGroup.get('descriptionTemplateId').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
</mat-form-field> </mat-form-field>
</div> </div>
</div> </div>

View File

@ -1,5 +1,6 @@
import { Component, Input } from '@angular/core'; import { Component, Input } from '@angular/core';
import { UntypedFormGroup } from '@angular/forms'; import { UntypedFormGroup } from '@angular/forms';
import { IsActive } from '@app/core/common/enum/is-active.enum';
import { DescriptionTemplate } from '@app/core/model/description-template/description-template'; import { DescriptionTemplate } from '@app/core/model/description-template/description-template';
import { Description } from '@app/core/model/description/description'; import { Description } from '@app/core/model/description/description';
import { DmpBlueprintDefinitionSection } from '@app/core/model/dmp-blueprint/dmp-blueprint'; import { DmpBlueprintDefinitionSection } from '@app/core/model/dmp-blueprint/dmp-blueprint';
@ -26,10 +27,10 @@ export class DescriptionBaseFieldsEditorComponent extends BaseComponent {
) { super(); } ) { super(); }
ngOnInit() { ngOnInit() {
const dmpDescriptionTemplates: DmpDescriptionTemplate[] = this.description.dmp.dmpDescriptionTemplates.filter(x => x.sectionId == this.description.dmpDescriptionTemplate.sectionId); const dmpDescriptionTemplates: DmpDescriptionTemplate[] = this.description.dmp.dmpDescriptionTemplates.filter(x => x.sectionId == this.description.dmpDescriptionTemplate.sectionId && x.isActive == IsActive.Active);
const currentVersionsOfDescriptionTemplates = dmpDescriptionTemplates.map(x => x.currentDescriptionTemplate); const currentVersionsOfDescriptionTemplates = dmpDescriptionTemplates.map(x => x.currentDescriptionTemplate);
//Check if the used tempalte in included in the current list. If not add it. //Check if the used tempalte in included in the current list. If not add it.
if (currentVersionsOfDescriptionTemplates.find(x => x.id == this.description?.descriptionTemplate?.id) == null) { if (this.description.descriptionTemplate && currentVersionsOfDescriptionTemplates.find(x => x.id == this.description?.descriptionTemplate?.id) == null) {
this.availableDescriptionTemplates.push(this.description.descriptionTemplate) this.availableDescriptionTemplates.push(this.description.descriptionTemplate)
} }
this.availableDescriptionTemplates.push(...currentVersionsOfDescriptionTemplates); this.availableDescriptionTemplates.push(...currentVersionsOfDescriptionTemplates);

View File

@ -32,17 +32,9 @@
<mat-icon [disabled]="isDirty()" style="width: 14px;">expand_more</mat-icon> <mat-icon [disabled]="isDirty()" style="width: 14px;">expand_more</mat-icon>
</button> </button>
<mat-menu #exportMenu="matMenu" xPosition="before"> <mat-menu #exportMenu="matMenu" xPosition="before">
<button mat-menu-item (click)="downloadPDF(formGroup.get('id').value)"> <button mat-menu-item *ngFor='let fileTransformer of fileTransformerService.availableFormats' (click)="fileTransformerService.exportDescription(formGroup.get('id').value, fileTransformer.repositoryId, fileTransformer.format)">
<i class="fa fa-file-pdf-o pr-2"></i> <i class="fa pr-2" [ngClass]="fileTransformer.icon ? fileTransformer.icon : 'fa-file-o'"></i>
<span>{{'GENERAL.FILE-TRANSFOMER.PDF' | translate}}</span> <span>{{'GENERAL.FILE-TRANSFORMER.' + fileTransformer?.format?.toUpperCase() | translate}}</span>
</button>
<button mat-menu-item (click)="downloadDOCX(formGroup.get('id').value)">
<i class="fa fa-file-word-o pr-2"></i>
<span>{{'GENERAL.FILE-TRANSFOMER.DOC' | translate}}</span>
</button>
<button mat-menu-item (click)="downloadXML(formGroup.get('id').value)">
<i class="fa fa-file-code-o pr-2"></i>
<span>{{'GENERAL.FILE-TRANSFOMER.XML' | translate}}</span>
</button> </button>
</mat-menu> </mat-menu>
</div> </div>

View File

@ -42,6 +42,7 @@ import { TableOfContentsComponent } from './table-of-contents/table-of-contents.
import { FormValidationErrorsDialogComponent } from '@common/forms/form-validation-errors-dialog/form-validation-errors-dialog.component'; import { FormValidationErrorsDialogComponent } from '@common/forms/form-validation-errors-dialog/form-validation-errors-dialog.component';
import { ConfigurationService } from '@app/core/services/configuration/configuration.service'; import { ConfigurationService } from '@app/core/services/configuration/configuration.service';
import { LockTargetType } from '@app/core/common/enum/lock-target-type'; import { LockTargetType } from '@app/core/common/enum/lock-target-type';
import { FileTransformerService } from '@app/core/services/file-transformer/file-transformer.service';
@Component({ @Component({
selector: 'app-description-editor-component', selector: 'app-description-editor-component',
@ -104,7 +105,8 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
private fileUtils: FileUtils, private fileUtils: FileUtils,
private matomoService: MatomoService, private matomoService: MatomoService,
private dmpService: DmpService, private dmpService: DmpService,
public visibilityRulesService: VisibilityRulesService public visibilityRulesService: VisibilityRulesService,
public fileTransformerService: FileTransformerService,
) { ) {
super(dialog, language, formService, router, uiNotificationService, httpErrorHandlingService, filterService, datePipe, route, queryParamsService, lockService, authService, configurationService); super(dialog, language, formService, router, uiNotificationService, httpErrorHandlingService, filterService, datePipe, route, queryParamsService, lockService, authService, configurationService);
@ -573,7 +575,10 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
// this.selectedSystemFields = this.selectedSystemFieldDisabled(); // this.selectedSystemFields = this.selectedSystemFieldDisabled();
this.descriptionEditorService.setValidationErrorModel(this.editorModel.validationErrorModel); this.descriptionEditorService.setValidationErrorModel(this.editorModel.validationErrorModel);
if (this.editorModel.status == DescriptionStatus.Finalized || this.isDeleted) { if (this.editorModel.status == DescriptionStatus.Finalized || this.isDeleted) {
this.viewOnly = true;
this.formGroup.disable(); this.formGroup.disable();
}else{
this.viewOnly = false;
} }
this.registerFormListeners(); this.registerFormListeners();
@ -616,7 +621,7 @@ export class DescriptionEditorComponent extends BaseEditor<DescriptionEditorMode
return; return;
} }
this.persistEntity(); // this.persistEntity();
} }
public delete() { public delete() {

View File

@ -414,7 +414,7 @@ export class DescriptionFieldEditorModel implements DescriptionFieldPersist {
textValue: string; textValue: string;
textListValue: string[]; textListValue: string[];
dateValue: Date; dateValue: Date;
references: ReferencePersist[]; references: ReferencePersist[] = [];
reference: ReferencePersist; reference: ReferencePersist;
externalIdentifier?: DescriptionExternalIdentifierEditorModel = new DescriptionExternalIdentifierEditorModel(this.validationErrorModel); externalIdentifier?: DescriptionExternalIdentifierEditorModel = new DescriptionExternalIdentifierEditorModel(this.validationErrorModel);
@ -429,9 +429,35 @@ export class DescriptionFieldEditorModel implements DescriptionFieldPersist {
this.textValue = item.textValue; this.textValue = item.textValue;
this.textListValue = item.textListValue; this.textListValue = item.textListValue;
this.dateValue = item.dateValue; this.dateValue = item.dateValue;
//TODO: refactor reference type
// this.references = descriptionReferences?.filter(x => x.data?.fieldId == descriptionTemplateField?.id && x.isActive == IsActive.Active).map(x => x.reference); this.reference = descriptionReferences?.filter(x => descriptionTemplateField.data.multipleSelect == false && x.data?.fieldId == descriptionTemplateField?.id && x.isActive == IsActive.Active).map(x => {
// this.reference = descriptionReferences?.find(x => x.data?.fieldId == descriptionTemplateField?.id && x.isActive == IsActive.Active)?.reference; return {
id: x.reference.id,
label: x.reference.label,
reference: x.reference.reference,
source: x.reference.source,
typeId: x.reference.type.id,
description: x.reference.source,
definition: x.reference.definition,
abbreviation: x.reference.abbreviation,
sourceType: x.reference.sourceType
}
})[0];
this.references = descriptionReferences?.filter(x => x.data?.fieldId == descriptionTemplateField?.id && x.isActive == IsActive.Active).map(x => {
return {
id: x.reference.id,
label: x.reference.label,
reference: x.reference.reference,
source: x.reference.source,
typeId: x.reference.type.id,
description: x.reference.source,
definition: x.reference.definition,
abbreviation: x.reference.abbreviation,
sourceType: x.reference.sourceType
}
});
this.externalIdentifier = new DescriptionExternalIdentifierEditorModel(this.validationErrorModel).fromModel(item.externalIdentifier); this.externalIdentifier = new DescriptionExternalIdentifierEditorModel(this.validationErrorModel).fromModel(item.externalIdentifier);
} }
return this; return this;

View File

@ -2,7 +2,7 @@ import { Injectable } from '@angular/core';
import { ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router'; import { ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
import { AppPermission } from '@app/core/common/enum/permission.enum'; import { AppPermission } from '@app/core/common/enum/permission.enum';
import { DescriptionTemplate, DescriptionTemplateBaseFieldData, DescriptionTemplateDefinition, DescriptionTemplateExternalDatasetData, DescriptionTemplateField, DescriptionTemplateFieldSet, DescriptionTemplateMultiplicity, DescriptionTemplatePage, DescriptionTemplateReferenceTypeData, DescriptionTemplateRule, DescriptionTemplateSection, DescriptionTemplateSelectData, DescriptionTemplateSelectOption, DescriptionTemplateUploadData, DescriptionTemplateUploadOption } from '@app/core/model/description-template/description-template'; import { DescriptionTemplate, DescriptionTemplateBaseFieldData, DescriptionTemplateDefinition, DescriptionTemplateExternalDatasetData, DescriptionTemplateField, DescriptionTemplateFieldSet, DescriptionTemplateMultiplicity, DescriptionTemplatePage, DescriptionTemplateReferenceTypeData, DescriptionTemplateRule, DescriptionTemplateSection, DescriptionTemplateSelectData, DescriptionTemplateSelectOption, DescriptionTemplateUploadData, DescriptionTemplateUploadOption } from '@app/core/model/description-template/description-template';
import { Description, DescriptionExternalIdentifier, DescriptionField, DescriptionPropertyDefinition, DescriptionPropertyDefinitionFieldSet, DescriptionPropertyDefinitionFieldSetItem, DescriptionReference, DescriptionTag } from '@app/core/model/description/description'; import { Description, DescriptionExternalIdentifier, DescriptionField, DescriptionPropertyDefinition, DescriptionPropertyDefinitionFieldSet, DescriptionPropertyDefinitionFieldSetItem, DescriptionReference, DescriptionReferenceData, DescriptionTag } from '@app/core/model/description/description';
import { DescriptionTemplatesInSection, DmpBlueprint, DmpBlueprintDefinition, DmpBlueprintDefinitionSection } from '@app/core/model/dmp-blueprint/dmp-blueprint'; import { DescriptionTemplatesInSection, DmpBlueprint, DmpBlueprintDefinition, DmpBlueprintDefinitionSection } from '@app/core/model/dmp-blueprint/dmp-blueprint';
import { Dmp, DmpDescriptionTemplate } from '@app/core/model/dmp/dmp'; import { Dmp, DmpDescriptionTemplate } from '@app/core/model/dmp/dmp';
import { ReferenceType } from '@app/core/model/reference-type/reference-type'; import { ReferenceType } from '@app/core/model/reference-type/reference-type';
@ -57,6 +57,7 @@ export class DescriptionEditorResolver extends BaseEditorResolver {
[nameof<Description>(x => x.dmpDescriptionTemplate), nameof<DmpDescriptionTemplate>(x => x.id)].join('.'), [nameof<Description>(x => x.dmpDescriptionTemplate), nameof<DmpDescriptionTemplate>(x => x.id)].join('.'),
[nameof<Description>(x => x.dmpDescriptionTemplate), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'), [nameof<Description>(x => x.dmpDescriptionTemplate), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'),
[nameof<Description>(x => x.dmpDescriptionTemplate), nameof<DmpDescriptionTemplate>(x => x.isActive)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.comment)].join('.'), [nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.comment)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.ordinal)].join('.'), [nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.ordinal)].join('.'),
@ -65,14 +66,24 @@ export class DescriptionEditorResolver extends BaseEditorResolver {
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.dateValue)].join('.'), [nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.dateValue)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.externalIdentifier), nameof<DescriptionExternalIdentifier>(x => x.identifier)].join('.'), [nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.externalIdentifier), nameof<DescriptionExternalIdentifier>(x => x.identifier)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.externalIdentifier), nameof<DescriptionExternalIdentifier>(x => x.type)].join('.'), [nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.externalIdentifier), nameof<DescriptionExternalIdentifier>(x => x.type)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.references), nameof<Reference>(x => x.id)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.references), nameof<Reference>(x => x.label)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.references), nameof<Reference>(x => x.type), nameof<ReferenceType>(x => x.id)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.references), nameof<Reference>(x => x.reference)].join('.'),
[nameof<Description>(x => x.properties), nameof<DescriptionPropertyDefinition>(x => x.fieldSets), nameof<DescriptionPropertyDefinitionFieldSet>(x => x.items), nameof<DescriptionPropertyDefinitionFieldSetItem>(x => x.fields), nameof<DescriptionField>(x => x.references), nameof<Reference>(x => x.isActive)].join('.'),
[nameof<Description>(x => x.descriptionTags), nameof<DescriptionTag>(x => x.id),].join('.'), [nameof<Description>(x => x.descriptionTags), nameof<DescriptionTag>(x => x.id),].join('.'),
[nameof<Description>(x => x.descriptionTags), nameof<DescriptionTag>(x => x.tag), nameof<Tag>(x => x.label)].join('.'), [nameof<Description>(x => x.descriptionTags), nameof<DescriptionTag>(x => x.tag), nameof<Tag>(x => x.label)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.data), nameof<DescriptionReferenceData>(x => x.fieldId)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.id)].join('.'), [nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.id)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.label)].join('.'), [nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.label)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.type)].join('.'), [nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.type), nameof<ReferenceType>(x => x.id)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.reference)].join('.'), [nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.reference)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.source)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.reference), nameof<Reference>(x => x.sourceType)].join('.'),
[nameof<Description>(x => x.descriptionReferences), nameof<DescriptionReference>(x => x.isActive)].join('.'),
nameof<Description>(x => x.createdAt), nameof<Description>(x => x.createdAt),
nameof<Description>(x => x.hash), nameof<Description>(x => x.hash),
nameof<Description>(x => x.isActive) nameof<Description>(x => x.isActive)
@ -85,6 +96,7 @@ export class DescriptionEditorResolver extends BaseEditorResolver {
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.label)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.label)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.version)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.version)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.groupId)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.groupId)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.isActive)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.id)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.id)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.ordinal)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.ordinal)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.title)].join('.'), (prefix ? prefix + '.' : '') + [nameof<DescriptionTemplate>(x => x.definition), nameof<DescriptionTemplateDefinition>(x => x.pages), nameof<DescriptionTemplatePage>(x => x.title)].join('.'),
@ -149,6 +161,7 @@ export class DescriptionEditorResolver extends BaseEditorResolver {
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.id)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.id)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.descriptionTemplateGroupId)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.descriptionTemplateGroupId)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.isActive)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.id)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.id)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.label)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.label)].join('.'),
(prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.version)].join('.'), (prefix ? prefix + '.' : '') + [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.currentDescriptionTemplate), nameof<DescriptionTemplate>(x => x.version)].join('.'),

View File

@ -46,10 +46,10 @@ export class DmpEditorModel extends BaseEditorModel implements DmpPersist {
item.blueprint.definition.sections.forEach(section => { item.blueprint.definition.sections.forEach(section => {
if (section.hasTemplates) { if (section.hasTemplates) {
const sectionTempaltesFromDmp = item.dmpDescriptionTemplates?.filter(x => x.sectionId == section.id) || []; const sectionTempaltesFromDmp = item.dmpDescriptionTemplates?.filter(x => x.sectionId == section.id && x.isActive == IsActive.Active) || [];
if (sectionTempaltesFromDmp.length > 0) { if (sectionTempaltesFromDmp.length > 0) {
item.dmpDescriptionTemplates?.filter(x => x.sectionId == section.id).forEach(dmpDescriptionTemplate => { sectionTempaltesFromDmp?.filter(x => x.sectionId == section.id).forEach(dmpDescriptionTemplate => {
this.descriptionTemplates.push(new DmpDescriptionTemplateEditorModel(this.validationErrorModel).fromModel( this.descriptionTemplates.push(new DmpDescriptionTemplateEditorModel(this.validationErrorModel).fromModel(
{ {
sectionId: section.id, sectionId: section.id,
@ -57,7 +57,7 @@ export class DmpEditorModel extends BaseEditorModel implements DmpPersist {
})); }));
}); });
} else if (section.descriptionTemplates?.length > 0) { } else if (section.descriptionTemplates?.length > 0) {
section.descriptionTemplates.forEach(blueprintDefinedDescriptionTemplate => { sectionTempaltesFromDmp.forEach(blueprintDefinedDescriptionTemplate => {
this.descriptionTemplates.push(new DmpDescriptionTemplateEditorModel(this.validationErrorModel).fromModel( this.descriptionTemplates.push(new DmpDescriptionTemplateEditorModel(this.validationErrorModel).fromModel(
{ {
sectionId: section.id, sectionId: section.id,
@ -294,28 +294,22 @@ export class DmpBlueprintValueEditorModel implements DmpBlueprintValuePersist {
fromModel(item: DmpBlueprintValue, dmpReferences: DmpReference[]): DmpBlueprintValueEditorModel { fromModel(item: DmpBlueprintValue, dmpReferences: DmpReference[]): DmpBlueprintValueEditorModel {
this.fieldId = item.fieldId; this.fieldId = item.fieldId;
this.fieldValue = item.fieldValue; this.fieldValue = item.fieldValue;
// TODO check typeId field this.references = dmpReferences?.filter(x => x.data.blueprintFieldId == this.fieldId && x.isActive == IsActive.Active).map(x => {
if(dmpReferences){ return {
dmpReferences.forEach(dmpReference => { data: x.data,
if(dmpReference.data.blueprintFieldId == this.fieldId){ reference: {
this.references.push({ id: x.reference.id,
data: dmpReference.data, label: x.reference.label,
reference: { reference: x.reference.reference,
id: dmpReference.reference.id, source: x.reference.source,
label: dmpReference.reference.label, typeId: x.reference.type?.id,
reference: dmpReference.reference.reference, description: x.reference.source,
source: dmpReference.reference.source, definition: x.reference.definition,
typeId: null, abbreviation: x.reference.abbreviation,
description: dmpReference.reference.source, sourceType: x.reference.sourceType
definition: dmpReference.reference.definition,
abbreviation: dmpReference.reference.abbreviation,
sourceType: dmpReference.reference.sourceType
}
})
} }
}) }
} });
return this; return this;
} }

View File

@ -82,6 +82,7 @@ export class DmpEditorResolver extends BaseEditorResolver {
[nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'), [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.sectionId)].join('.'),
[nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.descriptionTemplateGroupId)].join('.'), [nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.descriptionTemplateGroupId)].join('.'),
[nameof<Dmp>(x => x.dmpDescriptionTemplates), nameof<DmpDescriptionTemplate>(x => x.isActive)].join('.'),
// nameof<Dmp>(x => x.id), // nameof<Dmp>(x => x.id),

View File

@ -23,14 +23,11 @@ import { takeUntil } from 'rxjs/operators';
styleUrls: ['./dmp-deposit-dropdown.component.scss'] styleUrls: ['./dmp-deposit-dropdown.component.scss']
}) })
export class DmpDepositDropdown extends BaseComponent implements OnInit { export class DmpDepositDropdown extends BaseComponent implements OnInit {
@Input() @Input() inputRepos: DepositConfiguration[];
inputRepos: DepositConfiguration[]; @Input() dmp: Dmp;
@Input()
dmp: Dmp;
outputRepos = []; outputRepos = [];
logos: Map<string, SafeResourceUrl> = new Map<string, SafeResourceUrl>(); logos: Map<string, SafeResourceUrl> = new Map<string, SafeResourceUrl>();
@Output() @Output() outputReposEmitter: EventEmitter<EntityDoi[]> = new EventEmitter<EntityDoi[]>();
outputReposEmitter: EventEmitter<EntityDoi[]> = new EventEmitter<EntityDoi[]>();
private oauthLock: boolean; private oauthLock: boolean;
constructor( constructor(
@ -50,7 +47,7 @@ export class DmpDepositDropdown extends BaseComponent implements OnInit {
} }
ngOnInit(): void { ngOnInit(): void {
for (var i = 0; i < this.dmp.entityDois.length; i++) { for (var i = 0; i < this.dmp?.entityDois?.length; i++) {
this.inputRepos = this.inputRepos.filter(r => this.hasDoi(r, this.dmp.entityDois, i)); this.inputRepos = this.inputRepos.filter(r => this.hasDoi(r, this.dmp.entityDois, i));
} }
this.inputRepos.forEach(repo => { this.inputRepos.forEach(repo => {

View File

@ -501,7 +501,7 @@ export class DmpOverviewComponent extends BaseComponent implements OnInit {
} }
get inputRepos() { get inputRepos() {
return this.depositRepos.filter(repo => !this.dmp.entityDois.find(doi => doi.repositoryId === repo.repositoryId)); return this.depositRepos.filter(repo => !this.dmp.entityDois?.find(doi => doi.repositoryId === repo.repositoryId));
} }
moreDeposit() { moreDeposit() {

View File

@ -9,12 +9,14 @@ import { CommonUiModule } from '@common/ui/common-ui.module';
import { NgDialogAnimationService } from 'ng-dialog-animation'; import { NgDialogAnimationService } from 'ng-dialog-animation';
import { DmpFinalizeDialogModule } from '../dmp-finalize-dialog/dmp-finalize-dialog.module'; import { DmpFinalizeDialogModule } from '../dmp-finalize-dialog/dmp-finalize-dialog.module';
import { DmpOverviewRoutingModule } from './dmp-overview.routing'; import { DmpOverviewRoutingModule } from './dmp-overview.routing';
import { MultipleChoiceDialogModule } from '@common/modules/multiple-choice-dialog/multiple-choice-dialog.module';
@NgModule({ @NgModule({
imports: [ imports: [
CommonUiModule, CommonUiModule,
CommonFormsModule, CommonFormsModule,
ConfirmationDialogModule, ConfirmationDialogModule,
MultipleChoiceDialogModule,
FormattingModule, FormattingModule,
AutoCompleteModule, AutoCompleteModule,
DmpOverviewRoutingModule, DmpOverviewRoutingModule,

View File

@ -121,7 +121,7 @@ export class InAppNotificationEditorComponent extends BaseComponent implements O
} }
onCallbackSuccess(data?: any): void { onCallbackSuccess(data?: any): void {
// this.uiNotificationService.snackBarNotification(this.language.instant('COMMONS.SNACK-BAR.SUCCESSFUL-UPDATE'), SnackBarNotificationLevel.Success); // this.uiNotificationService.snackBarNotification(this.language.instant('GENERAL.SNACK-BAR.SUCCESSFUL-UPDATE'), SnackBarNotificationLevel.Success);
// this.router.navigate(['/mine-notifications']); // this.router.navigate(['/mine-notifications']);
} }

View File

@ -590,6 +590,36 @@ hr {
font-weight: 500; font-weight: 500;
} }
.normal-btn-sm {
min-width: 100px;
max-width: 256px;
height: 40px;
cursor: pointer;
background: var(--primary-color) 0% 0% no-repeat padding-box;
box-shadow: 0px 3px 6px #1E202029;
border-radius: 30px;
border: none;
color: #FFFFFF;
opacity: 1;
font-size: 0.87rem;
padding: 0.62rem 1.87rem;
font-weight: 400;
}
.normal-btn-light-sm {
background: #ffffff 0% 0% no-repeat padding-box;
box-shadow: 0px 3px 6px #1E202029;
border: 1px solid var(--primary-color);
border-radius: 30px;
opacity: 1;
min-width: 100px;
max-width: 256px;
height: 40px;
color: var(--primary-color);
font-size: 0.87rem;
font-weight: 400;
}
.mirror { .mirror {
-webkit-transform: scaleX(-1); -webkit-transform: scaleX(-1);
transform: scaleX(-1); transform: scaleX(-1);

View File

@ -254,7 +254,8 @@
"THREADS": { "THREADS": {
"NEW-THREAD": "New comment", "NEW-THREAD": "New comment",
"FROM-USER": "From", "FROM-USER": "From",
"SEND": "Send comment", "SEND": "Send",
"CANCEL": "Cancel",
"REPLY": "Reply", "REPLY": "Reply",
"PROTECTION": { "PROTECTION": {
"TITLE": "Visibility" "TITLE": "Visibility"

Binary file not shown.

After

Width:  |  Height:  |  Size: 214 KiB

View File

@ -109,7 +109,7 @@ export abstract class BaseEditor<EditorModelType extends BaseEditorModel, Entity
console.log("Success:", data); console.log("Success:", data);
this.uiNotificationService.snackBarNotification(this.isNew ? this.language.instant('COMMONS.SNACK-BAR.SUCCESSFUL-CREATION') : this.language.instant('COMMONS.SNACK-BAR.SUCCESSFUL-UPDATE'), SnackBarNotificationLevel.Success); this.uiNotificationService.snackBarNotification(this.isNew ? this.language.instant('GENERAL.SNACK-BAR.SUCCESSFUL-CREATION') : this.language.instant('GENERAL.SNACK-BAR.SUCCESSFUL-UPDATE'), SnackBarNotificationLevel.Success);
this.refreshOnNavigateToData(data ? data.id : null); this.refreshOnNavigateToData(data ? data.id : null);
} }

View File

@ -10,4 +10,6 @@ import { MultipleChoiceDialogComponent } from './multiple-choice-dialog.componen
declarations: [MultipleChoiceDialogComponent], declarations: [MultipleChoiceDialogComponent],
exports: [MultipleChoiceDialogComponent] exports: [MultipleChoiceDialogComponent]
}) })
export class MultipleChoiceDialogModule { } export class MultipleChoiceDialogModule {
constructor() { }
}