FINERACT-1932: Fineract modularization - custom modules
This commit is contained in:
committed by
Adam Saghy
parent
92e291a9e4
commit
655466785c
+1
-1
@@ -23,8 +23,8 @@ import java.util.List;
|
||||
import org.apache.fineract.accounting.glaccount.domain.GLAccountType;
|
||||
import org.apache.fineract.accounting.glaccount.domain.GLAccountUsage;
|
||||
import org.apache.fineract.accounting.journalentry.domain.JournalEntryType;
|
||||
import org.apache.fineract.accounting.producttoaccountmapping.domain.PortfolioProductType;
|
||||
import org.apache.fineract.infrastructure.core.data.EnumOptionData;
|
||||
import org.apache.fineract.portfolio.PortfolioProductType;
|
||||
|
||||
public final class AccountingEnumerations {
|
||||
|
||||
|
||||
+45
@@ -0,0 +1,45 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.codes.data;
|
||||
|
||||
import java.io.Serializable;
|
||||
import lombok.Data;
|
||||
import lombok.NoArgsConstructor;
|
||||
import lombok.experimental.Accessors;
|
||||
|
||||
/**
|
||||
* Immutable data object representing a code.
|
||||
*/
|
||||
|
||||
@Data
|
||||
@NoArgsConstructor
|
||||
@Accessors(chain = true)
|
||||
public final class CodeData implements Serializable {
|
||||
|
||||
private Long id;
|
||||
@SuppressWarnings("unused")
|
||||
private String name;
|
||||
@SuppressWarnings("unused")
|
||||
private boolean systemDefined;
|
||||
|
||||
public static CodeData instance(final Long id, final String name, final boolean systemDefined) {
|
||||
return new CodeData().setId(id).setName(name).setSystemDefined(systemDefined);
|
||||
}
|
||||
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.codes.service;
|
||||
|
||||
import java.util.Collection;
|
||||
import org.apache.fineract.infrastructure.codes.data.CodeData;
|
||||
|
||||
public interface CodeReadPlatformService {
|
||||
|
||||
Collection<CodeData> retrieveAllCodes();
|
||||
|
||||
CodeData retrieveCode(Long codeId);
|
||||
|
||||
CodeData retriveCode(String codeName);
|
||||
}
|
||||
+36
@@ -0,0 +1,36 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.core.exception;
|
||||
|
||||
import org.springframework.beans.BeansException;
|
||||
|
||||
public class ResourceNotFoundException extends AbstractPlatformResourceNotFoundException {
|
||||
|
||||
public ResourceNotFoundException(String globalisationMessageCode, String defaultUserMessage, Object[] defaultUserMessageArgs) {
|
||||
super(globalisationMessageCode, defaultUserMessage, defaultUserMessageArgs);
|
||||
}
|
||||
|
||||
public ResourceNotFoundException() {
|
||||
super("", "", "");
|
||||
}
|
||||
|
||||
public ResourceNotFoundException(BeansException e) {
|
||||
super("", "", "", e);
|
||||
}
|
||||
}
|
||||
+382
@@ -0,0 +1,382 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.core.serialization;
|
||||
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.BOOLEAN;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.DATE;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.DATETIME;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.DECIMAL;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.INTEGER;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.JSON;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.TEXT;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.TIMESTAMP;
|
||||
import static org.apache.fineract.infrastructure.core.service.database.JdbcJavaType.VARCHAR;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_AFTER;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_CODE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_INDEXED;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_LENGTH;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_MANDATORY;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_NAME;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_NEWCODE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_NEWNAME;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_BOOLEAN;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_DATE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_DATETIME;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_DECIMAL;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_DROPDOWN;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_JSON;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_NUMBER;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_STRING;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_TEXT;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_TYPE_TIMESTAMP;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_FIELD_UNIQUE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_ADDCOLUMNS;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_APPTABLE_NAME;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_CHANGECOLUMNS;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_COLUMNS;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_DATATABLE_NAME;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_DROPCOLUMNS;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_MULTIROW;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.API_PARAM_SUBTYPE;
|
||||
import static org.apache.fineract.infrastructure.dataqueries.api.DataTableApiConstant.TABLE_FIELD_ID;
|
||||
|
||||
import com.google.gson.JsonArray;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import jakarta.validation.constraints.NotNull;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.fineract.infrastructure.core.data.ApiParameterError;
|
||||
import org.apache.fineract.infrastructure.core.data.DataValidatorBuilder;
|
||||
import org.apache.fineract.infrastructure.core.exception.InvalidJsonException;
|
||||
import org.apache.fineract.infrastructure.core.exception.PlatformApiDataValidationException;
|
||||
import org.apache.fineract.infrastructure.core.exception.PlatformDataIntegrityException;
|
||||
import org.apache.fineract.infrastructure.core.service.database.DatabaseTypeResolver;
|
||||
import org.apache.fineract.infrastructure.core.service.database.JdbcJavaType;
|
||||
import org.apache.fineract.infrastructure.dataqueries.data.EntityTables;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public class DatatableCommandFromApiJsonDeserializer {
|
||||
|
||||
public static final String DATATABLE_NAME_REGEX_PATTERN = "^[a-zA-Z][a-zA-Z0-9\\-_\\s]{0,48}[a-zA-Z0-9]$";
|
||||
public static final String DATATABLE_COLUMN_NAME_REGEX_PATTERN = "^[a-zA-Z][a-zA-Z0-9\\-_\\s]{0,}[a-zA-Z0-9]$";
|
||||
|
||||
/**
|
||||
* The parameters supported for this command.
|
||||
*/
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_CREATE = Set.of(API_PARAM_DATATABLE_NAME, API_PARAM_SUBTYPE,
|
||||
API_PARAM_APPTABLE_NAME, API_PARAM_MULTIROW, API_PARAM_COLUMNS);
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_CREATE_COLUMNS = Set.of(API_FIELD_NAME, API_FIELD_TYPE, API_FIELD_LENGTH,
|
||||
API_FIELD_MANDATORY, API_FIELD_CODE, API_FIELD_UNIQUE, API_FIELD_INDEXED);
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_UPDATE = Set.of(API_PARAM_APPTABLE_NAME, API_PARAM_SUBTYPE,
|
||||
API_PARAM_CHANGECOLUMNS, API_PARAM_ADDCOLUMNS, API_PARAM_DROPCOLUMNS);
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_ADD_COLUMNS = Set.of(API_FIELD_NAME, API_FIELD_TYPE, API_FIELD_LENGTH,
|
||||
API_FIELD_MANDATORY, API_FIELD_AFTER, API_FIELD_CODE, API_FIELD_UNIQUE, API_FIELD_INDEXED);
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_CHANGE_COLUMNS = Set.of(API_FIELD_NAME, API_FIELD_NEWNAME, API_FIELD_LENGTH,
|
||||
API_FIELD_MANDATORY, API_FIELD_AFTER, API_FIELD_CODE, API_FIELD_NEWCODE, API_FIELD_UNIQUE, API_FIELD_INDEXED);
|
||||
private static final Set<String> SUPPORTED_PARAMETERS_FOR_DROP_COLUMNS = Set.of(API_FIELD_NAME);
|
||||
private static final Object[] SUPPORTED_COLUMN_TYPES = { API_FIELD_TYPE_STRING, API_FIELD_TYPE_NUMBER, API_FIELD_TYPE_BOOLEAN,
|
||||
API_FIELD_TYPE_DECIMAL, API_FIELD_TYPE_DATE, API_FIELD_TYPE_DATETIME, API_FIELD_TYPE_TEXT, API_FIELD_TYPE_JSON,
|
||||
API_FIELD_TYPE_DROPDOWN };
|
||||
|
||||
private final FromJsonHelper fromApiJsonHelper;
|
||||
private final DatabaseTypeResolver databaseTypeResolver;
|
||||
|
||||
@Autowired
|
||||
public DatatableCommandFromApiJsonDeserializer(final FromJsonHelper fromApiJsonHelper, DatabaseTypeResolver databaseTypeResolver) {
|
||||
this.fromApiJsonHelper = fromApiJsonHelper;
|
||||
this.databaseTypeResolver = databaseTypeResolver;
|
||||
}
|
||||
|
||||
public void validateForCreate(final String json) {
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
}
|
||||
|
||||
final Type typeOfMap = new TypeToken<Map<String, Object>>() {}.getType();
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(typeOfMap, json, SUPPORTED_PARAMETERS_FOR_CREATE);
|
||||
|
||||
final List<ApiParameterError> dataValidationErrors = new ArrayList<>();
|
||||
final DataValidatorBuilder baseDataValidator = new DataValidatorBuilder(dataValidationErrors).resource("datatable");
|
||||
|
||||
final JsonElement element = this.fromApiJsonHelper.parse(json);
|
||||
|
||||
final String datatableName = this.fromApiJsonHelper.extractStringNamed(API_PARAM_DATATABLE_NAME, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_DATATABLE_NAME).value(datatableName).notBlank().notExceedingLengthOf(50)
|
||||
.matchesRegularExpression(DATATABLE_NAME_REGEX_PATTERN);
|
||||
|
||||
final String apptableName = this.fromApiJsonHelper.extractStringNamed(API_PARAM_APPTABLE_NAME, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_APPTABLE_NAME).value(apptableName).notBlank().notExceedingLengthOf(50)
|
||||
.isOneOfTheseStringValues(EntityTables.getEntityNames());
|
||||
|
||||
EntityTables entityTable = EntityTables.fromEntityName(apptableName);
|
||||
validateEntitySubType(baseDataValidator, element, entityTable);
|
||||
|
||||
final String fkColumnName = entityTable == null ? null : entityTable.getForeignKeyColumnNameOnDatatable();
|
||||
|
||||
final Boolean multiRow = this.fromApiJsonHelper.extractBooleanNamed(API_PARAM_MULTIROW, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_MULTIROW).value(multiRow).ignoreIfNull().notBlank().isOneOfTheseValues(true, false);
|
||||
|
||||
final JsonArray columns = this.fromApiJsonHelper.extractJsonArrayNamed(API_PARAM_COLUMNS, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_COLUMNS).value(columns).notNull().jsonArrayNotEmpty();
|
||||
|
||||
if (columns != null) {
|
||||
for (final JsonElement column : columns) {
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(column.getAsJsonObject(), SUPPORTED_PARAMETERS_FOR_CREATE_COLUMNS);
|
||||
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NAME, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NAME).value(name).notBlank()
|
||||
.isNotOneOfTheseValues(TABLE_FIELD_ID, fkColumnName).matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
validateType(baseDataValidator, column);
|
||||
|
||||
final Boolean mandatory = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_MANDATORY, column);
|
||||
final Boolean unique = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_UNIQUE, column);
|
||||
final Boolean indexed = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_INDEXED, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_MANDATORY).value(mandatory).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
baseDataValidator.reset().parameter(API_FIELD_UNIQUE).value(unique).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
baseDataValidator.reset().parameter(API_FIELD_INDEXED).value(indexed).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
}
|
||||
}
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
|
||||
public void validateForUpdate(final String json) {
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
}
|
||||
// Because all parameters are optional, a check to see if at least one
|
||||
// parameter
|
||||
// has been specified is necessary in order to avoid JSON requests with
|
||||
// no parameters
|
||||
if (!json.matches("(?s)\\A\\{.*?(\\\".*?\\\"\\s*?:\\s*?)+.*?\\}\\z")) { // NOSONAR
|
||||
throw new PlatformDataIntegrityException("error.msg.invalid.request.body.no.parameters",
|
||||
"Provided JSON request body does not have any parameters.");
|
||||
}
|
||||
|
||||
final Type typeOfMap = new TypeToken<Map<String, Object>>() {
|
||||
|
||||
}.getType();
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(typeOfMap, json, SUPPORTED_PARAMETERS_FOR_UPDATE);
|
||||
|
||||
final List<ApiParameterError> dataValidationErrors = new ArrayList<>();
|
||||
final DataValidatorBuilder baseDataValidator = new DataValidatorBuilder(dataValidationErrors).resource("datatable");
|
||||
|
||||
final JsonElement element = this.fromApiJsonHelper.parse(json);
|
||||
final String apptableName = this.fromApiJsonHelper.extractStringNamed(API_PARAM_APPTABLE_NAME, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_APPTABLE_NAME).value(apptableName).ignoreIfNull().notBlank()
|
||||
.isOneOfTheseStringValues(EntityTables.getEntityNames());
|
||||
|
||||
EntityTables entityTable = EntityTables.fromEntityName(apptableName);
|
||||
validateEntitySubType(baseDataValidator, element, entityTable);
|
||||
|
||||
final String fkColumnName = entityTable.getForeignKeyColumnNameOnDatatable();
|
||||
|
||||
final JsonArray changeColumns = this.fromApiJsonHelper.extractJsonArrayNamed(API_PARAM_CHANGECOLUMNS, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_CHANGECOLUMNS).value(changeColumns).ignoreIfNull().jsonArrayNotEmpty();
|
||||
|
||||
if (changeColumns != null) {
|
||||
for (final JsonElement column : changeColumns) {
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(column.getAsJsonObject(), SUPPORTED_PARAMETERS_FOR_CHANGE_COLUMNS);
|
||||
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NAME, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NAME).value(name).notBlank()
|
||||
.isNotOneOfTheseValues(TABLE_FIELD_ID, fkColumnName).matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
final String newName = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NEWNAME, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NEWNAME).value(newName).ignoreIfNull().notBlank().notExceedingLengthOf(50)
|
||||
.isNotOneOfTheseValues(TABLE_FIELD_ID, fkColumnName).matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(API_FIELD_LENGTH, column)) {
|
||||
final String lengthStr = this.fromApiJsonHelper.extractStringNamed(API_FIELD_LENGTH, column);
|
||||
if (StringUtils.isWhitespace(lengthStr) || !StringUtils.isNumeric(lengthStr) || StringUtils.isBlank(lengthStr)) {
|
||||
baseDataValidator.reset().parameter(API_FIELD_LENGTH).failWithCode("not.greater.than.zero");
|
||||
} else {
|
||||
final Integer length = Integer.parseInt(lengthStr);
|
||||
baseDataValidator.reset().parameter(API_FIELD_LENGTH).value(length).ignoreIfNull().notBlank().positiveAmount();
|
||||
}
|
||||
}
|
||||
|
||||
final String code = this.fromApiJsonHelper.extractStringNamed(API_FIELD_CODE, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_CODE).value(code).ignoreIfNull().notBlank().notExceedingLengthOf(100)
|
||||
.matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
final String newCode = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NEWCODE, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NEWCODE).value(newCode).ignoreIfNull().notBlank().notExceedingLengthOf(100)
|
||||
.matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
if (StringUtils.isBlank(code) && StringUtils.isNotBlank(newCode)) {
|
||||
baseDataValidator.reset().parameter(API_FIELD_CODE).value(code).cantBeBlankWhenParameterProvidedIs(API_FIELD_NEWCODE,
|
||||
newCode);
|
||||
}
|
||||
|
||||
final Boolean mandatory = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_MANDATORY, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_MANDATORY).value(mandatory).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
|
||||
final Boolean after = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_AFTER, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_AFTER).value(after).ignoreIfNull().notBlank().isOneOfTheseValues(true, false);
|
||||
|
||||
final Boolean unique = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_UNIQUE, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_UNIQUE).value(unique).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
|
||||
final Boolean indexed = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_INDEXED, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_INDEXED).value(indexed).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
}
|
||||
}
|
||||
|
||||
final JsonArray addColumns = this.fromApiJsonHelper.extractJsonArrayNamed(API_PARAM_ADDCOLUMNS, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_ADDCOLUMNS).value(addColumns).ignoreIfNull().jsonArrayNotEmpty();
|
||||
|
||||
if (addColumns != null) {
|
||||
for (final JsonElement column : addColumns) {
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(column.getAsJsonObject(), SUPPORTED_PARAMETERS_FOR_ADD_COLUMNS);
|
||||
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NAME, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NAME).value(name).notBlank()
|
||||
.isNotOneOfTheseValues(TABLE_FIELD_ID, fkColumnName).matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
|
||||
validateType(baseDataValidator, column);
|
||||
|
||||
final Boolean mandatory = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_MANDATORY, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_MANDATORY).value(mandatory).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
|
||||
final Boolean after = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_AFTER, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_AFTER).value(after).ignoreIfNull().notBlank().isOneOfTheseValues(true, false);
|
||||
|
||||
final Boolean unique = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_UNIQUE, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_UNIQUE).value(unique).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
|
||||
final Boolean indexed = this.fromApiJsonHelper.extractBooleanNamed(API_FIELD_INDEXED, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_INDEXED).value(indexed).ignoreIfNull().notBlank().isOneOfTheseValues(true,
|
||||
false);
|
||||
}
|
||||
}
|
||||
|
||||
final JsonArray dropColumns = this.fromApiJsonHelper.extractJsonArrayNamed(API_PARAM_DROPCOLUMNS, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_DROPCOLUMNS).value(dropColumns).ignoreIfNull().jsonArrayNotEmpty();
|
||||
|
||||
if (dropColumns != null) {
|
||||
for (final JsonElement column : dropColumns) {
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(column.getAsJsonObject(), SUPPORTED_PARAMETERS_FOR_DROP_COLUMNS);
|
||||
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(API_FIELD_NAME, column);
|
||||
baseDataValidator.reset().parameter(API_FIELD_NAME).value(name).notBlank()
|
||||
.isNotOneOfTheseValues(TABLE_FIELD_ID, fkColumnName).matchesRegularExpression(DATATABLE_COLUMN_NAME_REGEX_PATTERN);
|
||||
}
|
||||
}
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
|
||||
private void validateType(DataValidatorBuilder validator, final JsonElement column) {
|
||||
final String type = this.fromApiJsonHelper.extractStringNamed(API_FIELD_TYPE, column);
|
||||
validator.reset().parameter(API_FIELD_TYPE).value(type).notBlank().isOneOfTheseStringValues(SUPPORTED_COLUMN_TYPES);
|
||||
if (type == null) {
|
||||
return;
|
||||
}
|
||||
JdbcJavaType jdbcType = mapApiTypeToJdbcType(type, false);
|
||||
if (jdbcType != null) {
|
||||
final Integer length = this.fromApiJsonHelper.extractIntegerSansLocaleNamed(API_FIELD_LENGTH, column);
|
||||
validator = validator.reset().parameter(API_FIELD_LENGTH).value(length);
|
||||
if (jdbcType.hasPrecision(databaseTypeResolver.databaseType())) {
|
||||
if (jdbcType.isStringType() && length == null) {
|
||||
validator.failWithCode("must.be.provided.when.type.is.String");
|
||||
}
|
||||
validator.ignoreIfNull().positiveAmount();
|
||||
} // else, the precision is ignored
|
||||
}
|
||||
final String code = this.fromApiJsonHelper.extractStringNamed(API_FIELD_CODE, column);
|
||||
if (type.equalsIgnoreCase(API_FIELD_TYPE_DROPDOWN)) {
|
||||
if (code != null) {
|
||||
validator.reset().parameter(API_FIELD_CODE).value(code).notBlank().matchesRegularExpression(DATATABLE_NAME_REGEX_PATTERN);
|
||||
} else {
|
||||
validator.reset().parameter(API_FIELD_CODE).value(code).cantBeBlankWhenParameterProvidedIs(API_FIELD_TYPE, type);
|
||||
}
|
||||
} else {
|
||||
validator.reset().parameter(API_FIELD_CODE).value(code).mustBeBlankWhenParameterProvided(API_FIELD_TYPE, type);
|
||||
}
|
||||
}
|
||||
|
||||
private static JdbcJavaType mapApiTypeToJdbcType(@NotNull String apiType, boolean fail) {
|
||||
switch (apiType.toLowerCase()) {
|
||||
case API_FIELD_TYPE_STRING:
|
||||
return VARCHAR;
|
||||
case API_FIELD_TYPE_NUMBER, API_FIELD_TYPE_DROPDOWN:
|
||||
return INTEGER;
|
||||
case API_FIELD_TYPE_BOOLEAN:
|
||||
return BOOLEAN;
|
||||
case API_FIELD_TYPE_DECIMAL:
|
||||
return DECIMAL;
|
||||
case API_FIELD_TYPE_DATE:
|
||||
return DATE;
|
||||
case API_FIELD_TYPE_DATETIME:
|
||||
return DATETIME;
|
||||
case API_FIELD_TYPE_TIMESTAMP:
|
||||
return TIMESTAMP;
|
||||
case API_FIELD_TYPE_TEXT:
|
||||
return TEXT;
|
||||
case API_FIELD_TYPE_JSON:
|
||||
return JSON;
|
||||
default: {
|
||||
if (fail) {
|
||||
throw new PlatformDataIntegrityException("error.msg.datatable.column.type.invalid",
|
||||
"Column type " + apiType + " is not supported.");
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
public static JdbcJavaType mapApiTypeToJdbcType(@NotNull String apiType) {
|
||||
return mapApiTypeToJdbcType(apiType, true);
|
||||
}
|
||||
|
||||
private void validateEntitySubType(final DataValidatorBuilder baseDataValidator, final JsonElement element,
|
||||
final EntityTables entityTable) {
|
||||
if (entityTable == EntityTables.CLIENT) {
|
||||
String entitySubType = this.fromApiJsonHelper.extractStringNamed(API_PARAM_SUBTYPE, element);
|
||||
baseDataValidator.reset().parameter(API_PARAM_SUBTYPE).value(entitySubType).notBlank(); // Person or Entity
|
||||
}
|
||||
}
|
||||
|
||||
private void throwExceptionIfValidationWarningsExist(final List<ApiParameterError> dataValidationErrors) {
|
||||
if (!dataValidationErrors.isEmpty()) {
|
||||
throw new PlatformApiDataValidationException("validation.msg.validation.errors.exist", "Validation errors exist.",
|
||||
dataValidationErrors);
|
||||
}
|
||||
}
|
||||
}
|
||||
+38
@@ -0,0 +1,38 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.dataqueries.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformDomainRuleException;
|
||||
|
||||
/**
|
||||
* A {@link AbstractPlatformDomainRuleException} thrown when datatable resources are not found.
|
||||
*/
|
||||
public class DatatableEntryRequiredException extends AbstractPlatformDomainRuleException {
|
||||
|
||||
public DatatableEntryRequiredException(String datatableName) {
|
||||
super("error.msg.entry.required.in.datatable." + datatableName,
|
||||
"The datatable " + datatableName + " needs to be filled in before the current action can be proceeded", datatableName);
|
||||
}
|
||||
|
||||
public DatatableEntryRequiredException(String datatableName, Long appTableId) {
|
||||
super("error.msg.entry.cannot.be.deleted.datatable." + datatableName + ".attached.to.entity.datatable.check",
|
||||
"The entry cannot be deleted, due to datatable " + datatableName + " is attached to an Entity-Datatable check",
|
||||
datatableName, appTableId);
|
||||
}
|
||||
}
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.dataqueries.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformResourceNotFoundException;
|
||||
import org.apache.fineract.infrastructure.dataqueries.data.EntityTables;
|
||||
|
||||
/**
|
||||
* A {@link RuntimeException} thrown when datatable resources are not found.
|
||||
*/
|
||||
public class DatatableNotFoundException extends AbstractPlatformResourceNotFoundException {
|
||||
|
||||
public DatatableNotFoundException(final String datatable, final Long id) {
|
||||
super("error.msg.datatable.data.not.found", "Data not found for datatable: ", datatable + " Id:" + id);
|
||||
}
|
||||
|
||||
public DatatableNotFoundException(final String datatable) {
|
||||
super("error.msg.datatable.not.found", "Datatable not found.", datatable);
|
||||
}
|
||||
|
||||
public DatatableNotFoundException(final EntityTables entityTable, final Long id) {
|
||||
this(entityTable.getName(), id);
|
||||
}
|
||||
|
||||
public DatatableNotFoundException(final EntityTables entityTable) {
|
||||
this(entityTable.getName());
|
||||
}
|
||||
}
|
||||
+28
@@ -0,0 +1,28 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.dataqueries.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformDomainRuleException;
|
||||
|
||||
public class DatatableSystemErrorException extends AbstractPlatformDomainRuleException {
|
||||
|
||||
public DatatableSystemErrorException(final String msg) {
|
||||
super("error.msg.datatable.system.error", msg, msg);
|
||||
}
|
||||
}
|
||||
+33
@@ -0,0 +1,33 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.dataqueries.service;
|
||||
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public class DatatableKeywordGenerator {
|
||||
|
||||
public String generateIndexName(String tableName, String columnName) {
|
||||
return "idx_%s_%s".formatted(tableName, columnName);
|
||||
}
|
||||
|
||||
public String generateUniqueKeyName(String tableName, String columnName) {
|
||||
return "uk_%s_%s".formatted(tableName, columnName);
|
||||
}
|
||||
}
|
||||
+24
@@ -0,0 +1,24 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.infrastructure.security.service;
|
||||
|
||||
public interface SqlInjectionPreventerService {
|
||||
|
||||
String encodeSql(String literal);
|
||||
}
|
||||
+68
@@ -0,0 +1,68 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.interoperation.domain;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
import lombok.Getter;
|
||||
|
||||
@Getter
|
||||
public enum InteropIdentifierType {
|
||||
|
||||
MSISDN("interopIdentifierType.msisdn"), //
|
||||
EMAIL("interopIdentifierType.email"), //
|
||||
PERSONAL_ID("interopIdentifierType.personalId", "PERSONALID", "PERSONALID"), //
|
||||
BUSINESS("interopIdentifierType.business"), //
|
||||
DEVICE("interopIdentifierType.device"), //
|
||||
ACCOUNT_ID("interopIdentifierType.accountId", "ACCOUNTID", "ACCOUNTID"), //
|
||||
IBAN("interopIdentifierType.iban"), //
|
||||
ALIAS("interopIdentifierType.alias"), //
|
||||
BBAN("interopIdentifierType.bban"), //
|
||||
; //
|
||||
|
||||
public static final InteropIdentifierType[] VALUES = values();
|
||||
|
||||
private static final Map<String, InteropIdentifierType> BY_ALIAS = Arrays.stream(VALUES)
|
||||
.collect(Collectors.toMap(InteropIdentifierType::getAlias, v -> v));
|
||||
private static final Map<String, InteropIdentifierType> BY_NAME = Arrays.stream(VALUES)
|
||||
.collect(Collectors.toMap(InteropIdentifierType::name, v -> v));
|
||||
|
||||
private final String code;
|
||||
private final String description;
|
||||
private final String alias;
|
||||
|
||||
InteropIdentifierType(String code, String description, String alias) {
|
||||
this.code = code;
|
||||
this.description = description == null ? name() : description;
|
||||
this.alias = alias == null ? name() : alias;
|
||||
}
|
||||
|
||||
InteropIdentifierType(String code) {
|
||||
this(code, null, null);
|
||||
}
|
||||
|
||||
public static InteropIdentifierType resolveName(String name) {
|
||||
if (name == null) {
|
||||
return null;
|
||||
}
|
||||
InteropIdentifierType idType = BY_ALIAS.get(name);
|
||||
return idType == null ? BY_NAME.get(name) : idType;
|
||||
}
|
||||
}
|
||||
+50
@@ -0,0 +1,50 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.data;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
|
||||
/**
|
||||
* Immutable data object representing currency.
|
||||
*/
|
||||
public class MoneyData {
|
||||
|
||||
private final String code;
|
||||
private final BigDecimal amount;
|
||||
private final int decimalPlaces;
|
||||
|
||||
public MoneyData(final String code, final BigDecimal amount, final int decimalPlaces) {
|
||||
this.code = code;
|
||||
this.amount = amount;
|
||||
this.decimalPlaces = decimalPlaces;
|
||||
}
|
||||
|
||||
public String getCode() {
|
||||
return this.code;
|
||||
}
|
||||
|
||||
public BigDecimal getAmount() {
|
||||
return this.amount;
|
||||
}
|
||||
|
||||
public int getDecimalPlaces() {
|
||||
return this.decimalPlaces;
|
||||
}
|
||||
|
||||
}
|
||||
-1
@@ -23,7 +23,6 @@ import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Table;
|
||||
import org.apache.fineract.infrastructure.core.domain.AbstractPersistableCustom;
|
||||
import org.apache.fineract.organisation.monetary.data.CurrencyData;
|
||||
import org.apache.fineract.organisation.office.domain.OrganisationCurrency;
|
||||
|
||||
@Entity
|
||||
@Table(name = "m_currency")
|
||||
|
||||
+43
@@ -0,0 +1,43 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.domain;
|
||||
|
||||
import java.util.List;
|
||||
import org.apache.fineract.organisation.monetary.data.CurrencyData;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
|
||||
import org.springframework.data.jpa.repository.Query;
|
||||
import org.springframework.data.repository.query.Param;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
public interface ApplicationCurrencyRepository
|
||||
extends JpaRepository<ApplicationCurrency, Long>, JpaSpecificationExecutor<ApplicationCurrency> {
|
||||
|
||||
String FIND_CURRENCY_DETAILS = "SELECT new org.apache.fineract.organisation.monetary.data.CurrencyData(ac.code, ac.name, ac.decimalPlaces, ac.inMultiplesOf, ac.displaySymbol, ac.nameCode) FROM ApplicationCurrency ac ";
|
||||
|
||||
ApplicationCurrency findOneByCode(String currencyCode);
|
||||
|
||||
@Query(FIND_CURRENCY_DETAILS + " WHERE ac.code = :code")
|
||||
CurrencyData findCurrencyDataByCode(@Param("code") String currencyCode);
|
||||
|
||||
@Query(FIND_CURRENCY_DETAILS)
|
||||
List<CurrencyData> findAllSorted(Sort sort);
|
||||
}
|
||||
+69
@@ -0,0 +1,69 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.domain;
|
||||
|
||||
import org.apache.fineract.organisation.monetary.exception.CurrencyNotFoundException;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
/**
|
||||
* <p>
|
||||
* Wrapper for {@link ApplicationCurrencyRepository} that is responsible for checking if {@link ApplicationCurrency} is
|
||||
* returned when using <code>findOne</code> repository method and throwing an appropriate not found exception.
|
||||
* </p>
|
||||
*
|
||||
* <p>
|
||||
* This is to avoid need for checking and throwing in multiple areas of code base where
|
||||
* {@link ApplicationCurrencyRepository} is required.
|
||||
* </p>
|
||||
*/
|
||||
@Service
|
||||
public class ApplicationCurrencyRepositoryWrapper {
|
||||
|
||||
private final ApplicationCurrencyRepository repository;
|
||||
|
||||
@Autowired
|
||||
public ApplicationCurrencyRepositoryWrapper(final ApplicationCurrencyRepository repository) {
|
||||
this.repository = repository;
|
||||
}
|
||||
|
||||
public ApplicationCurrency findOneWithNotFoundDetection(final MonetaryCurrency currency) {
|
||||
|
||||
final ApplicationCurrency defaultApplicationCurrency = this.repository.findOneByCode(currency.getCode());
|
||||
if (defaultApplicationCurrency == null) {
|
||||
throw new CurrencyNotFoundException(currency.getCode());
|
||||
}
|
||||
|
||||
final ApplicationCurrency applicationCurrency = ApplicationCurrency.from(defaultApplicationCurrency,
|
||||
currency.getDigitsAfterDecimal(), currency.getCurrencyInMultiplesOf());
|
||||
|
||||
return applicationCurrency;
|
||||
}
|
||||
|
||||
/**
|
||||
* Used when its not needed for {@link ApplicationCurrency} to inherit decimal place settings of existing currency.
|
||||
*/
|
||||
public ApplicationCurrency findOneWithNotFoundDetection(final String currencyCode) {
|
||||
final ApplicationCurrency applicationCurrency = this.repository.findOneByCode(currencyCode);
|
||||
if (applicationCurrency == null) {
|
||||
throw new CurrencyNotFoundException(currencyCode);
|
||||
}
|
||||
return applicationCurrency;
|
||||
}
|
||||
}
|
||||
+1
-2
@@ -16,13 +16,12 @@
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.office.domain;
|
||||
package org.apache.fineract.organisation.monetary.domain;
|
||||
|
||||
import jakarta.persistence.Column;
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Table;
|
||||
import org.apache.fineract.infrastructure.core.domain.AbstractPersistableCustom;
|
||||
import org.apache.fineract.organisation.monetary.domain.MonetaryCurrency;
|
||||
|
||||
/**
|
||||
* Represents currencies allowed for this MFI/organisation.
|
||||
+39
@@ -0,0 +1,39 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.domain;
|
||||
|
||||
import java.util.List;
|
||||
import org.apache.fineract.organisation.monetary.data.CurrencyData;
|
||||
import org.springframework.data.domain.Sort;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
|
||||
import org.springframework.data.jpa.repository.Query;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
public interface OrganisationCurrencyRepository
|
||||
extends JpaRepository<OrganisationCurrency, Long>, JpaSpecificationExecutor<OrganisationCurrency> {
|
||||
|
||||
String FIND_CURRENCY_DETAILS = "SELECT new org.apache.fineract.organisation.monetary.data.CurrencyData(oc.code, oc.name, oc.decimalPlaces, oc.inMultiplesOf, oc.displaySymbol, oc.nameCode) FROM OrganisationCurrency oc ";
|
||||
|
||||
OrganisationCurrency findOneByCode(String currencyCode);
|
||||
|
||||
@Query(FIND_CURRENCY_DETAILS)
|
||||
List<CurrencyData> findAllSorted(Sort sort);
|
||||
}
|
||||
+53
@@ -0,0 +1,53 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.domain;
|
||||
|
||||
import org.apache.fineract.organisation.monetary.exception.OrganizationalCurrencyNotFoundException;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
/**
|
||||
* <p>
|
||||
* Wrapper for {@link OrganisationCurrency} that is responsible for checking if {@link OrganisationCurrency} is returned
|
||||
* when using <code>findOne</code> repository method and throwing an appropriate not found exception.
|
||||
* </p>
|
||||
*
|
||||
* <p>
|
||||
* This is to avoid need for checking and throwing in multiple areas of code base where {@link OrganisationCurrency} is
|
||||
* required.
|
||||
* </p>
|
||||
*/
|
||||
@Service
|
||||
public class OrganisationCurrencyRepositoryWrapper {
|
||||
|
||||
private final OrganisationCurrencyRepository repository;
|
||||
|
||||
@Autowired
|
||||
public OrganisationCurrencyRepositoryWrapper(final OrganisationCurrencyRepository repository) {
|
||||
this.repository = repository;
|
||||
}
|
||||
|
||||
public OrganisationCurrency findOneWithNotFoundDetection(final String currencyCode) {
|
||||
final OrganisationCurrency organisationCurrency = this.repository.findOneByCode(currencyCode);
|
||||
if (organisationCurrency == null) {
|
||||
throw new OrganizationalCurrencyNotFoundException(currencyCode);
|
||||
}
|
||||
return organisationCurrency;
|
||||
}
|
||||
}
|
||||
+33
@@ -0,0 +1,33 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformDomainRuleException;
|
||||
|
||||
/**
|
||||
* A {@link RuntimeException} thrown when trying to delete a currency that is still in use.
|
||||
*/
|
||||
public class CurrencyInUseException extends AbstractPlatformDomainRuleException {
|
||||
|
||||
public CurrencyInUseException(final String currencyCode) {
|
||||
super("error.msg.currency.currencyCode.inUse",
|
||||
"Cannot remove currency with identifier " + currencyCode + " while it is still in use", currencyCode);
|
||||
}
|
||||
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformResourceNotFoundException;
|
||||
|
||||
/**
|
||||
* A {@link RuntimeException} thrown when loan resources are not found.
|
||||
*/
|
||||
public class CurrencyNotFoundException extends AbstractPlatformResourceNotFoundException {
|
||||
|
||||
public CurrencyNotFoundException(final String currencyCode) {
|
||||
super("error.msg.currency.currencyCode.invalid", "Currency with identifier " + currencyCode + " does not exist", currencyCode);
|
||||
}
|
||||
}
|
||||
+32
@@ -0,0 +1,32 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformResourceNotFoundException;
|
||||
|
||||
/**
|
||||
* A {@link RuntimeException} thrown when urrency is not supported by an Organization.
|
||||
*/
|
||||
public class OrganizationalCurrencyNotFoundException extends AbstractPlatformResourceNotFoundException {
|
||||
|
||||
public OrganizationalCurrencyNotFoundException(final String currencyCode) {
|
||||
super("error.msg.currency.currencyCode.invalid.or.not.supported",
|
||||
"Currency with identifier " + currencyCode + " does not exist or is not supported by the Organization", currencyCode);
|
||||
}
|
||||
}
|
||||
+79
@@ -0,0 +1,79 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.serialization;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.fineract.infrastructure.core.data.ApiParameterError;
|
||||
import org.apache.fineract.infrastructure.core.data.DataValidatorBuilder;
|
||||
import org.apache.fineract.infrastructure.core.exception.InvalidJsonException;
|
||||
import org.apache.fineract.infrastructure.core.exception.PlatformApiDataValidationException;
|
||||
import org.apache.fineract.infrastructure.core.serialization.FromJsonHelper;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public final class CurrencyCommandFromApiJsonDeserializer {
|
||||
|
||||
public static final String CURRENCIES = "currencies";
|
||||
/**
|
||||
* The parameters supported for this command.
|
||||
*/
|
||||
private static final Set<String> SUPPORTED_PARAMETERS = new HashSet<>(List.of(CURRENCIES));
|
||||
|
||||
private final FromJsonHelper fromApiJsonHelper;
|
||||
|
||||
@Autowired
|
||||
public CurrencyCommandFromApiJsonDeserializer(final FromJsonHelper fromApiJsonHelper) {
|
||||
this.fromApiJsonHelper = fromApiJsonHelper;
|
||||
}
|
||||
|
||||
public void validateForUpdate(final String json) {
|
||||
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
}
|
||||
|
||||
final Type typeOfMap = new TypeToken<Map<String, Object>>() {}.getType();
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(typeOfMap, json, SUPPORTED_PARAMETERS);
|
||||
|
||||
final List<ApiParameterError> dataValidationErrors = new ArrayList<>();
|
||||
final DataValidatorBuilder baseDataValidator = new DataValidatorBuilder(dataValidationErrors).resource(CURRENCIES);
|
||||
|
||||
final JsonElement element = this.fromApiJsonHelper.parse(json);
|
||||
final String[] currencies = this.fromApiJsonHelper.extractArrayNamed(CURRENCIES, element);
|
||||
baseDataValidator.reset().parameter(CURRENCIES).value(currencies).arrayNotEmpty();
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
|
||||
private void throwExceptionIfValidationWarningsExist(final List<ApiParameterError> dataValidationErrors) {
|
||||
if (!dataValidationErrors.isEmpty()) {
|
||||
throw new PlatformApiDataValidationException("validation.msg.validation.errors.exist", "Validation errors exist.",
|
||||
dataValidationErrors);
|
||||
}
|
||||
}
|
||||
}
|
||||
+83
@@ -0,0 +1,83 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.service;
|
||||
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
import java.util.Collection;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.core.domain.JdbcSupport;
|
||||
import org.apache.fineract.infrastructure.security.service.PlatformSecurityContext;
|
||||
import org.apache.fineract.organisation.monetary.data.CurrencyData;
|
||||
import org.springframework.jdbc.core.JdbcTemplate;
|
||||
import org.springframework.jdbc.core.RowMapper;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public class CurrencyReadPlatformServiceImpl implements CurrencyReadPlatformService {
|
||||
|
||||
private final PlatformSecurityContext context;
|
||||
private final JdbcTemplate jdbcTemplate;
|
||||
private final CurrencyMapper currencyRowMapper = new CurrencyMapper();
|
||||
|
||||
@Override
|
||||
public Collection<CurrencyData> retrieveAllowedCurrencies() {
|
||||
|
||||
this.context.authenticatedUser();
|
||||
|
||||
final String sql = "select " + this.currencyRowMapper.schema() + " from m_organisation_currency c order by c.name";
|
||||
|
||||
return this.jdbcTemplate.query(sql, this.currencyRowMapper); // NOSONAR
|
||||
}
|
||||
|
||||
@Override
|
||||
public Collection<CurrencyData> retrieveAllPlatformCurrencies() {
|
||||
|
||||
final String sql = "select " + this.currencyRowMapper.schema() + " from m_currency c order by c.name";
|
||||
|
||||
return this.jdbcTemplate.query(sql, this.currencyRowMapper); // NOSONAR
|
||||
}
|
||||
|
||||
@Override
|
||||
public CurrencyData retrieveCurrency(final String code) {
|
||||
|
||||
final String sql = "select " + this.currencyRowMapper.schema() + " from m_currency c where c.code = ? order by c.name";
|
||||
|
||||
return this.jdbcTemplate.queryForObject(sql, this.currencyRowMapper, new Object[] { code }); // NOSONAR
|
||||
}
|
||||
|
||||
private static final class CurrencyMapper implements RowMapper<CurrencyData> {
|
||||
|
||||
@Override
|
||||
public CurrencyData mapRow(final ResultSet rs, @SuppressWarnings("unused") final int rowNum) throws SQLException {
|
||||
|
||||
final String code = rs.getString("code");
|
||||
final String name = rs.getString("name");
|
||||
final int decimalPlaces = JdbcSupport.getInteger(rs, "decimalPlaces");
|
||||
final Integer inMultiplesOf = JdbcSupport.getInteger(rs, "inMultiplesOf");
|
||||
final String displaySymbol = rs.getString("displaySymbol");
|
||||
final String nameCode = rs.getString("nameCode");
|
||||
|
||||
return new CurrencyData(code, name, decimalPlaces, inMultiplesOf, displaySymbol, nameCode);
|
||||
}
|
||||
|
||||
public String schema() {
|
||||
return " c.code as code, c.name as name, c.decimal_places as decimalPlaces,c.currency_multiplesof as inMultiplesOf, c.display_symbol as displaySymbol, c.internationalized_name_code as nameCode ";
|
||||
}
|
||||
}
|
||||
}
|
||||
+42
@@ -0,0 +1,42 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.organisation.monetary.service;
|
||||
|
||||
import java.util.Collection;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.organisation.monetary.data.ApplicationCurrencyConfigurationData;
|
||||
import org.apache.fineract.organisation.monetary.data.CurrencyData;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public class OrganisationCurrencyReadPlatformServiceImpl implements OrganisationCurrencyReadPlatformService {
|
||||
|
||||
private final CurrencyReadPlatformService currencyReadPlatformService;
|
||||
|
||||
@Override
|
||||
public ApplicationCurrencyConfigurationData retrieveCurrencyConfiguration() {
|
||||
|
||||
final Collection<CurrencyData> selectedCurrencyOptions = this.currencyReadPlatformService.retrieveAllowedCurrencies();
|
||||
final Collection<CurrencyData> currencyOptions = this.currencyReadPlatformService.retrieveAllPlatformCurrencies();
|
||||
|
||||
// remove selected currency options
|
||||
currencyOptions.removeAll(selectedCurrencyOptions);
|
||||
|
||||
return new ApplicationCurrencyConfigurationData(currencyOptions, selectedCurrencyOptions);
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -16,7 +16,7 @@
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.accounting.producttoaccountmapping.domain;
|
||||
package org.apache.fineract.portfolio;
|
||||
|
||||
public enum PortfolioProductType {
|
||||
|
||||
+49
@@ -0,0 +1,49 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.domain;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.domain.ExternalId;
|
||||
import org.apache.fineract.portfolio.client.domain.search.SearchingClientRepository;
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
|
||||
import org.springframework.data.jpa.repository.Query;
|
||||
import org.springframework.data.repository.query.Param;
|
||||
|
||||
public interface ClientRepository extends JpaRepository<Client, Long>, JpaSpecificationExecutor<Client>, SearchingClientRepository {
|
||||
|
||||
String FIND_CLIENT_BY_ACCOUNT_NUMBER = "select client from Client client where client.accountNumber = :accountNumber";
|
||||
|
||||
@Query(FIND_CLIENT_BY_ACCOUNT_NUMBER)
|
||||
Client getClientByAccountNumber(@Param("accountNumber") String accountNumber);
|
||||
|
||||
@Query("""
|
||||
SELECT client
|
||||
FROM Client client
|
||||
JOIN client.office office
|
||||
LEFT JOIN client.transferToOffice transferToOffice
|
||||
WHERE client.id = :clientId
|
||||
AND (office.hierarchy LIKE :officeHierarchy OR transferToOffice.hierarchy LIKE :transferToOfficeHierarchy)
|
||||
""")
|
||||
Client fetchByClientIdAndHierarchy(@Param("clientId") Long clientId, @Param("officeHierarchy") String officeHierarchy,
|
||||
@Param("transferToOfficeHierarchy") String transferToOfficeHierarchy);
|
||||
|
||||
@Query("SELECT c.id FROM Client c WHERE c.externalId = :externalId")
|
||||
Long findIdByExternalId(@Param("externalId") ExternalId externalId);
|
||||
|
||||
}
|
||||
+41
@@ -0,0 +1,41 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.domain.search;
|
||||
|
||||
import java.time.LocalDate;
|
||||
import java.time.OffsetDateTime;
|
||||
import lombok.Getter;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.core.domain.ExternalId;
|
||||
|
||||
@Getter
|
||||
@RequiredArgsConstructor
|
||||
public class SearchedClient {
|
||||
|
||||
private final Long id;
|
||||
private final String displayName;
|
||||
private final ExternalId externalId;
|
||||
private final String accountNumber;
|
||||
private final Long officeId;
|
||||
private final String officeName;
|
||||
private final String mobileNo;
|
||||
private final Integer status;
|
||||
private final LocalDate activationDate;
|
||||
private final OffsetDateTime createdDate;
|
||||
}
|
||||
+27
@@ -0,0 +1,27 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.domain.search;
|
||||
|
||||
import org.springframework.data.domain.Page;
|
||||
import org.springframework.data.domain.Pageable;
|
||||
|
||||
public interface SearchingClientRepository {
|
||||
|
||||
Page<SearchedClient> searchByText(String searchText, Pageable pageable, String officeHierarchy);
|
||||
}
|
||||
+93
@@ -0,0 +1,93 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.domain.search;
|
||||
|
||||
import jakarta.persistence.EntityManager;
|
||||
import jakarta.persistence.TypedQuery;
|
||||
import jakarta.persistence.criteria.CriteriaBuilder;
|
||||
import jakarta.persistence.criteria.CriteriaQuery;
|
||||
import jakarta.persistence.criteria.Join;
|
||||
import jakarta.persistence.criteria.JoinType;
|
||||
import jakarta.persistence.criteria.Order;
|
||||
import jakarta.persistence.criteria.Path;
|
||||
import jakarta.persistence.criteria.Predicate;
|
||||
import jakarta.persistence.criteria.Root;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.core.jpa.CriteriaQueryFactory;
|
||||
import org.apache.fineract.organisation.office.domain.Office;
|
||||
import org.apache.fineract.portfolio.client.domain.Client;
|
||||
import org.apache.fineract.portfolio.client.domain.ClientIdentifier;
|
||||
import org.springframework.data.domain.Page;
|
||||
import org.springframework.data.domain.Pageable;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
@RequiredArgsConstructor
|
||||
public class SearchingClientRepositoryImpl implements SearchingClientRepository {
|
||||
|
||||
private final EntityManager entityManager;
|
||||
private final CriteriaQueryFactory criteriaQueryFactory;
|
||||
|
||||
@Override
|
||||
public Page<SearchedClient> searchByText(String searchText, Pageable pageable, String officeHierarchy) {
|
||||
/*
|
||||
* this whole thing can be replaced with Spring Data JPA 3+ with a findBy(Specification, Pageable) call but at
|
||||
* this point the upgrade is too costly
|
||||
*
|
||||
* https://github.com/spring-projects/spring-data-jpa/issues/2499
|
||||
*/
|
||||
String hierarchyLikeValue = officeHierarchy + "%";
|
||||
|
||||
CriteriaBuilder cb = entityManager.getCriteriaBuilder();
|
||||
CriteriaQuery<SearchedClient> query = cb.createQuery(SearchedClient.class);
|
||||
|
||||
Root<Client> root = query.from(Client.class);
|
||||
Path<Office> office = root.get("office");
|
||||
|
||||
Specification<Client> spec = (r, q, builder) -> {
|
||||
Path<Office> o = r.get("office");
|
||||
Join<Client, ClientIdentifier> identity = r.join("identifiers", JoinType.LEFT);
|
||||
|
||||
List<Predicate> predicates = new ArrayList<>();
|
||||
predicates.add(cb.like(o.get("hierarchy"), hierarchyLikeValue));
|
||||
|
||||
String searchLikeValue = "%" + searchText + "%";
|
||||
predicates.add(cb.or(cb.like(r.get("accountNumber"), searchLikeValue), cb.like(r.get("displayName"), searchLikeValue),
|
||||
cb.like(r.get("externalId"), searchLikeValue), cb.like(r.get("mobileNo"), searchLikeValue),
|
||||
cb.like(identity.get("documentKey"), searchLikeValue)));
|
||||
|
||||
return cb.and(predicates.toArray(new Predicate[0]));
|
||||
};
|
||||
criteriaQueryFactory.applySpecificationToCriteria(root, spec, query);
|
||||
|
||||
List<Order> orders = criteriaQueryFactory.ordersFromPageable(pageable, cb, root, () -> cb.desc(root.get("id")));
|
||||
query.orderBy(orders);
|
||||
|
||||
query.select(cb.construct(SearchedClient.class, root.get("id"), root.get("displayName"), root.get("externalId"),
|
||||
root.get("accountNumber"), office.get("id"), office.get("name"), root.get("mobileNo"), root.get("status"),
|
||||
root.get("activationDate"), root.get("createdDate")));
|
||||
|
||||
TypedQuery<SearchedClient> queryToExecute = entityManager.createQuery(query);
|
||||
|
||||
return criteriaQueryFactory.readPage(queryToExecute, Client.class, pageable, spec);
|
||||
}
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformDomainRuleException;
|
||||
|
||||
public class ClientNotActiveException extends AbstractPlatformDomainRuleException {
|
||||
|
||||
public ClientNotActiveException(final Long clientId) {
|
||||
super("error.msg.client.not.active.exception", "The Client with id `" + clientId + "` is not active", clientId);
|
||||
}
|
||||
|
||||
}
|
||||
+49
@@ -0,0 +1,49 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.client.exception;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.domain.ExternalId;
|
||||
import org.apache.fineract.infrastructure.core.exception.AbstractPlatformResourceNotFoundException;
|
||||
import org.springframework.dao.EmptyResultDataAccessException;
|
||||
|
||||
/**
|
||||
* A {@link RuntimeException} thrown when client resources are not found.
|
||||
*/
|
||||
public class ClientNotFoundException extends AbstractPlatformResourceNotFoundException {
|
||||
|
||||
public ClientNotFoundException(final Long id) {
|
||||
super("error.msg.client.id.invalid", "Client with identifier " + id + " does not exist", id);
|
||||
}
|
||||
|
||||
public ClientNotFoundException(final ExternalId externalId) {
|
||||
super("error.msg.client.id.invalid", "Client with identifier " + externalId + " does not exist", externalId);
|
||||
}
|
||||
|
||||
public ClientNotFoundException() {
|
||||
super("error.msg.client.not.found.with.basic.details", "Client not found with basic details.");
|
||||
}
|
||||
|
||||
public ClientNotFoundException(String value, String valueType) {
|
||||
super("error.msg.client.not.found.with." + valueType, "Client not found with valuer " + value + ".", value);
|
||||
}
|
||||
|
||||
public ClientNotFoundException(Long id, EmptyResultDataAccessException e) {
|
||||
super("error.msg.client.id.invalid", "Client with identifier " + id + " does not exist", id, e);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.note.domain;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
import org.apache.fineract.infrastructure.core.data.EnumOptionData;
|
||||
|
||||
public enum NoteType {
|
||||
|
||||
CLIENT(100, "noteType.client", "clients", "Client note"), //
|
||||
LOAN(200, "noteType.loan", "loans", "Loan note"), //
|
||||
LOAN_TRANSACTION(300, "noteType.loan.transaction", "loanTransactions", "Loan transaction note"), //
|
||||
SAVING_ACCOUNT(500, "noteType.saving", "savings", " account note"), //
|
||||
GROUP(600, "noteType.group", "groups", "Group note"), //
|
||||
SHARE_ACCOUNT(700, "noteType.shares", "accounts/share", "Share account note"), //
|
||||
SAVINGS_TRANSACTION(800, "noteType.savings.transaction", "savingsTransactions", "Savings transaction note"), //
|
||||
;
|
||||
|
||||
public static final NoteType[] VALUES = values();
|
||||
|
||||
private static final Map<Integer, NoteType> BY_ID = Arrays.stream(VALUES).collect(Collectors.toMap(NoteType::getValue, v -> v));
|
||||
private static final Map<String, NoteType> BY_API = Arrays.stream(VALUES).collect(Collectors.toMap(NoteType::getApiUrl, v -> v));
|
||||
|
||||
private final Integer value;
|
||||
private final String code;
|
||||
private final String apiUrl;
|
||||
private final String description;
|
||||
|
||||
NoteType(final Integer value, final String code, final String apiUrl, String description) {
|
||||
this.value = value;
|
||||
this.code = code;
|
||||
this.apiUrl = apiUrl;
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
public Integer getValue() {
|
||||
return this.value;
|
||||
}
|
||||
|
||||
public String getCode() {
|
||||
return this.code;
|
||||
}
|
||||
|
||||
public String getApiUrl() {
|
||||
return this.apiUrl;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public static NoteType fromInt(int i) {
|
||||
return BY_ID.get(i);
|
||||
}
|
||||
|
||||
public static NoteType fromApiUrl(final String url) {
|
||||
return BY_API.get(url);
|
||||
}
|
||||
|
||||
public EnumOptionData toEnumOptionData() {
|
||||
return new EnumOptionData(getValue().longValue(), getCode(), getDescription());
|
||||
}
|
||||
}
|
||||
+29
@@ -0,0 +1,29 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.note.service;
|
||||
|
||||
import java.util.Collection;
|
||||
import org.apache.fineract.portfolio.note.data.NoteData;
|
||||
|
||||
public interface NoteReadPlatformService {
|
||||
|
||||
NoteData retrieveNote(Long noteId, Long resourceId, Integer noteTypeId);
|
||||
|
||||
Collection<NoteData> retrieveNotesByResource(Long resourceId, Integer noteTypeId);
|
||||
}
|
||||
+34
@@ -0,0 +1,34 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.note.service;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.portfolio.client.domain.Client;
|
||||
|
||||
public interface NoteWritePlatformService {
|
||||
|
||||
CommandProcessingResult createNote(JsonCommand command);
|
||||
|
||||
CommandProcessingResult updateNote(JsonCommand command);
|
||||
|
||||
CommandProcessingResult deleteNote(JsonCommand command);
|
||||
|
||||
void createAndPersistClientNote(Client client, JsonCommand command);
|
||||
}
|
||||
+56
@@ -0,0 +1,56 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymentdetail.domain;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import org.apache.fineract.infrastructure.core.serialization.FromJsonHelper;
|
||||
import org.apache.fineract.portfolio.paymentdetail.PaymentDetailConstants;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentType;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
@Service
|
||||
public class PaymentDetailAssembler {
|
||||
|
||||
private final FromJsonHelper fromApiJsonHelper;
|
||||
private final PaymentTypeRepositoryWrapper repositoryWrapper;
|
||||
|
||||
@Autowired
|
||||
public PaymentDetailAssembler(final FromJsonHelper fromApiJsonHelper, final PaymentTypeRepositoryWrapper repositoryWrapper) {
|
||||
this.fromApiJsonHelper = fromApiJsonHelper;
|
||||
this.repositoryWrapper = repositoryWrapper;
|
||||
}
|
||||
|
||||
public PaymentDetail fetchPaymentDetail(final JsonObject json) {
|
||||
final Long paymentTypeId = this.fromApiJsonHelper.extractLongNamed(PaymentDetailConstants.paymentTypeParamName, json);
|
||||
if (paymentTypeId == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final PaymentType paymentType = this.repositoryWrapper.findOneWithNotFoundDetection(paymentTypeId);
|
||||
|
||||
final String accountNumber = this.fromApiJsonHelper.extractStringNamed(PaymentDetailConstants.accountNumberParamName, json);
|
||||
final String checkNumber = this.fromApiJsonHelper.extractStringNamed(PaymentDetailConstants.checkNumberParamName, json);
|
||||
final String routingCode = this.fromApiJsonHelper.extractStringNamed(PaymentDetailConstants.routingCodeParamName, json);
|
||||
final String receiptNumber = this.fromApiJsonHelper.extractStringNamed(PaymentDetailConstants.receiptNumberParamName, json);
|
||||
final String bankNumber = this.fromApiJsonHelper.extractStringNamed(PaymentDetailConstants.bankNumberParamName, json);
|
||||
return PaymentDetail.instance(paymentType, accountNumber, checkNumber, routingCode, receiptNumber, bankNumber);
|
||||
}
|
||||
}
|
||||
+28
@@ -0,0 +1,28 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymentdetail.domain;
|
||||
|
||||
import org.springframework.data.jpa.repository.JpaRepository;
|
||||
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
|
||||
import org.springframework.stereotype.Repository;
|
||||
|
||||
@Repository
|
||||
public interface PaymentDetailRepository extends JpaRepository<PaymentDetail, Long>, JpaSpecificationExecutor<PaymentDetail> {
|
||||
// no added behaviour
|
||||
}
|
||||
+32
@@ -0,0 +1,32 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymentdetail.service;
|
||||
|
||||
import java.util.Map;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.portfolio.paymentdetail.domain.PaymentDetail;
|
||||
|
||||
public interface PaymentDetailWritePlatformService {
|
||||
|
||||
PaymentDetail createAndPersistPaymentDetail(JsonCommand command, Map<String, Object> changes);
|
||||
|
||||
PaymentDetail createPaymentDetail(JsonCommand command, Map<String, Object> changes);
|
||||
|
||||
PaymentDetail persistPaymentDetail(PaymentDetail paymentDetail);
|
||||
}
|
||||
+66
@@ -0,0 +1,66 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymentdetail.service;
|
||||
|
||||
import java.util.Map;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.portfolio.paymentdetail.PaymentDetailConstants;
|
||||
import org.apache.fineract.portfolio.paymentdetail.domain.PaymentDetail;
|
||||
import org.apache.fineract.portfolio.paymentdetail.domain.PaymentDetailRepository;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentType;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public class PaymentDetailWritePlatformServiceJpaRepositoryImpl implements PaymentDetailWritePlatformService {
|
||||
|
||||
private final PaymentDetailRepository paymentDetailRepository;
|
||||
// private final CodeValueRepositoryWrapper codeValueRepositoryWrapper;
|
||||
private final PaymentTypeRepositoryWrapper paymentTyperepositoryWrapper;
|
||||
|
||||
@Override
|
||||
public PaymentDetail createPaymentDetail(final JsonCommand command, final Map<String, Object> changes) {
|
||||
final Long paymentTypeId = command.longValueOfParameterNamed(PaymentDetailConstants.paymentTypeParamName);
|
||||
if (paymentTypeId == null) {
|
||||
return null;
|
||||
}
|
||||
|
||||
final PaymentType paymentType = this.paymentTyperepositoryWrapper.findOneWithNotFoundDetection(paymentTypeId);
|
||||
final PaymentDetail paymentDetail = PaymentDetail.generatePaymentDetail(paymentType, command, changes);
|
||||
return paymentDetail;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional
|
||||
public PaymentDetail persistPaymentDetail(final PaymentDetail paymentDetail) {
|
||||
return this.paymentDetailRepository.saveAndFlush(paymentDetail);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional
|
||||
public PaymentDetail createAndPersistPaymentDetail(final JsonCommand command, final Map<String, Object> changes) {
|
||||
final PaymentDetail paymentDetail = createPaymentDetail(command, changes);
|
||||
if (paymentDetail != null) {
|
||||
return persistPaymentDetail(paymentDetail);
|
||||
}
|
||||
return paymentDetail;
|
||||
}
|
||||
}
|
||||
+38
@@ -0,0 +1,38 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymentdetail.starter;
|
||||
|
||||
import org.apache.fineract.portfolio.paymentdetail.domain.PaymentDetailRepository;
|
||||
import org.apache.fineract.portfolio.paymentdetail.service.PaymentDetailWritePlatformService;
|
||||
import org.apache.fineract.portfolio.paymentdetail.service.PaymentDetailWritePlatformServiceJpaRepositoryImpl;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@Configuration
|
||||
public class PaymentDetailConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(PaymentDetailWritePlatformService.class)
|
||||
PaymentDetailWritePlatformService paymentDetailWritePlatformService(PaymentDetailRepository paymentDetailRepository,
|
||||
PaymentTypeRepositoryWrapper paymentTyperepositoryWrapper) {
|
||||
return new PaymentDetailWritePlatformServiceJpaRepositoryImpl(paymentDetailRepository, paymentTyperepositoryWrapper);
|
||||
}
|
||||
}
|
||||
+157
@@ -0,0 +1,157 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.api;
|
||||
|
||||
import io.swagger.v3.oas.annotations.Operation;
|
||||
import io.swagger.v3.oas.annotations.Parameter;
|
||||
import io.swagger.v3.oas.annotations.media.ArraySchema;
|
||||
import io.swagger.v3.oas.annotations.media.Content;
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
import io.swagger.v3.oas.annotations.parameters.RequestBody;
|
||||
import io.swagger.v3.oas.annotations.responses.ApiResponse;
|
||||
import io.swagger.v3.oas.annotations.responses.ApiResponses;
|
||||
import io.swagger.v3.oas.annotations.tags.Tag;
|
||||
import jakarta.ws.rs.Consumes;
|
||||
import jakarta.ws.rs.DELETE;
|
||||
import jakarta.ws.rs.GET;
|
||||
import jakarta.ws.rs.POST;
|
||||
import jakarta.ws.rs.PUT;
|
||||
import jakarta.ws.rs.Path;
|
||||
import jakarta.ws.rs.PathParam;
|
||||
import jakarta.ws.rs.Produces;
|
||||
import jakarta.ws.rs.QueryParam;
|
||||
import jakarta.ws.rs.core.Context;
|
||||
import jakarta.ws.rs.core.MediaType;
|
||||
import jakarta.ws.rs.core.UriInfo;
|
||||
import java.util.Collection;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.commands.domain.CommandWrapper;
|
||||
import org.apache.fineract.commands.service.CommandWrapperBuilder;
|
||||
import org.apache.fineract.commands.service.PortfolioCommandSourceWritePlatformService;
|
||||
import org.apache.fineract.infrastructure.core.api.ApiRequestParameterHelper;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.infrastructure.core.serialization.ApiRequestJsonSerializationSettings;
|
||||
import org.apache.fineract.infrastructure.core.serialization.DefaultToApiJsonSerializer;
|
||||
import org.apache.fineract.infrastructure.security.service.PlatformSecurityContext;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeData;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeReadPlatformService;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Path("/v1/paymenttypes")
|
||||
@Component
|
||||
@Tag(name = "Payment Type", description = "This defines the payment type")
|
||||
@RequiredArgsConstructor
|
||||
public class PaymentTypeApiResource {
|
||||
|
||||
private final PlatformSecurityContext securityContext;
|
||||
private final DefaultToApiJsonSerializer<PaymentTypeData> jsonSerializer;
|
||||
private final PaymentTypeReadPlatformService readPlatformService;
|
||||
private final PortfolioCommandSourceWritePlatformService commandWritePlatformService;
|
||||
private final ApiRequestParameterHelper apiRequestParameterHelper;
|
||||
private final PaymentTypeRepositoryWrapper paymentTypeRepositoryWrapper;
|
||||
|
||||
@GET
|
||||
@Consumes({ MediaType.TEXT_HTML, MediaType.APPLICATION_JSON })
|
||||
@Produces(MediaType.APPLICATION_JSON)
|
||||
@Operation(summary = "Retrieve all Payment Types", description = "Retrieve list of payment types")
|
||||
@ApiResponses({
|
||||
@ApiResponse(responseCode = "200", description = "OK", content = @Content(array = @ArraySchema(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.GetPaymentTypesResponse.class)))) })
|
||||
public String getAllPaymentTypes(@Context final UriInfo uriInfo,
|
||||
@QueryParam("onlyWithCode") @Parameter(description = "onlyWithCode") final boolean onlyWithCode) {
|
||||
this.securityContext.authenticatedUser().validateHasReadPermission(PaymentTypeApiResourceConstants.ENTITY_NAME);
|
||||
Collection<PaymentTypeData> paymentTypes = null;
|
||||
if (onlyWithCode) {
|
||||
paymentTypes = this.readPlatformService.retrieveAllPaymentTypesWithCode();
|
||||
} else {
|
||||
paymentTypes = this.readPlatformService.retrieveAllPaymentTypes();
|
||||
}
|
||||
final ApiRequestJsonSerializationSettings settings = this.apiRequestParameterHelper.process(uriInfo.getQueryParameters());
|
||||
return this.jsonSerializer.serialize(settings, paymentTypes, PaymentTypeApiResourceConstants.RESPONSE_DATA_PARAMETERS);
|
||||
}
|
||||
|
||||
@GET
|
||||
@Path("{paymentTypeId}")
|
||||
@Consumes({ MediaType.TEXT_HTML, MediaType.APPLICATION_JSON })
|
||||
@Produces(MediaType.APPLICATION_JSON)
|
||||
@Operation(summary = "Retrieve a Payment Type", description = "Retrieves a payment type")
|
||||
@ApiResponses({
|
||||
@ApiResponse(responseCode = "200", description = "OK", content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.GetPaymentTypesPaymentTypeIdResponse.class))) })
|
||||
public String retrieveOnePaymentType(@PathParam("paymentTypeId") @Parameter(description = "paymentTypeId") final Long paymentTypeId,
|
||||
@Context final UriInfo uriInfo) {
|
||||
this.securityContext.authenticatedUser().validateHasReadPermission(PaymentTypeApiResourceConstants.ENTITY_NAME);
|
||||
this.paymentTypeRepositoryWrapper.findOneWithNotFoundDetection(paymentTypeId);
|
||||
final PaymentTypeData paymentTypes = this.readPlatformService.retrieveOne(paymentTypeId);
|
||||
final ApiRequestJsonSerializationSettings settings = this.apiRequestParameterHelper.process(uriInfo.getQueryParameters());
|
||||
return this.jsonSerializer.serialize(settings, paymentTypes, PaymentTypeApiResourceConstants.RESPONSE_DATA_PARAMETERS);
|
||||
}
|
||||
|
||||
@POST
|
||||
@Consumes({ MediaType.APPLICATION_JSON })
|
||||
@Produces({ MediaType.APPLICATION_JSON })
|
||||
@Operation(summary = "Create a Payment Type", description = "Creates a new Payment type\n\n" + "Mandatory Fields: name\n\n"
|
||||
+ "Optional Fields: Description, isCashPayment,Position")
|
||||
@RequestBody(required = true, content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.PostPaymentTypesRequest.class)))
|
||||
@ApiResponses({
|
||||
@ApiResponse(responseCode = "200", description = "OK", content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.PostPaymentTypesResponse.class))) })
|
||||
public String createPaymentType(@Parameter(hidden = true) final String apiRequestBodyAsJson) {
|
||||
|
||||
final CommandWrapper commandRequest = new CommandWrapperBuilder().createPaymentType().withJson(apiRequestBodyAsJson).build();
|
||||
|
||||
final CommandProcessingResult result = this.commandWritePlatformService.logCommandSource(commandRequest);
|
||||
|
||||
return this.jsonSerializer.serialize(result);
|
||||
}
|
||||
|
||||
@PUT
|
||||
@Path("{paymentTypeId}")
|
||||
@Consumes({ MediaType.APPLICATION_JSON })
|
||||
@Produces({ MediaType.APPLICATION_JSON })
|
||||
@Operation(summary = "Update a Payment Type", description = "Updates a Payment Type")
|
||||
@RequestBody(required = true, content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.PutPaymentTypesPaymentTypeIdRequest.class)))
|
||||
@ApiResponses({
|
||||
@ApiResponse(responseCode = "200", description = "OK", content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.PutPaymentTypesPaymentTypeIdResponse.class))) })
|
||||
public String updatePaymentType(@PathParam("paymentTypeId") @Parameter(description = "paymentTypeId") final Long paymentTypeId,
|
||||
@Parameter(hidden = true) final String apiRequestBodyAsJson) {
|
||||
|
||||
final CommandWrapper commandRequest = new CommandWrapperBuilder().updatePaymentType(paymentTypeId).withJson(apiRequestBodyAsJson)
|
||||
.build();
|
||||
|
||||
final CommandProcessingResult result = this.commandWritePlatformService.logCommandSource(commandRequest);
|
||||
|
||||
return this.jsonSerializer.serialize(result);
|
||||
}
|
||||
|
||||
@DELETE
|
||||
@Path("{paymentTypeId}")
|
||||
@Consumes({ MediaType.APPLICATION_JSON })
|
||||
@Produces({ MediaType.APPLICATION_JSON })
|
||||
@Operation(summary = "Delete a Payment Type", description = "Deletes payment type")
|
||||
@ApiResponses({
|
||||
@ApiResponse(responseCode = "200", description = "OK", content = @Content(schema = @Schema(implementation = PaymentTypeApiResourceSwagger.DeletePaymentTypesPaymentTypeIdResponse.class))) })
|
||||
public String deleteCode(@PathParam("paymentTypeId") @Parameter(description = "paymentTypeId") final Long paymentTypeId) {
|
||||
|
||||
final CommandWrapper commandRequest = new CommandWrapperBuilder().deletePaymentType(paymentTypeId).build();
|
||||
|
||||
final CommandProcessingResult result = this.commandWritePlatformService.logCommandSource(commandRequest);
|
||||
|
||||
return this.jsonSerializer.serialize(result);
|
||||
}
|
||||
|
||||
}
|
||||
+136
@@ -0,0 +1,136 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.api;
|
||||
|
||||
import io.swagger.v3.oas.annotations.media.Schema;
|
||||
|
||||
/**
|
||||
* Created by Chirag Gupta on 01/01/18.
|
||||
*/
|
||||
public final class PaymentTypeApiResourceSwagger {
|
||||
|
||||
private PaymentTypeApiResourceSwagger() {}
|
||||
|
||||
@Schema(description = "GetPaymentTypesResponse")
|
||||
public static final class GetPaymentTypesResponse {
|
||||
|
||||
private GetPaymentTypesResponse() {}
|
||||
|
||||
@Schema(example = "24")
|
||||
public Long id;
|
||||
@Schema(example = "PTC")
|
||||
public String name;
|
||||
@Schema(example = "Cash")
|
||||
public String description;
|
||||
@Schema(example = "true")
|
||||
public Boolean isCashPayment;
|
||||
@Schema(example = "0")
|
||||
public Integer position;
|
||||
@Schema(example = "REPAYMENT_REFUND")
|
||||
public String codeName;
|
||||
@Schema(example = "false")
|
||||
public Boolean isSystemDefined;
|
||||
}
|
||||
|
||||
@Schema(description = "GetPaymentTypesPaymentTypeIdResponse")
|
||||
public static final class GetPaymentTypesPaymentTypeIdResponse {
|
||||
|
||||
private GetPaymentTypesPaymentTypeIdResponse() {}
|
||||
|
||||
@Schema(example = "13")
|
||||
public Long id;
|
||||
@Schema(example = "cash")
|
||||
public String name;
|
||||
@Schema(example = "cash Payment")
|
||||
public String description;
|
||||
@Schema(example = "true")
|
||||
public Boolean isCashPayment;
|
||||
@Schema(example = "1")
|
||||
public Integer position;
|
||||
@Schema(example = "REPAYMENT_REFUND")
|
||||
public String codeName;
|
||||
@Schema(example = "false")
|
||||
public Boolean isSystemDefined;
|
||||
}
|
||||
|
||||
@Schema(description = "PostPaymentTypesRequest")
|
||||
public static final class PostPaymentTypesRequest {
|
||||
|
||||
private PostPaymentTypesRequest() {}
|
||||
|
||||
@Schema(example = "cash")
|
||||
public String name;
|
||||
@Schema(example = "cash payment type")
|
||||
public String description;
|
||||
@Schema(example = "true")
|
||||
public Boolean isCashPayment;
|
||||
@Schema(example = "1")
|
||||
public Integer position;
|
||||
@Schema(example = "REPAYMENT_REFUND")
|
||||
public String codeName;
|
||||
@Schema(example = "false")
|
||||
public Boolean isSystemDefined;
|
||||
}
|
||||
|
||||
@Schema(description = "PostPaymentTypesResponse")
|
||||
public static final class PostPaymentTypesResponse {
|
||||
|
||||
private PostPaymentTypesResponse() {}
|
||||
|
||||
@Schema(example = "1")
|
||||
public Long resourceId;
|
||||
}
|
||||
|
||||
@Schema(description = "PutPaymentTypesPaymentTypeIdRequest")
|
||||
public static final class PutPaymentTypesPaymentTypeIdRequest {
|
||||
|
||||
private PutPaymentTypesPaymentTypeIdRequest() {}
|
||||
|
||||
@Schema(example = "mPay")
|
||||
public String name;
|
||||
@Schema(example = "not a cash payment type")
|
||||
public String description;
|
||||
@Schema(example = "false")
|
||||
public Boolean isCashPayment;
|
||||
@Schema(example = "3")
|
||||
public Integer position;
|
||||
@Schema(example = "REPAYMENT_REFUND")
|
||||
public String codeName;
|
||||
@Schema(example = "false")
|
||||
public Boolean isSystemDefined;
|
||||
}
|
||||
|
||||
@Schema(description = "PutPaymentTypesPaymentTypeIdResponse")
|
||||
public static final class PutPaymentTypesPaymentTypeIdResponse {
|
||||
|
||||
private PutPaymentTypesPaymentTypeIdResponse() {}
|
||||
|
||||
@Schema(example = "13")
|
||||
public Long resourceId;
|
||||
}
|
||||
|
||||
@Schema(description = "DeletePaymentTypesPaymentTypeIdResponse")
|
||||
public static final class DeletePaymentTypesPaymentTypeIdResponse {
|
||||
|
||||
private DeletePaymentTypesPaymentTypeIdResponse() {}
|
||||
|
||||
@Schema(example = "13")
|
||||
public Long resourceId;
|
||||
}
|
||||
}
|
||||
+176
@@ -0,0 +1,176 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.data;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.apache.fineract.infrastructure.core.data.ApiParameterError;
|
||||
import org.apache.fineract.infrastructure.core.data.DataValidatorBuilder;
|
||||
import org.apache.fineract.infrastructure.core.exception.InvalidJsonException;
|
||||
import org.apache.fineract.infrastructure.core.exception.PlatformApiDataValidationException;
|
||||
import org.apache.fineract.infrastructure.core.serialization.FromJsonHelper;
|
||||
import org.apache.fineract.portfolio.paymenttype.api.PaymentTypeApiResourceConstants;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
@Component
|
||||
public class PaymentTypeDataValidator {
|
||||
|
||||
private final FromJsonHelper fromApiJsonHelper;
|
||||
private static final Set<String> CREATE_PAYMENT_TYPE_REQUEST_DATA_PARAMETERS = new HashSet<>(
|
||||
Arrays.asList(PaymentTypeApiResourceConstants.NAME, PaymentTypeApiResourceConstants.DESCRIPTION,
|
||||
PaymentTypeApiResourceConstants.ISCASHPAYMENT, PaymentTypeApiResourceConstants.POSITION,
|
||||
PaymentTypeApiResourceConstants.CODE_NAME, PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED));
|
||||
|
||||
private static final Set<String> UPDATE_PAYMENT_TYPE_REQUEST_DATA_PARAMETERS = new HashSet<>(
|
||||
Arrays.asList(PaymentTypeApiResourceConstants.NAME, PaymentTypeApiResourceConstants.DESCRIPTION,
|
||||
PaymentTypeApiResourceConstants.ISCASHPAYMENT, PaymentTypeApiResourceConstants.POSITION,
|
||||
PaymentTypeApiResourceConstants.CODE_NAME, PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED));
|
||||
|
||||
@Autowired
|
||||
public PaymentTypeDataValidator(final FromJsonHelper fromApiJsonHelper) {
|
||||
this.fromApiJsonHelper = fromApiJsonHelper;
|
||||
}
|
||||
|
||||
public void validateForCreate(final String json) {
|
||||
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
}
|
||||
|
||||
final Type typeOfMap = new TypeToken<Map<String, Object>>() {}.getType();
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(typeOfMap, json, CREATE_PAYMENT_TYPE_REQUEST_DATA_PARAMETERS);
|
||||
final JsonElement element = this.fromApiJsonHelper.parse(json);
|
||||
|
||||
final List<ApiParameterError> dataValidationErrors = new ArrayList<>();
|
||||
|
||||
final DataValidatorBuilder baseDataValidator = new DataValidatorBuilder(dataValidationErrors)
|
||||
.resource(PaymentTypeApiResourceConstants.ENTITY_NAME);
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.NAME, element)) {
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.NAME, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.NAME).value(name).notBlank();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.DESCRIPTION, element)) {
|
||||
final String description = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.DESCRIPTION, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.DESCRIPTION).value(description).ignoreIfNull()
|
||||
.notExceedingLengthOf(500);
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.ISCASHPAYMENT, element)) {
|
||||
final Boolean isCashPayment = this.fromApiJsonHelper.extractBooleanNamed(PaymentTypeApiResourceConstants.ISCASHPAYMENT,
|
||||
element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.ISCASHPAYMENT).value(isCashPayment)
|
||||
.validateForBooleanValue();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.POSITION, element)) {
|
||||
final Long position = this.fromApiJsonHelper.extractLongNamed(PaymentTypeApiResourceConstants.POSITION, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.POSITION).value(position).ignoreIfNull()
|
||||
.integerZeroOrGreater();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.CODE_NAME, element)) {
|
||||
final String codeName = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.CODE_NAME, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.CODE_NAME).value(codeName).ignoreIfNull()
|
||||
.notExceedingLengthOf(100);
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED, element)) {
|
||||
final Boolean isSystemDefined = this.fromApiJsonHelper.extractBooleanNamed(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED,
|
||||
element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED).value(isSystemDefined)
|
||||
.validateForBooleanValue();
|
||||
}
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
|
||||
private void throwExceptionIfValidationWarningsExist(final List<ApiParameterError> dataValidationErrors) {
|
||||
if (!dataValidationErrors.isEmpty()) {
|
||||
//
|
||||
throw new PlatformApiDataValidationException(dataValidationErrors);
|
||||
}
|
||||
}
|
||||
|
||||
public void validateForUpdate(final String json) {
|
||||
if (StringUtils.isBlank(json)) {
|
||||
throw new InvalidJsonException();
|
||||
}
|
||||
|
||||
final Type typeOfMap = new TypeToken<Map<String, Object>>() {}.getType();
|
||||
this.fromApiJsonHelper.checkForUnsupportedParameters(typeOfMap, json, UPDATE_PAYMENT_TYPE_REQUEST_DATA_PARAMETERS);
|
||||
|
||||
final JsonElement element = this.fromApiJsonHelper.parse(json);
|
||||
|
||||
final List<ApiParameterError> dataValidationErrors = new ArrayList<>();
|
||||
|
||||
final DataValidatorBuilder baseDataValidator = new DataValidatorBuilder(dataValidationErrors)
|
||||
.resource(PaymentTypeApiResourceConstants.ENTITY_NAME);
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.NAME, element)) {
|
||||
final String name = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.NAME, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.NAME).value(name);
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.DESCRIPTION, element)) {
|
||||
final String description = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.DESCRIPTION, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.DESCRIPTION).value(description).ignoreIfNull()
|
||||
.notExceedingLengthOf(500);
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.ISCASHPAYMENT, element)) {
|
||||
final Boolean isCashPayment = this.fromApiJsonHelper.extractBooleanNamed(PaymentTypeApiResourceConstants.ISCASHPAYMENT,
|
||||
element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.ISCASHPAYMENT).value(isCashPayment)
|
||||
.validateForBooleanValue();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.POSITION, element)) {
|
||||
final Long position = this.fromApiJsonHelper.extractLongNamed(PaymentTypeApiResourceConstants.POSITION, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.POSITION).value(position).ignoreIfNull()
|
||||
.integerZeroOrGreater();
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.CODE_NAME, element)) {
|
||||
final String codeName = this.fromApiJsonHelper.extractStringNamed(PaymentTypeApiResourceConstants.CODE_NAME, element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.CODE_NAME).value(codeName).ignoreIfNull()
|
||||
.notExceedingLengthOf(100);
|
||||
}
|
||||
|
||||
if (this.fromApiJsonHelper.parameterExists(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED, element)) {
|
||||
final Boolean isSystemDefined = this.fromApiJsonHelper.extractBooleanNamed(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED,
|
||||
element);
|
||||
baseDataValidator.reset().parameter(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED).value(isSystemDefined)
|
||||
.validateForBooleanValue();
|
||||
}
|
||||
|
||||
throwExceptionIfValidationWarningsExist(dataValidationErrors);
|
||||
}
|
||||
|
||||
}
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.handler;
|
||||
|
||||
import org.apache.fineract.commands.annotation.CommandType;
|
||||
import org.apache.fineract.commands.handler.NewCommandSourceHandler;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeWriteService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
@Service
|
||||
@CommandType(entity = "PAYMENTTYPE", action = "CREATE")
|
||||
public class CreatePaymentTypeCommandHandler implements NewCommandSourceHandler {
|
||||
|
||||
private final PaymentTypeWriteService paymentTypeWriteService;
|
||||
|
||||
@Autowired
|
||||
public CreatePaymentTypeCommandHandler(final PaymentTypeWriteService paymentTypeWriteService) {
|
||||
this.paymentTypeWriteService = paymentTypeWriteService;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional
|
||||
public CommandProcessingResult processCommand(JsonCommand command) {
|
||||
return this.paymentTypeWriteService.createPaymentType(command);
|
||||
}
|
||||
}
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.handler;
|
||||
|
||||
import org.apache.fineract.commands.annotation.CommandType;
|
||||
import org.apache.fineract.commands.handler.NewCommandSourceHandler;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeWriteService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
@Service
|
||||
@CommandType(entity = "PAYMENTTYPE", action = "DELETE")
|
||||
public class DeletePaymentTypeCommandHandler implements NewCommandSourceHandler {
|
||||
|
||||
private final PaymentTypeWriteService paymentTypeWriteService;
|
||||
|
||||
@Autowired
|
||||
public DeletePaymentTypeCommandHandler(final PaymentTypeWriteService paymentTypeWriteService) {
|
||||
this.paymentTypeWriteService = paymentTypeWriteService;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional
|
||||
public CommandProcessingResult processCommand(JsonCommand command) {
|
||||
return this.paymentTypeWriteService.deletePaymentType(command.entityId());
|
||||
}
|
||||
}
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.handler;
|
||||
|
||||
import org.apache.fineract.commands.annotation.CommandType;
|
||||
import org.apache.fineract.commands.handler.NewCommandSourceHandler;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeWriteService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.transaction.annotation.Transactional;
|
||||
|
||||
@Service
|
||||
@CommandType(entity = "PAYMENTTYPE", action = "UPDATE")
|
||||
public class UpdatePaymentTypeCommandHandler implements NewCommandSourceHandler {
|
||||
|
||||
private final PaymentTypeWriteService paymentTypeWriteService;
|
||||
|
||||
@Autowired
|
||||
public UpdatePaymentTypeCommandHandler(final PaymentTypeWriteService paymentTypeWriteService) {
|
||||
this.paymentTypeWriteService = paymentTypeWriteService;
|
||||
}
|
||||
|
||||
@Override
|
||||
@Transactional
|
||||
public CommandProcessingResult processCommand(JsonCommand command) {
|
||||
return this.paymentTypeWriteService.updatePaymentType(command.entityId(), command);
|
||||
}
|
||||
}
|
||||
+34
@@ -0,0 +1,34 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.mapper;
|
||||
|
||||
import java.util.List;
|
||||
import org.apache.fineract.infrastructure.core.config.MapstructMapperConfig;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeData;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentType;
|
||||
import org.mapstruct.Mapper;
|
||||
|
||||
@Mapper(config = MapstructMapperConfig.class)
|
||||
public interface PaymentTypeMapper {
|
||||
|
||||
PaymentTypeData map(PaymentType source);
|
||||
|
||||
List<PaymentTypeData> map(List<PaymentType> sources);
|
||||
|
||||
}
|
||||
+32
@@ -0,0 +1,32 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.service;
|
||||
|
||||
import java.util.Collection;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeData;
|
||||
|
||||
public interface PaymentTypeReadPlatformService {
|
||||
|
||||
Collection<PaymentTypeData> retrieveAllPaymentTypes();
|
||||
|
||||
Collection<PaymentTypeData> retrieveAllPaymentTypesWithCode();
|
||||
|
||||
PaymentTypeData retrieveOne(Long paymentTypeId);
|
||||
|
||||
}
|
||||
+67
@@ -0,0 +1,67 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.service;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.security.service.PlatformSecurityContext;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeData;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentType;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.apache.fineract.portfolio.paymenttype.mapper.PaymentTypeMapper;
|
||||
import org.springframework.cache.annotation.Cacheable;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public class PaymentTypeReadPlatformServiceImpl implements PaymentTypeReadPlatformService {
|
||||
|
||||
private final PlatformSecurityContext context;
|
||||
private final PaymentTypeMapper paymentTypeMapper;
|
||||
private final PaymentTypeRepositoryWrapper paymentTypeRepository;
|
||||
|
||||
@Override
|
||||
@Cacheable(value = "payment_types", key = "T(org.apache.fineract.infrastructure.core.service.ThreadLocalContextUtil).getTenant().getTenantIdentifier().concat('payment_types')")
|
||||
public Collection<PaymentTypeData> retrieveAllPaymentTypes() {
|
||||
// TODO Auto-generated method stub
|
||||
this.context.authenticatedUser();
|
||||
|
||||
List<PaymentType> paymentType = this.paymentTypeRepository.findAll();
|
||||
return this.paymentTypeMapper.map(paymentType);
|
||||
}
|
||||
|
||||
@Override
|
||||
@Cacheable(value = "paymentTypesWithCode", key = "T(org.apache.fineract.infrastructure.core.service.ThreadLocalContextUtil).getTenant().getTenantIdentifier().concat('payment_types')")
|
||||
public Collection<PaymentTypeData> retrieveAllPaymentTypesWithCode() {
|
||||
// TODO Auto-generated method stub
|
||||
this.context.authenticatedUser();
|
||||
|
||||
List<PaymentType> paymentType = this.paymentTypeRepository.findAllWithCodeName();
|
||||
return this.paymentTypeMapper.map(paymentType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public PaymentTypeData retrieveOne(Long paymentTypeId) {
|
||||
// TODO Auto-generated method stub
|
||||
this.context.authenticatedUser();
|
||||
|
||||
final PaymentType paymentType = this.paymentTypeRepository.findOneWithNotFoundDetection(paymentTypeId);
|
||||
return this.paymentTypeMapper.map(paymentType);
|
||||
}
|
||||
|
||||
}
|
||||
+31
@@ -0,0 +1,31 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.service;
|
||||
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
|
||||
public interface PaymentTypeWriteService {
|
||||
|
||||
CommandProcessingResult createPaymentType(JsonCommand command);
|
||||
|
||||
CommandProcessingResult updatePaymentType(Long id, JsonCommand command);
|
||||
|
||||
CommandProcessingResult deletePaymentType(Long id);
|
||||
}
|
||||
+103
@@ -0,0 +1,103 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.service;
|
||||
|
||||
import java.util.Map;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import org.apache.fineract.infrastructure.core.api.JsonCommand;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResult;
|
||||
import org.apache.fineract.infrastructure.core.data.CommandProcessingResultBuilder;
|
||||
import org.apache.fineract.infrastructure.core.exception.ErrorHandler;
|
||||
import org.apache.fineract.infrastructure.core.exception.PlatformDataIntegrityException;
|
||||
import org.apache.fineract.portfolio.paymenttype.api.PaymentTypeApiResourceConstants;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeDataValidator;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentType;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepository;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.springframework.cache.annotation.CacheEvict;
|
||||
import org.springframework.dao.DataIntegrityViolationException;
|
||||
import org.springframework.orm.jpa.JpaSystemException;
|
||||
|
||||
@RequiredArgsConstructor
|
||||
public class PaymentTypeWriteServiceImpl implements PaymentTypeWriteService {
|
||||
|
||||
private final PaymentTypeRepository repository;
|
||||
private final PaymentTypeRepositoryWrapper repositoryWrapper;
|
||||
private final PaymentTypeDataValidator fromApiJsonDeserializer;
|
||||
|
||||
@Override
|
||||
@CacheEvict(value = "payment_types", key = "T(org.apache.fineract.infrastructure.core.service.ThreadLocalContextUtil).getTenant().getTenantIdentifier().concat('payment_types')")
|
||||
public CommandProcessingResult createPaymentType(JsonCommand command) {
|
||||
this.fromApiJsonDeserializer.validateForCreate(command.json());
|
||||
String name = command.stringValueOfParameterNamed(PaymentTypeApiResourceConstants.NAME);
|
||||
String description = command.stringValueOfParameterNamed(PaymentTypeApiResourceConstants.DESCRIPTION);
|
||||
Boolean isCashPayment = command.booleanObjectValueOfParameterNamed(PaymentTypeApiResourceConstants.ISCASHPAYMENT);
|
||||
Long position = command.longValueOfParameterNamed(PaymentTypeApiResourceConstants.POSITION);
|
||||
String codeName = command.stringValueOfParameterNamed(PaymentTypeApiResourceConstants.CODE_NAME);
|
||||
Boolean isSystemDefined = command.booleanObjectValueOfParameterNamed(PaymentTypeApiResourceConstants.IS_SYSTEM_DEFINED);
|
||||
if (isSystemDefined == null) {
|
||||
isSystemDefined = false;
|
||||
}
|
||||
|
||||
PaymentType newPaymentType = new PaymentType(name, description, isCashPayment, position, codeName, isSystemDefined);
|
||||
this.repository.saveAndFlush(newPaymentType);
|
||||
return new CommandProcessingResultBuilder().withCommandId(command.commandId()).withEntityId(newPaymentType.getId()).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
@CacheEvict(value = "payment_types", key = "T(org.apache.fineract.infrastructure.core.service.ThreadLocalContextUtil).getTenant().getTenantIdentifier().concat('payment_types')")
|
||||
public CommandProcessingResult updatePaymentType(Long paymentTypeId, JsonCommand command) {
|
||||
|
||||
this.fromApiJsonDeserializer.validateForUpdate(command.json());
|
||||
final PaymentType paymentType = this.repositoryWrapper.findOneWithNotFoundDetection(paymentTypeId);
|
||||
final Map<String, Object> changes = paymentType.update(command);
|
||||
|
||||
if (!changes.isEmpty()) {
|
||||
this.repository.save(paymentType);
|
||||
}
|
||||
|
||||
return new CommandProcessingResultBuilder().withCommandId(command.commandId()).withEntityId(command.entityId()).build();
|
||||
}
|
||||
|
||||
@Override
|
||||
@CacheEvict(value = "payment_types", key = "T(org.apache.fineract.infrastructure.core.service.ThreadLocalContextUtil).getTenant().getTenantIdentifier().concat('payment_types')")
|
||||
public CommandProcessingResult deletePaymentType(Long paymentTypeId) {
|
||||
final PaymentType paymentType = this.repositoryWrapper.findOneWithNotFoundDetection(paymentTypeId);
|
||||
try {
|
||||
this.repository.delete(paymentType);
|
||||
this.repository.flush();
|
||||
} catch (final JpaSystemException | DataIntegrityViolationException e) {
|
||||
final Throwable throwable = e.getMostSpecificCause();
|
||||
handleDataIntegrityIssues(throwable, e);
|
||||
}
|
||||
return new CommandProcessingResultBuilder().withEntityId(paymentType.getId()).build();
|
||||
}
|
||||
|
||||
private void handleDataIntegrityIssues(final Throwable realCause, final Exception dve) {
|
||||
if (realCause.getMessage().contains("acc_product_mapping")) {
|
||||
throw new PlatformDataIntegrityException("error.msg.payment.type.association.exist",
|
||||
"cannot.delete.payment.type.with.association");
|
||||
} else if (realCause.getMessage().contains("payment_type_id")) {
|
||||
throw new PlatformDataIntegrityException("error.msg.payment.type.association.exist",
|
||||
"cannot.delete.payment.type.with.association");
|
||||
}
|
||||
throw ErrorHandler.getMappable(dve, "error.msg.paymenttypes.unknown.data.integrity.issue",
|
||||
"Unknown data integrity issue with resource.");
|
||||
}
|
||||
}
|
||||
+50
@@ -0,0 +1,50 @@
|
||||
/**
|
||||
* Licensed to the Apache Software Foundation (ASF) under one
|
||||
* or more contributor license agreements. See the NOTICE file
|
||||
* distributed with this work for additional information
|
||||
* regarding copyright ownership. The ASF licenses this file
|
||||
* to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance
|
||||
* with the License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing,
|
||||
* software distributed under the License is distributed on an
|
||||
* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
|
||||
* KIND, either express or implied. See the License for the
|
||||
* specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*/
|
||||
package org.apache.fineract.portfolio.paymenttype.starter;
|
||||
|
||||
import org.apache.fineract.infrastructure.security.service.PlatformSecurityContext;
|
||||
import org.apache.fineract.portfolio.paymenttype.data.PaymentTypeDataValidator;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepository;
|
||||
import org.apache.fineract.portfolio.paymenttype.domain.PaymentTypeRepositoryWrapper;
|
||||
import org.apache.fineract.portfolio.paymenttype.mapper.PaymentTypeMapper;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeReadPlatformService;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeReadPlatformServiceImpl;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeWriteService;
|
||||
import org.apache.fineract.portfolio.paymenttype.service.PaymentTypeWriteServiceImpl;
|
||||
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
@Configuration
|
||||
public class PaymentTypeConfiguration {
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(PaymentTypeReadPlatformService.class)
|
||||
PaymentTypeReadPlatformService paymentTypeReadPlatformService(PlatformSecurityContext context, PaymentTypeMapper paymentTypeMapper,
|
||||
PaymentTypeRepositoryWrapper paymentTypeRepositoryWrapper) {
|
||||
return new PaymentTypeReadPlatformServiceImpl(context, paymentTypeMapper, paymentTypeRepositoryWrapper);
|
||||
}
|
||||
|
||||
@Bean
|
||||
@ConditionalOnMissingBean(PaymentTypeWriteService.class)
|
||||
PaymentTypeWriteService paymentTypeWriteService(PaymentTypeRepository repository, PaymentTypeRepositoryWrapper repositoryWrapper,
|
||||
PaymentTypeDataValidator fromApiJsonDeserializer) {
|
||||
return new PaymentTypeWriteServiceImpl(repository, repositoryWrapper, fromApiJsonDeserializer);
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user