add Usage Limit periodicity
This commit is contained in:
parent
25c3ae2c11
commit
48434f845e
|
@ -0,0 +1,30 @@
|
|||
package org.opencdmp.commons.enums;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonValue;
|
||||
import org.opencdmp.data.converters.enums.DatabaseEnum;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
public enum UsageLimitPeriodicityRange implements DatabaseEnum<Short> {
|
||||
|
||||
Monthly((short) 0),
|
||||
Yearly((short) 1);
|
||||
|
||||
private final Short value;
|
||||
|
||||
UsageLimitPeriodicityRange(Short value) {
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
@JsonValue
|
||||
public Short getValue() {
|
||||
return value;
|
||||
}
|
||||
|
||||
private static final Map<Short, UsageLimitPeriodicityRange> map = EnumUtils.getEnumValueMap(UsageLimitPeriodicityRange.class);
|
||||
|
||||
public static UsageLimitPeriodicityRange of(Short i) {
|
||||
return map.get(i);
|
||||
}
|
||||
|
||||
}
|
|
@ -10,7 +10,7 @@ public enum AccountingValueType implements DatabaseEnum<Short> {
|
|||
|
||||
Plus((short) 0),
|
||||
Minus((short) 1),
|
||||
Reset((short) 3);
|
||||
Reset((short) 2);
|
||||
|
||||
private final Short value;
|
||||
|
||||
|
|
|
@ -0,0 +1,35 @@
|
|||
package org.opencdmp.commons.types.usagelimit;
|
||||
|
||||
import jakarta.xml.bind.annotation.*;
|
||||
import org.opencdmp.commons.enums.ReferenceFieldDataType;
|
||||
import org.opencdmp.commons.enums.UsageLimitPeriodicityRange;
|
||||
import org.opencdmp.commons.types.reference.FieldEntity;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
@XmlRootElement(name = "definition")
|
||||
@XmlAccessorType(XmlAccessType.FIELD)
|
||||
public class DefinitionEntity {
|
||||
|
||||
@XmlAttribute(name = "hasPeriodicity")
|
||||
private Boolean hasPeriodicity;
|
||||
|
||||
@XmlAttribute(name = "periodicityRange")
|
||||
private UsageLimitPeriodicityRange periodicityRange;
|
||||
|
||||
public Boolean getHasPeriodicity() {
|
||||
return hasPeriodicity;
|
||||
}
|
||||
|
||||
public void setHasPeriodicity(Boolean hasPeriodicity) {
|
||||
this.hasPeriodicity = hasPeriodicity;
|
||||
}
|
||||
|
||||
public UsageLimitPeriodicityRange getPeriodicityRange() {
|
||||
return periodicityRange;
|
||||
}
|
||||
|
||||
public void setPeriodicityRange(UsageLimitPeriodicityRange periodicityRange) {
|
||||
this.periodicityRange = periodicityRange;
|
||||
}
|
||||
}
|
|
@ -1,11 +1,13 @@
|
|||
package org.opencdmp.data;
|
||||
|
||||
import jakarta.persistence.*;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.opencdmp.commons.enums.IsActive;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.data.converters.enums.IsActiveConverter;
|
||||
import org.opencdmp.data.converters.enums.UsageLimitTargetMetricConverter;
|
||||
import org.opencdmp.data.tenant.TenantScopedBaseEntity;
|
||||
import org.opencdmp.data.types.SQLXMLType;
|
||||
|
||||
import java.time.Instant;
|
||||
import java.util.UUID;
|
||||
|
@ -39,6 +41,12 @@ public class UsageLimitEntity extends TenantScopedBaseEntity {
|
|||
|
||||
public static final String _value = "value";
|
||||
|
||||
@Type(SQLXMLType.class)
|
||||
@Column(name = "definition", columnDefinition = "xml")
|
||||
private String definition;
|
||||
|
||||
public static final String _definition = "definition";
|
||||
|
||||
@Column(name = "is_active", nullable = false)
|
||||
@Convert(converter = IsActiveConverter.class)
|
||||
private IsActive isActive;
|
||||
|
@ -87,6 +95,14 @@ public class UsageLimitEntity extends TenantScopedBaseEntity {
|
|||
this.value = value;
|
||||
}
|
||||
|
||||
public String getDefinition() {
|
||||
return definition;
|
||||
}
|
||||
|
||||
public void setDefinition(String definition) {
|
||||
this.definition = definition;
|
||||
}
|
||||
|
||||
public IsActive getIsActive() {
|
||||
return isActive;
|
||||
}
|
||||
|
|
|
@ -49,7 +49,8 @@ public class AccountingEntryCreatedIntegrationEventHandlerImpl implements Accoun
|
|||
event.setType(valueType);
|
||||
event.setResource(tenantCode);
|
||||
event.setUserId(subjectId);
|
||||
event.setValue(1.0);
|
||||
if (valueType != null && valueType.equals(AccountingValueType.Reset)) event.setValue(0.0);
|
||||
else event.setValue(1.0);
|
||||
event.setTenant(tenantId);
|
||||
|
||||
this.handle(event);
|
||||
|
|
|
@ -2,6 +2,7 @@ package org.opencdmp.model;
|
|||
|
||||
import org.opencdmp.commons.enums.IsActive;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.model.usagelimit.Definition;
|
||||
|
||||
import java.time.Instant;
|
||||
import java.util.UUID;
|
||||
|
@ -23,6 +24,9 @@ public class UsageLimit {
|
|||
private IsActive isActive;
|
||||
public static final String _isActive = "isActive";
|
||||
|
||||
private Definition definition;
|
||||
public static final String _definition = "definition";
|
||||
|
||||
private Instant createdAt;
|
||||
public static final String _createdAt = "createdAt";
|
||||
|
||||
|
@ -67,6 +71,14 @@ public class UsageLimit {
|
|||
this.value = value;
|
||||
}
|
||||
|
||||
public Definition getDefinition() {
|
||||
return definition;
|
||||
}
|
||||
|
||||
public void setDefinition(Definition definition) {
|
||||
this.definition = definition;
|
||||
}
|
||||
|
||||
public IsActive getIsActive() {
|
||||
return isActive;
|
||||
}
|
||||
|
|
|
@ -1,14 +1,18 @@
|
|||
package org.opencdmp.model.builder;
|
||||
|
||||
import gr.cite.tools.data.builder.BuilderFactory;
|
||||
import gr.cite.tools.exception.MyApplicationException;
|
||||
import gr.cite.tools.fieldset.FieldSet;
|
||||
import gr.cite.tools.logging.DataLogEntry;
|
||||
import gr.cite.tools.logging.LoggerService;
|
||||
import org.opencdmp.authorization.AuthorizationFlags;
|
||||
import org.opencdmp.commons.XmlHandlingService;
|
||||
import org.opencdmp.commons.scope.tenant.TenantScope;
|
||||
import org.opencdmp.commons.types.usagelimit.DefinitionEntity;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.data.UsageLimitEntity;
|
||||
import org.opencdmp.model.UsageLimit;
|
||||
import org.opencdmp.model.builder.usagelimit.DefinitionBuilder;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
|
@ -22,15 +26,19 @@ import java.util.*;
|
|||
public class UsageLimitBuilder extends BaseBuilder<UsageLimit, UsageLimitEntity> {
|
||||
|
||||
private final TenantScope tenantScope;
|
||||
private final XmlHandlingService xmlHandlingService;
|
||||
private final BuilderFactory builderFactory;
|
||||
|
||||
private EnumSet<AuthorizationFlags> authorize = EnumSet.of(AuthorizationFlags.None);
|
||||
|
||||
@Autowired
|
||||
public UsageLimitBuilder(
|
||||
ConventionService conventionService,
|
||||
TenantScope tenantScope) {
|
||||
ConventionService conventionService,
|
||||
TenantScope tenantScope, XmlHandlingService xmlHandlingService, BuilderFactory builderFactory) {
|
||||
super(conventionService, new LoggerService(LoggerFactory.getLogger(UsageLimitBuilder.class)));
|
||||
this.tenantScope = tenantScope;
|
||||
this.xmlHandlingService = xmlHandlingService;
|
||||
this.builderFactory = builderFactory;
|
||||
}
|
||||
|
||||
public UsageLimitBuilder authorize(EnumSet<AuthorizationFlags> values) {
|
||||
|
@ -45,6 +53,8 @@ public class UsageLimitBuilder extends BaseBuilder<UsageLimit, UsageLimitEntity>
|
|||
if (fields == null || data == null || fields.isEmpty())
|
||||
return new ArrayList<>();
|
||||
|
||||
FieldSet definitionFields = fields.extractPrefixed(this.asPrefix(UsageLimit._definition));
|
||||
|
||||
List<UsageLimit> models = new ArrayList<>();
|
||||
for (UsageLimitEntity d : data) {
|
||||
UsageLimit m = new UsageLimit();
|
||||
|
@ -64,6 +74,10 @@ public class UsageLimitBuilder extends BaseBuilder<UsageLimit, UsageLimitEntity>
|
|||
m.setIsActive(d.getIsActive());
|
||||
if (fields.hasField(this.asIndexer(UsageLimit._hash)))
|
||||
m.setHash(this.hashValue(d.getUpdatedAt()));
|
||||
if (!definitionFields.isEmpty() && d.getDefinition() != null) {
|
||||
DefinitionEntity definition = this.xmlHandlingService.fromXmlSafe(DefinitionEntity.class, d.getDefinition());
|
||||
m.setDefinition(this.builderFactory.builder(DefinitionBuilder.class).authorize(this.authorize).build(definitionFields, definition));
|
||||
}
|
||||
if (fields.hasField(this.asIndexer(UsageLimit._belongsToCurrentTenant))) m.setBelongsToCurrentTenant(this.getBelongsToCurrentTenant(d, this.tenantScope));
|
||||
|
||||
models.add(m);
|
||||
|
|
|
@ -0,0 +1,55 @@
|
|||
package org.opencdmp.model.builder.usagelimit;
|
||||
|
||||
import gr.cite.tools.exception.MyApplicationException;
|
||||
import gr.cite.tools.fieldset.FieldSet;
|
||||
import gr.cite.tools.logging.DataLogEntry;
|
||||
import gr.cite.tools.logging.LoggerService;
|
||||
import org.opencdmp.authorization.AuthorizationFlags;
|
||||
import org.opencdmp.commons.types.usagelimit.DefinitionEntity;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.model.builder.BaseBuilder;
|
||||
import org.opencdmp.model.usagelimit.Definition;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
@Component("usagelimitdefinitionbuilder")
|
||||
@Scope(value = ConfigurableBeanFactory.SCOPE_PROTOTYPE)
|
||||
public class DefinitionBuilder extends BaseBuilder<Definition, DefinitionEntity> {
|
||||
|
||||
private EnumSet<AuthorizationFlags> authorize = EnumSet.of(AuthorizationFlags.None);
|
||||
|
||||
@Autowired
|
||||
public DefinitionBuilder(
|
||||
ConventionService conventionService) {
|
||||
super(conventionService, new LoggerService(LoggerFactory.getLogger(DefinitionBuilder.class)));
|
||||
}
|
||||
|
||||
public DefinitionBuilder authorize(EnumSet<AuthorizationFlags> values) {
|
||||
this.authorize = values;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Definition> build(FieldSet fields, List<DefinitionEntity> data) throws MyApplicationException {
|
||||
this.logger.debug("building for {} items requesting {} fields", Optional.ofNullable(data).map(List::size).orElse(0), Optional.ofNullable(fields).map(FieldSet::getFields).map(Set::size).orElse(0));
|
||||
this.logger.trace(new DataLogEntry("requested fields", fields));
|
||||
if (fields == null || data == null || fields.isEmpty())
|
||||
return new ArrayList<>();
|
||||
|
||||
List<Definition> models = new ArrayList<>();
|
||||
for (DefinitionEntity d : data) {
|
||||
Definition m = new Definition();
|
||||
if (fields.hasField(this.asIndexer(Definition._periodicityRange))) m.setPeriodicityRange(d.getPeriodicityRange());
|
||||
if (fields.hasField(this.asIndexer(Definition._hasPeriodicity))) m.setHasPeriodicity(d.getHasPeriodicity());
|
||||
|
||||
models.add(m);
|
||||
}
|
||||
this.logger.debug("build {} items", Optional.of(models).map(List::size).orElse(0));
|
||||
return models;
|
||||
}
|
||||
}
|
|
@ -7,6 +7,8 @@ import gr.cite.tools.logging.DataLogEntry;
|
|||
import gr.cite.tools.logging.LoggerService;
|
||||
import org.opencdmp.authorization.Permission;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.model.UsageLimit;
|
||||
import org.opencdmp.model.censorship.usagelimit.DefinitionCensor;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
|
@ -35,6 +37,8 @@ public class UsageLimitsCensor extends BaseCensor {
|
|||
return;
|
||||
|
||||
this.authService.authorizeForce(Permission.BrowseUsageLimit);
|
||||
FieldSet definitionFields = fields.extractPrefixed(this.asIndexerPrefix(UsageLimit._definition));
|
||||
this.censorFactory.censor(DefinitionCensor.class).censor(definitionFields);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -0,0 +1,45 @@
|
|||
package org.opencdmp.model.censorship.usagelimit;
|
||||
|
||||
import gr.cite.commons.web.authz.service.AuthorizationService;
|
||||
import gr.cite.tools.data.censor.CensorFactory;
|
||||
import gr.cite.tools.fieldset.FieldSet;
|
||||
import gr.cite.tools.logging.DataLogEntry;
|
||||
import gr.cite.tools.logging.LoggerService;
|
||||
import org.opencdmp.authorization.Permission;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.model.censorship.BaseCensor;
|
||||
import org.opencdmp.model.censorship.reference.FieldCensor;
|
||||
import org.opencdmp.model.reference.Definition;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
@Component("usagelimitdefinitioncensor")
|
||||
@Scope(value = ConfigurableBeanFactory.SCOPE_PROTOTYPE)
|
||||
public class DefinitionCensor extends BaseCensor {
|
||||
|
||||
private static final LoggerService logger = new LoggerService(LoggerFactory.getLogger(DefinitionCensor.class));
|
||||
|
||||
protected final AuthorizationService authService;
|
||||
protected final CensorFactory censorFactory;
|
||||
|
||||
public DefinitionCensor(ConventionService conventionService,
|
||||
AuthorizationService authService,
|
||||
CensorFactory censorFactory) {
|
||||
super(conventionService);
|
||||
this.authService = authService;
|
||||
this.censorFactory = censorFactory;
|
||||
}
|
||||
|
||||
public void censor(FieldSet fields) {
|
||||
logger.debug(new DataLogEntry("censoring fields", fields));
|
||||
if (fields == null || fields.isEmpty())
|
||||
return;
|
||||
|
||||
this.authService.authorizeForce(Permission.BrowseUsageLimit);
|
||||
}
|
||||
|
||||
}
|
|
@ -1,11 +1,13 @@
|
|||
package org.opencdmp.model.persist;
|
||||
|
||||
import gr.cite.tools.validation.ValidatorFactory;
|
||||
import gr.cite.tools.validation.specification.Specification;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.commons.validation.BaseValidator;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.data.UsageLimitEntity;
|
||||
import org.opencdmp.errorcode.ErrorThesaurusProperties;
|
||||
import org.opencdmp.model.persist.usagelimit.DefinitionPersist;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
import org.springframework.context.MessageSource;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
|
@ -30,6 +32,9 @@ public class UsageLimitPersist {
|
|||
private Long value;
|
||||
public static final String _value = "value";
|
||||
|
||||
private DefinitionPersist definition;
|
||||
public static final String _definition = "definition";
|
||||
|
||||
private String hash;
|
||||
public static final String _hash = "hash";
|
||||
|
||||
|
@ -65,6 +70,14 @@ public class UsageLimitPersist {
|
|||
this.value = value;
|
||||
}
|
||||
|
||||
public DefinitionPersist getDefinition() {
|
||||
return definition;
|
||||
}
|
||||
|
||||
public void setDefinition(DefinitionPersist definition) {
|
||||
this.definition = definition;
|
||||
}
|
||||
|
||||
public String getHash() {
|
||||
return this.hash;
|
||||
}
|
||||
|
@ -81,9 +94,12 @@ public class UsageLimitPersist {
|
|||
|
||||
private final MessageSource messageSource;
|
||||
|
||||
protected UsageLimitPersistValidator(ConventionService conventionService, ErrorThesaurusProperties errors, MessageSource messageSource) {
|
||||
private final ValidatorFactory validatorFactory;
|
||||
|
||||
protected UsageLimitPersistValidator(ConventionService conventionService, ErrorThesaurusProperties errors, MessageSource messageSource, ValidatorFactory validatorFactory) {
|
||||
super(conventionService, errors);
|
||||
this.messageSource = messageSource;
|
||||
this.validatorFactory = validatorFactory;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -117,7 +133,12 @@ public class UsageLimitPersist {
|
|||
.failOn(UsageLimitPersist._value).failWith(this.messageSource.getMessage("Validation_Required", new Object[]{UsageLimitPersist._value}, LocaleContextHolder.getLocale())),
|
||||
this.spec()
|
||||
.must(() -> item.getValue() > 0)
|
||||
.failOn(UsageLimitPersist._value).failWith(this.messageSource.getMessage("Validation_UnexpectedValue", new Object[]{UsageLimitPersist._value}, LocaleContextHolder.getLocale()))
|
||||
.failOn(UsageLimitPersist._value).failWith(this.messageSource.getMessage("Validation_UnexpectedValue", new Object[]{UsageLimitPersist._value}, LocaleContextHolder.getLocale())),
|
||||
this.refSpec()
|
||||
.iff(() -> !this.isNull(item.getDefinition()))
|
||||
.on(UsageLimitPersist._definition)
|
||||
.over(item.getDefinition())
|
||||
.using(() -> this.validatorFactory.validator(org.opencdmp.model.persist.usagelimit.DefinitionPersist.DefinitionPersistValidator.class))
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,76 @@
|
|||
package org.opencdmp.model.persist.usagelimit;
|
||||
|
||||
import gr.cite.tools.validation.specification.Specification;
|
||||
import org.opencdmp.commons.enums.UsageLimitPeriodicityRange;
|
||||
import org.opencdmp.commons.validation.BaseValidator;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.errorcode.ErrorThesaurusProperties;
|
||||
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
|
||||
import org.springframework.context.MessageSource;
|
||||
import org.springframework.context.annotation.Scope;
|
||||
import org.springframework.context.i18n.LocaleContextHolder;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
public class DefinitionPersist {
|
||||
|
||||
private Boolean hasPeriodicity;
|
||||
public final static String _hasPeriodicity = "hasPeriodicity";
|
||||
|
||||
private UsageLimitPeriodicityRange periodicityRange;
|
||||
public final static String _periodicityRange = "periodicityRange";
|
||||
|
||||
public Boolean getHasPeriodicity() {
|
||||
return hasPeriodicity;
|
||||
}
|
||||
|
||||
public void setHasPeriodicity(Boolean hasPeriodicity) {
|
||||
this.hasPeriodicity = hasPeriodicity;
|
||||
}
|
||||
|
||||
public UsageLimitPeriodicityRange getPeriodicityRange() {
|
||||
return periodicityRange;
|
||||
}
|
||||
|
||||
public void setPeriodicityRange(UsageLimitPeriodicityRange periodicityRange) {
|
||||
this.periodicityRange = periodicityRange;
|
||||
}
|
||||
|
||||
@Component(DefinitionPersistValidator.ValidatorName)
|
||||
@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE)
|
||||
public static class DefinitionPersistValidator extends BaseValidator<DefinitionPersist> {
|
||||
|
||||
public static final String ValidatorName = "UsageLimit.DefinitionPersistValidator";
|
||||
|
||||
private final MessageSource messageSource;
|
||||
|
||||
|
||||
protected DefinitionPersistValidator(ConventionService conventionService, ErrorThesaurusProperties errors, MessageSource messageSource) {
|
||||
super(conventionService, errors);
|
||||
this.messageSource = messageSource;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Class<DefinitionPersist> modelClass() {
|
||||
return DefinitionPersist.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected List<Specification> specifications(DefinitionPersist item) {
|
||||
return Arrays.asList(
|
||||
this.spec()
|
||||
.must(() -> !this.isNull(item.getHasPeriodicity()))
|
||||
.failOn(DefinitionPersist._hasPeriodicity).failWith(this.messageSource.getMessage("Validation_Required", new Object[]{DefinitionPersist._hasPeriodicity}, LocaleContextHolder.getLocale())),
|
||||
this.spec()
|
||||
.iff(() -> !this.isNull(item.getHasPeriodicity()) && item.getHasPeriodicity())
|
||||
.must(() -> !this.isNull(item.getPeriodicityRange()))
|
||||
.failOn(DefinitionPersist._periodicityRange).failWith(this.messageSource.getMessage("Validation_Required", new Object[]{DefinitionPersist._periodicityRange}, LocaleContextHolder.getLocale()))
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
package org.opencdmp.model.usagelimit;
|
||||
|
||||
import org.opencdmp.commons.enums.UsageLimitPeriodicityRange;
|
||||
|
||||
public class Definition {
|
||||
|
||||
private Boolean hasPeriodicity;
|
||||
public final static String _hasPeriodicity = "hasPeriodicity";
|
||||
|
||||
private UsageLimitPeriodicityRange periodicityRange;
|
||||
public final static String _periodicityRange = "periodicityRange";
|
||||
|
||||
public Boolean getHasPeriodicity() {
|
||||
return hasPeriodicity;
|
||||
}
|
||||
|
||||
public void setHasPeriodicity(Boolean hasPeriodicity) {
|
||||
this.hasPeriodicity = hasPeriodicity;
|
||||
}
|
||||
|
||||
public UsageLimitPeriodicityRange getPeriodicityRange() {
|
||||
return periodicityRange;
|
||||
}
|
||||
|
||||
public void setPeriodicityRange(UsageLimitPeriodicityRange periodicityRange) {
|
||||
this.periodicityRange = periodicityRange;
|
||||
}
|
||||
}
|
|
@ -194,6 +194,7 @@ public class UsageLimitQuery extends QueryBase<UsageLimitEntity> {
|
|||
item.setLabel(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._label, String.class));
|
||||
item.setTargetMetric(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._targetMetric, UsageLimitTargetMetric.class));
|
||||
item.setValue(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._value, Long.class));
|
||||
item.setDefinition(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._definition, String.class));
|
||||
item.setCreatedAt(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._createdAt, Instant.class));
|
||||
item.setUpdatedAt(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._updatedAt, Instant.class));
|
||||
item.setIsActive(QueryBase.convertSafe(tuple, columns, UsageLimitEntity._isActive, IsActive.class));
|
||||
|
@ -210,6 +211,8 @@ public class UsageLimitQuery extends QueryBase<UsageLimitEntity> {
|
|||
return UsageLimitEntity._targetMetric;
|
||||
else if (item.match(UsageLimit._value))
|
||||
return UsageLimitEntity._value;
|
||||
else if (item.prefix(UsageLimit._definition))
|
||||
return UsageLimitEntity._definition;
|
||||
else if (item.match(UsageLimit._createdAt))
|
||||
return UsageLimitEntity._createdAt;
|
||||
else if (item.match(UsageLimit._updatedAt))
|
||||
|
|
|
@ -3,15 +3,15 @@ package org.opencdmp.service.accounting;
|
|||
import org.opencdmp.commons.types.accounting.AccountingSourceEntity;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
|
||||
import java.time.Instant;
|
||||
import java.util.List;
|
||||
|
||||
@ConfigurationProperties(prefix = "accounting")
|
||||
public class AccountingProperties {
|
||||
private Boolean enabled;
|
||||
private String serviceId;
|
||||
|
||||
private Instant fromInstant;
|
||||
private String subjectId;
|
||||
|
||||
private List<String> projectFields;
|
||||
|
||||
private List<AccountingSourceEntity> sources;
|
||||
|
@ -28,6 +28,14 @@ public class AccountingProperties {
|
|||
this.enabled = enabled;
|
||||
}
|
||||
|
||||
public Instant getFromInstant() {
|
||||
return fromInstant;
|
||||
}
|
||||
|
||||
public void setFromInstant(Instant fromInstant) {
|
||||
this.fromInstant = fromInstant;
|
||||
}
|
||||
|
||||
public void setServiceId(String serviceId) {
|
||||
this.serviceId = serviceId;
|
||||
}
|
||||
|
|
|
@ -1,14 +1,16 @@
|
|||
package org.opencdmp.service.accounting;
|
||||
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.commons.types.usagelimit.DefinitionEntity;
|
||||
|
||||
import javax.management.InvalidApplicationException;
|
||||
import java.util.UUID;
|
||||
|
||||
public interface AccountingService {
|
||||
|
||||
Integer getCurrentMetricValue(UsageLimitTargetMetric metric) throws InvalidApplicationException;
|
||||
Integer getCurrentMetricValue(UsageLimitTargetMetric metric, DefinitionEntity definition) throws InvalidApplicationException;
|
||||
|
||||
void set(String metric);
|
||||
void set(String metric, UUID tenantId, String tenantCode) throws InvalidApplicationException;
|
||||
|
||||
void increase(String metric) throws InvalidApplicationException;
|
||||
|
||||
|
|
|
@ -11,6 +11,7 @@ import gr.cite.tools.exception.MyNotFoundException;
|
|||
import gr.cite.tools.logging.LoggerService;
|
||||
import gr.cite.tools.logging.MapLogEntry;
|
||||
import gr.cite.tools.validation.ValidatorFactory;
|
||||
import org.opencdmp.commons.enums.UsageLimitPeriodicityRange;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.commons.enums.accounting.AccountingAggregateType;
|
||||
import org.opencdmp.commons.enums.accounting.AccountingDataRangeType;
|
||||
|
@ -19,6 +20,7 @@ import org.opencdmp.commons.enums.accounting.AccountingValueType;
|
|||
import org.opencdmp.commons.scope.tenant.TenantScope;
|
||||
import org.opencdmp.commons.scope.user.UserScope;
|
||||
import org.opencdmp.commons.types.accounting.AccountingSourceEntity;
|
||||
import org.opencdmp.commons.types.usagelimit.DefinitionEntity;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.data.UserCredentialEntity;
|
||||
import org.opencdmp.integrationevent.outbox.accountingentrycreated.AccountingEntryCreatedIntegrationEvent;
|
||||
|
@ -47,10 +49,7 @@ import java.security.InvalidAlgorithmParameterException;
|
|||
import java.security.InvalidKeyException;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.time.Instant;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.*;
|
||||
|
||||
@Service
|
||||
public class AccountingServiceImpl implements AccountingService {
|
||||
|
@ -130,7 +129,7 @@ public class AccountingServiceImpl implements AccountingService {
|
|||
});
|
||||
}
|
||||
|
||||
public Integer getCurrentMetricValue(UsageLimitTargetMetric metric) throws InvalidApplicationException {
|
||||
public Integer getCurrentMetricValue(UsageLimitTargetMetric metric, DefinitionEntity definition) throws InvalidApplicationException {
|
||||
if (this.isEnabled) {
|
||||
AccountingClient accountingClient = null;
|
||||
try {
|
||||
|
@ -154,13 +153,20 @@ public class AccountingServiceImpl implements AccountingService {
|
|||
throw new MyNotFoundException(this.messageSource.getMessage("General_ItemNotFound", new Object[]{this.accountingProperties.getSources().getFirst().getRepositoryId(), AccountingClient.class.getSimpleName()}, LocaleContextHolder.getLocale()));
|
||||
|
||||
AccountingInfoLookup lookup = new AccountingInfoLookup();
|
||||
lookup.setTo(Instant.now());
|
||||
lookup.setDateRangeType(AccountingDataRangeType.ThisYear);
|
||||
if (definition.getHasPeriodicity()) {
|
||||
if (definition.getPeriodicityRange().equals(UsageLimitPeriodicityRange.Monthly)) lookup.setDateRangeType(AccountingDataRangeType.ThisMonth);
|
||||
else lookup.setDateRangeType(AccountingDataRangeType.ThisYear);
|
||||
} else {
|
||||
lookup.setDateRangeType(AccountingDataRangeType.Custom);
|
||||
lookup.setTo(Instant.now());
|
||||
lookup.setFrom(this.accountingProperties.getFromInstant());
|
||||
}
|
||||
|
||||
lookup.setMeasure(AccountingMeasureType.Unit);
|
||||
lookup.setServiceCodes(List.of(this.accountingProperties.getServiceId()));
|
||||
lookup.setAggregateTypes(List.of(AccountingAggregateType.Sum));
|
||||
lookup.setActionCodes(List.of(metric.getValue()));
|
||||
lookup.setUserCodes(List.of(this.getSubjectId()));
|
||||
|
||||
try {
|
||||
lookup.setResourceCodes(List.of(this.tenantScope.getTenantCode() != null ? this.tenantScope.getTenantCode() : this.tenantScope.getDefaultTenantCode()));
|
||||
} catch (InvalidApplicationException e) {
|
||||
|
@ -191,8 +197,12 @@ public class AccountingServiceImpl implements AccountingService {
|
|||
return null;
|
||||
}
|
||||
|
||||
public void set(String metric) {
|
||||
//TODO
|
||||
public void set(String metric, UUID tenantId, String tenantCode) throws InvalidApplicationException{
|
||||
if (this.isEnabled) {
|
||||
String subjectId = this.getSubjectId();
|
||||
|
||||
this.accountingEntryCreatedIntegrationEventHandler.handleAccountingEntry(metric, AccountingValueType.Reset, subjectId, tenantId, tenantCode);
|
||||
}
|
||||
}
|
||||
|
||||
public void increase(String metric) throws InvalidApplicationException {
|
||||
|
|
|
@ -5,6 +5,7 @@ import gr.cite.tools.exception.MyForbiddenException;
|
|||
import gr.cite.tools.exception.MyNotFoundException;
|
||||
import gr.cite.tools.exception.MyValidationException;
|
||||
import gr.cite.tools.fieldset.FieldSet;
|
||||
import jakarta.xml.bind.JAXBException;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import org.opencdmp.model.UsageLimit;
|
||||
import org.opencdmp.model.persist.UsageLimitPersist;
|
||||
|
@ -14,7 +15,7 @@ import java.util.UUID;
|
|||
|
||||
public interface UsageLimitService {
|
||||
|
||||
UsageLimit persist(UsageLimitPersist model, FieldSet fields) throws MyForbiddenException, MyValidationException, MyApplicationException, MyNotFoundException, InvalidApplicationException;
|
||||
UsageLimit persist(UsageLimitPersist model, FieldSet fields) throws MyForbiddenException, MyValidationException, MyApplicationException, MyNotFoundException, InvalidApplicationException, JAXBException;
|
||||
|
||||
void deleteAndSave(UUID id) throws MyForbiddenException, InvalidApplicationException;
|
||||
|
||||
|
|
|
@ -11,11 +11,15 @@ import gr.cite.tools.fieldset.BaseFieldSet;
|
|||
import gr.cite.tools.fieldset.FieldSet;
|
||||
import gr.cite.tools.logging.LoggerService;
|
||||
import gr.cite.tools.logging.MapLogEntry;
|
||||
import jakarta.xml.bind.JAXBException;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.opencdmp.authorization.AuthorizationFlags;
|
||||
import org.opencdmp.authorization.Permission;
|
||||
import org.opencdmp.commons.XmlHandlingService;
|
||||
import org.opencdmp.commons.enums.IsActive;
|
||||
import org.opencdmp.commons.enums.UsageLimitTargetMetric;
|
||||
import gr.cite.tools.data.query.QueryFactory;
|
||||
import org.opencdmp.commons.types.usagelimit.DefinitionEntity;
|
||||
import org.opencdmp.convention.ConventionService;
|
||||
import org.opencdmp.data.TenantEntityManager;
|
||||
import org.opencdmp.data.UsageLimitEntity;
|
||||
|
@ -24,6 +28,7 @@ import org.opencdmp.model.UsageLimit;
|
|||
import org.opencdmp.model.builder.UsageLimitBuilder;
|
||||
import org.opencdmp.model.deleter.UsageLimitDeleter;
|
||||
import org.opencdmp.model.persist.UsageLimitPersist;
|
||||
import org.opencdmp.model.persist.usagelimit.DefinitionPersist;
|
||||
import org.opencdmp.query.UsageLimitQuery;
|
||||
import org.opencdmp.service.accounting.AccountingProperties;
|
||||
import org.opencdmp.service.accounting.AccountingService;
|
||||
|
@ -63,6 +68,8 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
|
||||
private final TenantEntityManager tenantEntityManager;
|
||||
|
||||
private final XmlHandlingService xmlHandlingService;
|
||||
|
||||
private final AccountingService accountingService;
|
||||
|
||||
private final UsageLimitProperties usageLimitProperties;
|
||||
|
@ -79,7 +86,7 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
ConventionService conventionService,
|
||||
ErrorThesaurusProperties errors,
|
||||
MessageSource messageSource,
|
||||
QueryFactory queryFactory, TenantEntityManager tenantEntityManager, AccountingService accountingService, UsageLimitProperties usageLimitProperties, AccountingProperties accountingProperties) {
|
||||
QueryFactory queryFactory, TenantEntityManager tenantEntityManager, XmlHandlingService xmlHandlingService, AccountingService accountingService, UsageLimitProperties usageLimitProperties, AccountingProperties accountingProperties) {
|
||||
this.entityManager = entityManager;
|
||||
this.authorizationService = authorizationService;
|
||||
this.deleterFactory = deleterFactory;
|
||||
|
@ -89,12 +96,13 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
this.messageSource = messageSource;
|
||||
this.queryFactory = queryFactory;
|
||||
this.tenantEntityManager = tenantEntityManager;
|
||||
this.xmlHandlingService = xmlHandlingService;
|
||||
this.accountingService = accountingService;
|
||||
this.usageLimitProperties = usageLimitProperties;
|
||||
this.accountingProperties = accountingProperties;
|
||||
}
|
||||
|
||||
public UsageLimit persist(UsageLimitPersist model, FieldSet fields) throws MyForbiddenException, MyValidationException, MyApplicationException, MyNotFoundException, InvalidApplicationException {
|
||||
public UsageLimit persist(UsageLimitPersist model, FieldSet fields) throws MyForbiddenException, MyValidationException, MyApplicationException, MyNotFoundException, InvalidApplicationException, JAXBException {
|
||||
logger.debug(new MapLogEntry("persisting data UsageLimit").And("model", model).And("fields", fields));
|
||||
|
||||
this.authorizationService.authorizeForce(Permission.EditUsageLimit);
|
||||
|
@ -132,6 +140,8 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
data.setTargetMetric(model.getTargetMetric());
|
||||
data.setValue(model.getValue());
|
||||
data.setUpdatedAt(Instant.now());
|
||||
data.setDefinition(this.xmlHandlingService.toXml(this.buildDefinitionEntity(model.getDefinition())));
|
||||
|
||||
if (isUpdate)
|
||||
this.entityManager.merge(data);
|
||||
else
|
||||
|
@ -141,6 +151,17 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
return this.builderFactory.builder(UsageLimitBuilder.class).authorize(AuthorizationFlags.AllExceptPublic).build(BaseFieldSet.build(fields, UsageLimit._id), data);
|
||||
}
|
||||
|
||||
private @NotNull DefinitionEntity buildDefinitionEntity(DefinitionPersist persist) {
|
||||
DefinitionEntity data = new DefinitionEntity();
|
||||
if (persist == null)
|
||||
return data;
|
||||
|
||||
data.setHasPeriodicity(persist.getHasPeriodicity());
|
||||
if (persist.getHasPeriodicity()) data.setPeriodicityRange(persist.getPeriodicityRange());
|
||||
|
||||
return data;
|
||||
}
|
||||
|
||||
public void deleteAndSave(UUID id) throws MyForbiddenException, InvalidApplicationException {
|
||||
logger.debug("deleting UsageLimit: {}", id);
|
||||
|
||||
|
@ -155,13 +176,17 @@ public class UsageLimitServiceImpl implements UsageLimitService {
|
|||
|
||||
if (metric == null) throw new MyApplicationException("Target Metric not defined");
|
||||
|
||||
Integer currentValue = this.accountingService.getCurrentMetricValue(metric);
|
||||
|
||||
try {
|
||||
this.tenantEntityManager.loadExplicitTenantFilters();
|
||||
UsageLimitEntity usageLimitEntity = this.queryFactory.query(UsageLimitQuery.class).disableTracking().usageLimitTargetMetrics(metric).isActive(IsActive.Active).firstAs(new BaseFieldSet().ensure(UsageLimit._label).ensure(UsageLimit._targetMetric).ensure(UsageLimit._value));
|
||||
if (usageLimitEntity != null && currentValue >= usageLimitEntity.getValue()) throw new MyValidationException(this.errors.getUsageLimitException().getCode(), usageLimitEntity.getLabel());
|
||||
UsageLimitEntity usageLimitEntity = this.queryFactory.query(UsageLimitQuery.class).disableTracking().usageLimitTargetMetrics(metric).isActive(IsActive.Active).first();
|
||||
|
||||
if (usageLimitEntity != null) {
|
||||
DefinitionEntity definition = this.xmlHandlingService.fromXmlSafe(DefinitionEntity.class, usageLimitEntity.getDefinition());
|
||||
if (definition == null) throw new MyNotFoundException(this.messageSource.getMessage("General_ItemNotFound", new Object[]{usageLimitEntity.getId(), DefinitionEntity.class.getSimpleName()}, LocaleContextHolder.getLocale()));
|
||||
|
||||
Integer currentValue = this.accountingService.getCurrentMetricValue(metric, definition);
|
||||
if (currentValue >= usageLimitEntity.getValue()) throw new MyValidationException(this.errors.getUsageLimitException().getCode(), usageLimitEntity.getLabel());
|
||||
}
|
||||
} catch (InvalidApplicationException e) {
|
||||
log.error(e.getMessage(), e);
|
||||
throw new MyApplicationException(e.getMessage());
|
||||
|
|
|
@ -46,9 +46,9 @@ import java.util.UUID;
|
|||
|
||||
@RestController
|
||||
@RequestMapping(path = "api/usage-limit")
|
||||
public class UsageFilterController {
|
||||
public class UsageLimitController {
|
||||
|
||||
private static final LoggerService logger = new LoggerService(LoggerFactory.getLogger(UsageFilterController.class));
|
||||
private static final LoggerService logger = new LoggerService(LoggerFactory.getLogger(UsageLimitController.class));
|
||||
|
||||
private final BuilderFactory builderFactory;
|
||||
|
||||
|
@ -62,7 +62,7 @@ public class UsageFilterController {
|
|||
|
||||
private final MessageSource messageSource;
|
||||
|
||||
public UsageFilterController(
|
||||
public UsageLimitController(
|
||||
BuilderFactory builderFactory,
|
||||
AuditService auditService,
|
||||
UsageLimitService usageLimitService,
|
|
@ -2,5 +2,6 @@ accounting:
|
|||
enabled: ${ACCOUNTING_ENABLED}
|
||||
serviceId: ${SERVICE_ID}
|
||||
subjectId: unknown
|
||||
fromInstant: 1990-01-01T05:47:26.853Z
|
||||
projectFields:
|
||||
- sum
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
export enum UsageLimitPeriodicityRange {
|
||||
Monthly = 0,
|
||||
Yearly = 1
|
||||
}
|
|
@ -1,3 +1,4 @@
|
|||
import { UsageLimitPeriodicityRange } from "@app/core/common/enum/usage-limit-periodicity-range";
|
||||
import { UsageLimitTargetMetric } from "@app/core/common/enum/usage-limit-target-metric";
|
||||
import { BaseEntity, BaseEntityPersist } from "@common/base/base-entity.model";
|
||||
|
||||
|
@ -5,10 +6,24 @@ export interface UsageLimit extends BaseEntity {
|
|||
label: string;
|
||||
targetMetric: UsageLimitTargetMetric;
|
||||
value: number;
|
||||
definition: UsageLimitDefinition;
|
||||
}
|
||||
|
||||
export interface UsageLimitDefinition {
|
||||
hasPeriodicity: Boolean;
|
||||
periodicityRange: UsageLimitPeriodicityRange
|
||||
}
|
||||
|
||||
// persist
|
||||
|
||||
export interface UsageLimitPersist extends BaseEntityPersist {
|
||||
label: string;
|
||||
targetMetric: UsageLimitTargetMetric;
|
||||
value: number;
|
||||
definition: UsageLimitDefinitionPersist;
|
||||
}
|
||||
|
||||
export interface UsageLimitDefinitionPersist {
|
||||
hasPeriodicity: Boolean;
|
||||
periodicityRange: UsageLimitPeriodicityRange
|
||||
}
|
|
@ -30,6 +30,7 @@ import { PlanBlueprintExtraFieldDataType } from '../../common/enum/plan-blueprin
|
|||
import { PlanStatus } from '../../common/enum/plan-status';
|
||||
import { ValidationType } from '../../common/enum/validation-type';
|
||||
import { UsageLimitTargetMetric } from '@app/core/common/enum/usage-limit-target-metric';
|
||||
import { UsageLimitPeriodicityRange } from '@app/core/common/enum/usage-limit-periodicity-range';
|
||||
|
||||
@Injectable()
|
||||
export class EnumUtils {
|
||||
|
@ -318,4 +319,12 @@ export class EnumUtils {
|
|||
}
|
||||
}
|
||||
|
||||
public toUsageLimitPeriodicityRangeString(value: UsageLimitPeriodicityRange): string {
|
||||
switch (value) {
|
||||
case UsageLimitPeriodicityRange.Monthly: return this.language.instant('TYPES.USAGE-LIMIT-PERIODICITY-RANGE.MONTHLY');
|
||||
case UsageLimitPeriodicityRange.Yearly: return this.language.instant('TYPES.USAGE-LIMIT-PERIODICITY-RANGE.YEARLY');
|
||||
default: return '';
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -52,6 +52,23 @@
|
|||
<mat-error *ngIf="formGroup.get('value').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
<div class="col-4">
|
||||
<mat-checkbox [formControl]="formGroup.get('definition').get('hasPeriodicity')">
|
||||
{{'USAGE-LIMIT-EDITOR.FIELDS.HAS-PERIODICITY' | translate}}
|
||||
<mat-error *ngIf="formGroup.get('definition').get('hasPeriodicity').hasError('backendError')">{{formGroup.get('definition').get('hasPeriodicity').getError('backendError').message}}</mat-error>
|
||||
<mat-error *ngIf="formGroup.get('definition').get('hasPeriodicity').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-checkbox>
|
||||
</div>
|
||||
<div class="col-4" *ngIf="formGroup.get('definition').get('hasPeriodicity').value">
|
||||
<mat-form-field class="w-100">
|
||||
<mat-label>{{'USAGE-LIMIT-EDITOR.FIELDS.PERIODICITY-RANGE' | translate}}</mat-label>
|
||||
<mat-select [formControl]="formGroup.get('definition').get('periodicityRange')">
|
||||
<mat-option *ngFor="let range of periodicityRangeEnum" [value]="range">{{enumUtils.toUsageLimitPeriodicityRangeString(range)}}</mat-option>
|
||||
</mat-select>
|
||||
<mat-error *ngIf="formGroup.get('definition').get('periodicityRange').hasError('backendError')">{{formGroup.get('definition').get('periodicityRange').getError('backendError').message}}</mat-error>
|
||||
<mat-error *ngIf="formGroup.get('definition').get('periodicityRange').hasError('required')">{{'GENERAL.VALIDATION.REQUIRED' | translate}}</mat-error>
|
||||
</mat-form-field>
|
||||
</div>
|
||||
</div>
|
||||
</mat-card-content>
|
||||
</mat-card>
|
||||
|
|
|
@ -28,6 +28,7 @@ import { UsageLimitEditorService } from './usage-limit-editor.service';
|
|||
import { RouterUtilsService } from '@app/core/services/router/router-utils.service';
|
||||
import { Title } from '@angular/platform-browser';
|
||||
import { UsageLimitTargetMetric } from '@app/core/common/enum/usage-limit-target-metric';
|
||||
import { UsageLimitPeriodicityRange } from '@app/core/common/enum/usage-limit-periodicity-range';
|
||||
|
||||
|
||||
@Component({
|
||||
|
@ -43,6 +44,7 @@ export class UsageLimitEditorComponent extends BaseEditor<UsageLimitEditorModel,
|
|||
formGroup: UntypedFormGroup = null;
|
||||
showInactiveDetails = false;
|
||||
targetMetricEnum = this.enumUtils.getEnumValues<UsageLimitTargetMetric>(UsageLimitTargetMetric);
|
||||
periodicityRangeEnum = this.enumUtils.getEnumValues<UsageLimitPeriodicityRange>(UsageLimitPeriodicityRange);
|
||||
|
||||
protected get canDelete(): boolean {
|
||||
return !this.isDeleted && !this.isNew && this.hasPermission(this.authService.permissionEnum.DeleteUsageLimit) && this.editorModel.belongsToCurrentTenant != false;;
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
import { UntypedFormBuilder, UntypedFormGroup, Validators } from "@angular/forms";
|
||||
import { UsageLimitPeriodicityRange } from "@app/core/common/enum/usage-limit-periodicity-range";
|
||||
import { UsageLimitTargetMetric } from "@app/core/common/enum/usage-limit-target-metric";
|
||||
import { UsageLimit, UsageLimitPersist } from "@app/core/model/usage-limit/usage-limit";
|
||||
import { UsageLimit, UsageLimitDefinition, UsageLimitDefinitionPersist, UsageLimitPersist } from "@app/core/model/usage-limit/usage-limit";
|
||||
import { BaseEditorModel } from "@common/base/base-form-editor-model";
|
||||
import { BackendErrorValidator } from "@common/forms/validation/custom-validator";
|
||||
import { ValidationErrorModel } from "@common/forms/validation/error-model/validation-error-model";
|
||||
|
@ -11,6 +12,7 @@ export class UsageLimitEditorModel extends BaseEditorModel implements UsageLimit
|
|||
targetMetric: UsageLimitTargetMetric;
|
||||
value: number;
|
||||
permissions: string[];
|
||||
definition: DefinitionEditorModel = new DefinitionEditorModel(this.validationErrorModel);
|
||||
|
||||
public validationErrorModel: ValidationErrorModel = new ValidationErrorModel();
|
||||
protected formBuilder: UntypedFormBuilder = new UntypedFormBuilder();
|
||||
|
@ -23,6 +25,7 @@ export class UsageLimitEditorModel extends BaseEditorModel implements UsageLimit
|
|||
this.label = item.label;
|
||||
this.targetMetric = item.targetMetric;
|
||||
this.value = item.value;
|
||||
if (item.definition) this.definition = new DefinitionEditorModel(this.validationErrorModel).fromModel(item.definition);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
@ -35,6 +38,10 @@ export class UsageLimitEditorModel extends BaseEditorModel implements UsageLimit
|
|||
label: [{ value: this.label, disabled: disabled }, context.getValidation('label').validators],
|
||||
targetMetric: [{ value: this.targetMetric, disabled: disabled }, context.getValidation('targetMetric').validators],
|
||||
value: [{ value: this.value, disabled: disabled }, context.getValidation('value').validators],
|
||||
definition: this.definition.buildForm({
|
||||
rootPath: `definition.`,
|
||||
disabled: disabled
|
||||
}),
|
||||
hash: [{ value: this.hash, disabled: disabled }, context.getValidation('hash').validators]
|
||||
});
|
||||
}
|
||||
|
@ -52,3 +59,56 @@ export class UsageLimitEditorModel extends BaseEditorModel implements UsageLimit
|
|||
return baseContext;
|
||||
}
|
||||
}
|
||||
|
||||
export class DefinitionEditorModel implements UsageLimitDefinitionPersist {
|
||||
hasPeriodicity: Boolean = false;
|
||||
periodicityRange: UsageLimitPeriodicityRange;
|
||||
|
||||
protected formBuilder: UntypedFormBuilder = new UntypedFormBuilder();
|
||||
|
||||
constructor(
|
||||
public validationErrorModel: ValidationErrorModel = new ValidationErrorModel()
|
||||
) { }
|
||||
|
||||
public fromModel(item: UsageLimitDefinition): DefinitionEditorModel {
|
||||
if (item) {
|
||||
this.hasPeriodicity = item.hasPeriodicity;
|
||||
this.periodicityRange = item.periodicityRange;
|
||||
}
|
||||
return this;
|
||||
}
|
||||
|
||||
buildForm(params?: {
|
||||
context?: ValidationContext,
|
||||
disabled?: boolean,
|
||||
rootPath?: string
|
||||
}): UntypedFormGroup {
|
||||
let { context = null, disabled = false, rootPath } = params ?? {}
|
||||
if (context == null) {
|
||||
context = DefinitionEditorModel.createValidationContext({
|
||||
validationErrorModel: this.validationErrorModel,
|
||||
rootPath
|
||||
});
|
||||
}
|
||||
|
||||
return this.formBuilder.group({
|
||||
hasPeriodicity: [{ value: this.hasPeriodicity, disabled: disabled }, context.getValidation('hasPeriodicity').validators],
|
||||
periodicityRange: [{ value: this.periodicityRange, disabled: disabled }, context.getValidation('periodicityRange').validators],
|
||||
});
|
||||
}
|
||||
|
||||
static createValidationContext(params: {
|
||||
rootPath?: string,
|
||||
validationErrorModel: ValidationErrorModel
|
||||
}): ValidationContext {
|
||||
const { rootPath = '', validationErrorModel } = params;
|
||||
|
||||
const baseContext: ValidationContext = new ValidationContext();
|
||||
const baseValidationArray: Validation[] = new Array<Validation>();
|
||||
baseValidationArray.push({ key: 'hasPeriodicity', validators: [Validators.required, BackendErrorValidator(validationErrorModel, `${rootPath}hasPeriodicity`)] });
|
||||
baseValidationArray.push({ key: 'periodicityRange', validators: [BackendErrorValidator(validationErrorModel, `${rootPath}periodicityRange`)] });
|
||||
|
||||
baseContext.validation = baseValidationArray;
|
||||
return baseContext;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import { Injectable } from '@angular/core';
|
||||
import { ActivatedRouteSnapshot, RouterStateSnapshot } from '@angular/router';
|
||||
import { UsageLimit } from '@app/core/model/usage-limit/usage-limit';
|
||||
import { UsageLimit, UsageLimitDefinition } from '@app/core/model/usage-limit/usage-limit';
|
||||
import { UsageLimitService } from '@app/core/services/usage-limit/usage.service';
|
||||
import { BreadcrumbService } from '@app/ui/misc/breadcrumb/breadcrumb.service';
|
||||
import { BaseEditorResolver } from '@common/base/base-editor.resolver';
|
||||
|
@ -22,6 +22,8 @@ export class UsageLimitEditorResolver extends BaseEditorResolver {
|
|||
nameof<UsageLimit>(x => x.label),
|
||||
nameof<UsageLimit>(x => x.targetMetric),
|
||||
nameof<UsageLimit>(x => x.value),
|
||||
[nameof<UsageLimit>(x => x.definition), nameof<UsageLimitDefinition>(x => x.hasPeriodicity)].join('.'),
|
||||
[nameof<UsageLimit>(x => x.definition), nameof<UsageLimitDefinition>(x => x.periodicityRange)].join('.'),
|
||||
nameof<UsageLimit>(x => x.createdAt),
|
||||
nameof<UsageLimit>(x => x.updatedAt),
|
||||
nameof<UsageLimit>(x => x.hash),
|
||||
|
|
Loading…
Reference in New Issue