This commit is contained in:
akulikov 2023-05-28 19:28:06 +03:00
parent 7a8c5d704e
commit a5bd6dd1cf
15 changed files with 135 additions and 60 deletions

View file

@ -22,7 +22,7 @@ public class ProcessorConfiguration {
public Processor<FondListingsRequestParam> fondListingsRequestProcessor(ImdgProvider imdgProvider, KafkaSender kafkaSender) {
Processor<FondListingsRequestParam> processor = new Processor<>();
List<Stage<FondListingsRequestParam>> pipeline = new ArrayList<>();
pipeline.add(new PrepareSecurities());
pipeline.add(new PrepareIncomeSecurities());
pipeline.add(new PrepareIssuerCompanies());
pipeline.add(new ValidateIncomeSecurities());
pipeline.add(new ValidateIssuerCompanies());

View file

@ -6,33 +6,36 @@ import io.swagger.annotations.ApiResponses;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.*;
import ru.spcex.clearing.gatewayapi.exception.GatewayException;
import ru.spcex.clearing.gatewayapi.logic.ProcessResult;
import ru.spcex.clearing.gatewayapi.logic.Processor;
import ru.spcex.clearing.gatewayapi.logic.companies.CompaniesRequestParam;
import ru.spcex.clearing.gatewayapi.logic.listings_fond.FondListingsRequestParam;
import ru.spcex.clearing.gatewayapi.logic.listings_mm.MMListingsRequestParam;
import ru.spcex.clearing.gatewayapi.request.BaseRequest;
import ru.spcex.clearing.gatewayapi.request.CommonRequest;
import ru.spcex.clearing.gatewayapi.request.CompaniesRequest;
import ru.spcex.clearing.gatewayapi.request.FondListingsRequest;
import ru.spcex.clearing.gatewayapi.request.MMListingsRequest;
import ru.spcex.clearing.gatewayapi.response.CommonResponse;
import ru.spcex.platform.utils.enumeration.EnumMessage;
import ru.spcex.platform.utils.enumeration.IMessageResolver;
@Controller
@RequestMapping("/")
public class GatewayController {
private final Logger log = LoggerFactory.getLogger(getClass());
private final IMessageResolver messageResolver;
private final Processor<FondListingsRequestParam> fondListingsRequestProcessor;
private final Processor<MMListingsRequestParam> mmListingsRequestProcessor;
private final Processor<CompaniesRequestParam> companiesRequestProcessor;
public GatewayController(
IMessageResolver messageResolver,
@Qualifier("fondListingsRequestProcessor")
Processor<FondListingsRequestParam> fondListingsRequestProcessor,
@Qualifier("mmListingsRequestProcessor")
@ -40,13 +43,13 @@ public class GatewayController {
@Qualifier("companiesRequestProcessor")
Processor<CompaniesRequestParam> companiesRequestProcessor
) {
this.messageResolver = messageResolver;
this.fondListingsRequestProcessor = fondListingsRequestProcessor;
this.mmListingsRequestProcessor = mmListingsRequestProcessor;
this.companiesRequestProcessor = companiesRequestProcessor;
}
@ApiOperation(value = "Экспорт ценных бумаг в Клиринговую систему")
@ApiResponses(value = {
@ApiResponse(code = 200, message = "OK", response = CommonResponse.class),
@ -60,14 +63,13 @@ public class GatewayController {
)
@ResponseBody
public CommonResponse listingsFond(@RequestBody FondListingsRequest request) {
CommonResponse commonResponse = createResponse(request);
FondListingsRequestParam requestParam = new FondListingsRequestParam(request);
ProcessResult processResult = fondListingsRequestProcessor.process(requestParam);
return commonResponse;
if (processResult.getError() != null) throw new GatewayException(request, processResult.getError());
return createResponse(request, true);
}
@ApiOperation(value = "Экспорт спецификаций биржевых инструментов в Клиринговую систему")
@ApiResponses(value = {
@ApiResponse(code = 200, message = "OK", response = CommonResponse.class),
@ -81,14 +83,13 @@ public class GatewayController {
)
@ResponseBody
public CommonResponse listingsMM(@RequestBody MMListingsRequest request) {
CommonResponse commonResponse = createResponse(request);
MMListingsRequestParam requestParam = new MMListingsRequestParam(request);
ProcessResult processResult = mmListingsRequestProcessor.process(requestParam);
return commonResponse;
if (processResult.getError() != null) throw new GatewayException(request, processResult.getError());
return createResponse(request, true);
}
@ApiOperation(value = "Экспорт участников в клиринговую систему")
@ApiResponses(value = {
@ApiResponse(code = 200, message = "OK", response = CommonResponse.class),
@ -102,22 +103,32 @@ public class GatewayController {
)
@ResponseBody
public CommonResponse companies(@RequestBody CompaniesRequest request) {
CommonResponse commonResponse = createResponse(request);
CompaniesRequestParam requestParam = new CompaniesRequestParam(request);
ProcessResult processResult = companiesRequestProcessor.process(requestParam);
return commonResponse;
if (processResult.getError() != null) throw new GatewayException(request, processResult.getError());
return createResponse(request, true);
}
public CommonResponse errorResponse() {
return null;
@ResponseStatus(value = HttpStatus.BAD_REQUEST)
@ResponseBody
@ExceptionHandler(GatewayException.class)
public CommonResponse errorResponse(GatewayException exception) {
CommonResponse errorResponse = createResponse(exception.getIncomeRequest(), false);
errorResponse.setCode(exception.getError().getId());
errorResponse.setMessage(messageResolver.resolve(new EnumMessage(exception.getError(), exception.getErrorArgs())));
return errorResponse;
}
private CommonResponse createResponse(BaseRequest request) {
private CommonResponse createResponse(CommonRequest request, boolean success) {
CommonResponse commonResponse = new CommonResponse();
commonResponse.setId(request.getId());
commonResponse.setType(request.getType());
commonResponse.setDatetime(request.getDatetime());
commonResponse.setSection(request.getSection());
if (success) {
commonResponse.setCode(0L);
commonResponse.setMessage("success");
}
return commonResponse;
}

View file

@ -3,6 +3,7 @@ package ru.spcex.clearing.gatewayapi.errors;
import ru.spcex.platform.utils.enumeration.IErrorEnumId;
public enum GatewayError implements IErrorEnumId {
InternalError(6000L),
UserVerifyDenial(6443L),
CompanyNotFound(6001L),
SecurityNotFound(6002L),

View file

@ -1,5 +1,29 @@
package ru.spcex.clearing.gatewayapi.exception;
public class GatewayException extends RuntimeException {
import ru.spcex.clearing.gatewayapi.errors.GatewayError;
import ru.spcex.clearing.gatewayapi.request.CommonRequest;
public class GatewayException extends RuntimeException {
private final CommonRequest incomeRequest;
private final Object[] errorArgs;
private final GatewayError error;
public GatewayException(CommonRequest incomeRequest, GatewayError error, Object ... args) {
this.error = error;
this.incomeRequest = incomeRequest;
this.errorArgs = args;
}
public CommonRequest getIncomeRequest() {
return incomeRequest;
}
public GatewayError getError() {
return error;
}
public Object[] getErrorArgs() {
return errorArgs;
}
}

View file

@ -4,6 +4,15 @@ import ru.spcex.clearing.gatewayapi.errors.GatewayError;
public class ProcessResult {
private GatewayError error = null;
private Object[] errorArgs;
public ProcessResult() {
}
public ProcessResult(GatewayError error, Object ... errorArgs) {
this.error = error;
}
public GatewayError getError() {
return error;

View file

@ -1,16 +1,26 @@
package ru.spcex.clearing.gatewayapi.logic;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.spcex.clearing.gatewayapi.errors.GatewayError;
import java.util.List;
public class Processor<T> {
private final Logger log = LoggerFactory.getLogger(getClass());
private List<Stage<T>> pipeline;
public ProcessResult process(T param) {
for (Stage<T> stage : pipeline) {
ProcessResult processResult = stage.process(param);
if (processResult != null) return processResult;
try {
for (Stage<T> stage : pipeline) {
ProcessResult processResult = stage.process(param);
if (processResult != null) return processResult;
}
} catch (RuntimeException e) {
log.error("", e);
return new ProcessResult(GatewayError.InternalError);
}
return null;
return new ProcessResult();
}
public List<Stage<T>> getPipeline() {

View file

@ -2,6 +2,7 @@ package ru.spcex.clearing.gatewayapi.logic.listings_fond;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.spcex.clearing.gatewayapi.errors.GatewayError;
import ru.spcex.clearing.gatewayapi.logic.ProcessResult;
import ru.spcex.clearing.gatewayapi.logic.Stage;
import ru.spcex.clearing.gatewayapi.request.objects.*;
@ -12,7 +13,7 @@ import java.util.Map;
import java.util.UUID;
import java.util.stream.Collectors;
public class PrepareSecurities extends Stage<FondListingsRequestParam> {
public class PrepareIncomeSecurities extends Stage<FondListingsRequestParam> {
private final Logger log = LoggerFactory.getLogger(getClass());
@Override
@ -72,7 +73,9 @@ public class PrepareSecurities extends Stage<FondListingsRequestParam> {
.filter(incomeSecurity -> !incomeSecurity.isInvalidData())
.collect(Collectors.toList());
// todo check list is empty
if (filteredIncomeSecurities.isEmpty()) {
return new ProcessResult(GatewayError.SecurityNotFound);
}
param.setSecurities(filteredIncomeSecurities);

View file

@ -93,8 +93,6 @@ public class PrepareIssuerCompanies extends Stage<FondListingsRequestParam> {
.filter(issuerCompany -> !issuerCompany.isInvalidData())
.collect(Collectors.toList());
// todo check list is empty
param.setIssuerCompanyList(filteredIssuerCompany);
return null;
}

View file

@ -3,6 +3,7 @@ package ru.spcex.clearing.gatewayapi.logic.listings_fond;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.spcex.clearing.gatewayapi.errors.GatewayError;
import ru.spcex.clearing.gatewayapi.logic.ProcessResult;
import ru.spcex.clearing.gatewayapi.logic.Stage;
import ru.spcex.clearing.gatewayapi.request.objects.CouponSchedule;
@ -160,7 +161,9 @@ public class ValidateIncomeSecurities extends Stage<FondListingsRequestParam> {
.filter(incomeSecurity -> !incomeSecurity.isInvalidData())
.collect(Collectors.toList());
// todo check list is empty
if (filteredIncomeSecurities.isEmpty()) {
return new ProcessResult(GatewayError.SecurityNotFound);
}
param.setSecurities(filteredIncomeSecurities);

View file

@ -2,6 +2,7 @@ package ru.spcex.clearing.gatewayapi.logic.listings_mm;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import ru.spcex.clearing.gatewayapi.errors.GatewayError;
import ru.spcex.clearing.gatewayapi.logic.ProcessResult;
import ru.spcex.clearing.gatewayapi.logic.Stage;
import ru.spcex.clearing.gatewayapi.request.objects.DirAuctionBiddingType;
@ -97,7 +98,9 @@ public class PrepareExchangeInstruments extends Stage<MMListingsRequestParam> {
.filter(exchangeInstrument -> !exchangeInstrument.isInvalidData())
.collect(Collectors.toList());
// todo check list is empty
if (filteredExchangeInstrument.isEmpty()) {
return new ProcessResult(GatewayError.SecurityNotFound);
}
param.setExchangeInstrumentsList(filteredExchangeInstrument);
return null;

View file

@ -8,7 +8,7 @@ import ru.spcex.clearing.gatewayapi.config.deserializers.InstantDeserializer;
import java.time.Instant;
import java.util.UUID;
public class BaseRequest {
public class CommonRequest {
@JsonProperty("id")
@ApiModelProperty(

View file

@ -4,36 +4,37 @@ import com.fasterxml.jackson.annotation.JsonProperty;
import io.swagger.annotations.ApiModelProperty;
import ru.spcex.clearing.gatewayapi.request.objects.*;
import java.util.ArrayList;
import java.util.List;
public class CompaniesRequest extends BaseRequest {
public class CompaniesRequest extends CommonRequest {
@JsonProperty("company")
@ApiModelProperty(value = "Список компаний")
private List<MemberCompany> companyList;
private List<MemberCompany> companyList = new ArrayList<>();
@JsonProperty("company_info")
@ApiModelProperty(value = "Список профилей участников")
private List<MemberCompanyInfo> companyInfoList;
private List<MemberCompanyInfo> companyInfoList = new ArrayList<>();
@JsonProperty("company_clearing_category")
@ApiModelProperty(value = "Список категорий участников клиринга")
private List<MemberCompanyClearingCategory> companyClearingCategoryList;
private List<MemberCompanyClearingCategory> companyClearingCategoryList = new ArrayList<>();
@JsonProperty("company_symbols")
@ApiModelProperty(value = "Список реквизитов участников")
private List<MemberCompanySymbols> memberCompanySymbolsList;
private List<MemberCompanySymbols> memberCompanySymbolsList = new ArrayList<>();
@JsonProperty("contact")
@ApiModelProperty(value = "Список контактов участников")
private List<MemberContact> contactList;
private List<MemberContact> contactList = new ArrayList<>();
@JsonProperty("profile_document")
@ApiModelProperty(value = "Список документов участников")
private List<MemberProfileDocument> memberProfileDocumentList;
private List<MemberProfileDocument> memberProfileDocumentList = new ArrayList<>();
@JsonProperty("client")
@ApiModelProperty(value = "Список клиентов участников")
private List<MemberClient> memberClientList;
private List<MemberClient> memberClientList = new ArrayList<>();
public List<MemberCompany> getCompanyList() {

View file

@ -4,44 +4,45 @@ import com.fasterxml.jackson.annotation.JsonProperty;
import io.swagger.annotations.ApiModelProperty;
import ru.spcex.clearing.gatewayapi.request.objects.*;
import java.util.ArrayList;
import java.util.List;
public class FondListingsRequest extends BaseRequest {
public class FondListingsRequest extends CommonRequest {
@JsonProperty("security")
@ApiModelProperty(value = "Список инструментов")
private List<FondSecurity> securities;
private List<FondSecurity> securities = new ArrayList<>();
@JsonProperty("coupon_schedule")
@ApiModelProperty(value = "Список coupon_schedule")
private List<CouponSchedule> couponSchedules;
private List<CouponSchedule> couponSchedules = new ArrayList<>();
@JsonProperty("currency")
@ApiModelProperty(value = "Список валют")
private List<Currency> currencies;
private List<Currency> currencies = new ArrayList<>();
@JsonProperty("listing")
@ApiModelProperty(value = "Список режимов торгов")
private List<IncomeListing> listingList;
private List<IncomeListing> listingList = new ArrayList<>();
@JsonProperty("nominal")
@ApiModelProperty(value = "Список nominal")
private List<Nominal> nominalList;
private List<Nominal> nominalList = new ArrayList<>();
@JsonProperty("company")
@ApiModelProperty(value = "Список компаний эмитентов")
private List<IssuerCompany> issuerCompanyList;
private List<IssuerCompany> issuerCompanyList = new ArrayList<>();
@JsonProperty("company_info")
@ApiModelProperty(value = "Список профилей компаний эмитентов")
private List<IssuerCompanyInfo> issuerCompanyInfoList;
private List<IssuerCompanyInfo> issuerCompanyInfoList = new ArrayList<>();
@JsonProperty("company_symbols")
@ApiModelProperty(value = "Список реквизитов компаний эмитентов")
private List<IssuerCompanySymbols> issuerCompanySymbolsList;
private List<IssuerCompanySymbols> issuerCompanySymbolsList = new ArrayList<>();
@JsonProperty("contact")
@ApiModelProperty(value = "Список контактов компаний эмитентов")
private List<IssuerContact> issuerContactList;
private List<IssuerContact> issuerContactList = new ArrayList<>();
public List<FondSecurity> getSecurities() {
return securities;

View file

@ -4,28 +4,29 @@ import com.fasterxml.jackson.annotation.JsonProperty;
import io.swagger.annotations.ApiModelProperty;
import ru.spcex.clearing.gatewayapi.request.objects.*;
import java.util.ArrayList;
import java.util.List;
public class MMListingsRequest extends BaseRequest {
public class MMListingsRequest extends CommonRequest {
@JsonProperty("exchange_instrument")
@ApiModelProperty(value = "Список инструментов")
private List<ExchangeInstrument> exchangeInstrumentList;
private List<ExchangeInstrument> exchangeInstrumentList = new ArrayList<>();
@JsonProperty("dir_auction_bidding_type")
@ApiModelProperty(value = "Справочник «Тип аукциона или торгов»")
private List<DirAuctionBiddingType> dirAuctionBiddingTypeList;
private List<DirAuctionBiddingType> dirAuctionBiddingTypeList = new ArrayList<>();
@JsonProperty("dir_currency_code")
@ApiModelProperty(value = "Справочник «Коды валют»")
private List<DirCurrencyCode> dirCurrencyCodeList;
private List<DirCurrencyCode> dirCurrencyCodeList = new ArrayList<>();
@JsonProperty("trading_mode")
@ApiModelProperty(value = "Список режимов торгов Спецификации биржевого инструмента")
private List<TradingMode> tradingModeList;
private List<TradingMode> tradingModeList = new ArrayList<>();
@JsonProperty("dir_trading_mode_mkr")
@ApiModelProperty(value = "Справочник «Режимы торгов МКР»")
private List<DirTradingModeMkr> dirTradingModeMkrList;
private List<DirTradingModeMkr> dirTradingModeMkrList = new ArrayList<>();
public List<ExchangeInstrument> getExchangeInstrumentList() {
return exchangeInstrumentList;

View file

@ -11,10 +11,6 @@ import java.util.UUID;
@ApiModel(description = "Базовый формат ответа")
public class CommonResponse {
@JsonProperty("code")
@ApiModelProperty(value = "Код ответа", example = "200")
private Integer code;
@JsonProperty("id")
@ApiModelProperty(
value = "Значение соответствует полученному из запроса",
@ -43,6 +39,12 @@ public class CommonResponse {
)
private String section;
@JsonProperty("code")
private Long code;
@JsonProperty("message")
private String message;
public UUID getId() {
return id;
}
@ -75,11 +77,19 @@ public class CommonResponse {
this.section = section;
}
public Integer getCode() {
public Long getCode() {
return code;
}
public void setCode(Integer code) {
public void setCode(Long code) {
this.code = code;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
}