This commit is contained in:
etreschenkov 2026-04-27 17:34:31 +03:00
parent 378e63e7d9
commit 5e8ba401cc
8 changed files with 144 additions and 1 deletions

View file

@ -21,6 +21,7 @@ import ru.spcex.clearing.backendapi.controller.request.cud.common.CommonDeleteAc
import ru.spcex.clearing.backendapi.controller.request.cud.order.OrderCompanyNewAction;
import ru.spcex.clearing.backendapi.controller.request.cud.order.OrderCompanyUpdateAction;
import ru.spcex.clearing.backendapi.controller.request.cud.order.OrderCurrencyUpdateAction;
import ru.spcex.clearing.backendapi.controller.request.cud.order.OrderCurrencyUpdateStatusAction;
import ru.spcex.clearing.backendapi.controller.request.cud.order.OrderOvernightTypeUpdateAction;
import ru.spcex.clearing.backendapi.controller.response.BasicSpcexResponse;
import ru.spcex.clearing.backendapi.controller.response.cud.CudResponse;
@ -66,6 +67,19 @@ public class OrderCurrencyController extends AbstractQueueController {
return processRequest(Consts.ORDER_CURRENCY_UPDATE, orderCurrencyUpdateAction);
}
@ApiOperation(value = "update order currency.")
@ApiResponses(value = {@ApiResponse(code = 200, message = "OK", response = CudResponse.class), @ApiResponse(code = 400, message = "Ошибка валидации", response = BasicSpcexResponse.class)})
@RequestMapping(value = "status/{id}", method = RequestMethod.PUT, consumes = MediaType.APPLICATION_JSON_VALUE)
@ResponseBody
public CudResponse updateStatus(
@ApiParam(value = "Идентификатор изменяемого объекта.", required = true, example = "1234")
@PathVariable("id") Long id,
@ApiParam(value = "Новые значения полей объекта.", required = true)
@RequestBody OrderCurrencyUpdateStatusAction orderCurrencyUpdateStatusAction) throws ExecutionException, InterruptedException {
orderCurrencyUpdateStatusAction.setId(id);
return processRequest(Consts.ORDER_CURRENCY_STATUS_UPDATE, orderCurrencyUpdateStatusAction);
}
@ApiOperation(value = "update overnight type for order currency.")
@ApiResponses(value = {@ApiResponse(code = 200, message = "OK", response = CudResponse.class), @ApiResponse(code = 400, message = "Ошибка валидации", response = BasicSpcexResponse.class)})
@RequestMapping(path = "/overnightType/{id}", method = RequestMethod.PUT, consumes = MediaType.APPLICATION_JSON_VALUE)

View file

@ -0,0 +1,47 @@
package ru.spcex.clearing.backendapi.controller.request.cud.order;
import com.fasterxml.jackson.annotation.JsonProperty;
import io.swagger.annotations.ApiModelProperty;
import ru.spcex.clearing.backendapi.domain.actions.IAction;
import ru.spcex.clearing.platform.messaging.domain.ActionType;
import ru.spcex.clearing.platform.messaging.domain.cud.order.OrderCurrencyUpdateRequest;
public class OrderCurrencyUpdateStatusAction implements IAction<OrderCurrencyUpdateRequest> {
@ApiModelProperty(value = "Идентификатор записи", example = "12")
@JsonProperty
private Long id;
@ApiModelProperty(value = "Статус заявки", example = "ACT")
@JsonProperty
private String status;
@Override
public OrderCurrencyUpdateRequest toRequest() {
OrderCurrencyUpdateRequest request = new OrderCurrencyUpdateRequest();
request.setId(id);
request.setStatus(status);
return request;
}
@ApiModelProperty(hidden = true)
@Override
public ActionType getActionType() {
return ActionType.UPDATE;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
public String getStatus() {
return status;
}
public void setStatus(String status) {
this.status = status;
}
}

View file

@ -2754,6 +2754,10 @@
<status type="12" name="Статус заявки" shortname="Статус" link="orderStatus"/>
<comment type="2" length="255" name="Комментарий" shortname="Комментарий"/>
</put>
<put name="Изменение заявки" class="ru.spcex.clearing.backendapi.controller.request.cud.order.OrderCurrencyUpdateStatusAction">
<id type="1" name="Идентификатор записи" shortname="ID" link="orderCurrency" linkCode="id" required="true"/>
<status type="12" name="Статус заявки" shortname="Статус" link="orderStatus"/>
</put>
<put name="Изменение типа сделки переноса" destination="order-currency/overnightType" class="ru.spcex.clearing.backendapi.controller.request.cud.order.OrderOvernightTypeUpdateAction">
<id type="1" name="Идентификатор записи" shortname="ID" link="orderCurrency" linkCode="id" required="true"/>
<overnightType type="12" name="Тип сделок переноса компании" shortname="Тип сделок переноса" required="true" link="overnightType"/>

View file

@ -1,5 +1,6 @@
package ru.spcex.clearing.dflt.management.config;
import java.util.Arrays;
import java.util.Optional;
import java.util.function.Function;
import org.springframework.beans.factory.annotation.Autowired;
@ -33,6 +34,7 @@ import ru.spcex.clearing.validation.common.rules.DictionaryPresentRule;
import ru.spcex.clearing.validation.common.rules.IdPresentRule;
import ru.spcex.clearing.validation.common.rules.SpecialIdPresentRule;
import ru.spcex.platform.enumeration.OrderAffil;
import ru.spcex.platform.enumeration.OrderStatus;
import ru.spcex.platform.imdg.api.Imdg;
import ru.spcex.platform.imdg.api.ImdgProvider;
import ru.spcex.platform.imdg.api.predicate.ImdgPredicateBuilder;
@ -44,6 +46,7 @@ import ru.spcex.platform.imdg.validation.LogPrefixId;
import ru.spcex.platform.imdg.validation.rule.PresentById;
import ru.spcex.platform.imdg.validation.rule.PresentByPredicate;
import ru.spcex.platform.utils.enumeration.EnumMessage;
import ru.spcex.platform.utils.enumeration.IEnumKey;
import ru.spcex.platform.utils.validation.IValidationRule;
import ru.spcex.platform.utils.validation.IValidator;
import ru.spcex.platform.utils.validation.ValidatorImpl;
@ -249,6 +252,55 @@ public class ValidationConfig {
};
}
@Bean("orderCurrencyUpdateValidator")
public Function<OrderCurrencyUpdateRequest, IValidator> orderCurrencyUpdateStatusValidator() {
return req -> {
ImdgValidationContext<OrderCurrencyUpdateRequest> ctx = new ImdgValidationContext<>();
ctx.setValidatedObject(req);
ctx.setLogPrefix(LogPrefixId.INSTANCE);
ctx.addImdg(IMDGDistributedNames.Map_OrderStatusDictionary, orderStatusDictionaryImdg);
var orderCurrencyPresentById = PresentByPredicate
.builder(byId(orderCurrencyImdg.predicateBuilder(), req))
.mapName(IMDGDistributedNames.Map_OrderCurrency)
.errorProvider(r -> recordNotFound(r.getId()))
.store(OrderCurrencyValidationStored.OrderCurrency)
.build();
var status = new IValidationRule<ImdgValidationContext<OrderCurrencyUpdateRequest>>() {
@Override
public Optional<EnumMessage> validate(ImdgValidationContext<OrderCurrencyUpdateRequest> ctx) {
OrderCurrencyUpdateRequest validatedObject = ctx.getValidatedObject();
OrderCurrency orderCurrency = ctx.getStoredObject(OrderCurrencyValidationStored.OrderCurrency);
OrderStatus orderStatusReq = IEnumKey.getEnumByKey(OrderStatus.class, validatedObject.getStatus());
OrderStatus orderStatusExist = IEnumKey.getEnumByKey(OrderStatus.class, orderCurrency.getStatus());
if (!Arrays.asList(OrderStatus.CREATED, OrderStatus.HOLD).contains(orderStatusReq)) {
return of(DefaultManagementErrors.IncorrectFieldValue, "status=");
}
if (orderStatusReq == OrderStatus.CREATED && orderStatusExist == OrderStatus.HOLD) {
return of(DefaultManagementErrors.IncorrectFieldValue, "status=");
}
if (orderStatusReq == OrderStatus.HOLD && orderStatusExist == OrderStatus.CREATED) {
return of(DefaultManagementErrors.IncorrectFieldValue, "status=");
}
return empty();
}
};
return new ValidatorImpl<>(ctx,
orderCurrencyPresentById,
DictionaryPresentRule.instance(
"status",
OrderCurrencyUpdateRequest::getStatus,
IMDGDistributedNames.Map_OrderStatusDictionary,
OrderStatusDictionary.class,
DefaultManagementErrors.RequiredFieldIsEmpty,
DefaultManagementErrors.DictionaryNotFound,
true),
status
);
};
}
private EnumMessage dictNotFound(String dictName, String code) {
return new EnumMessage(DefaultManagementErrors.DictionaryNotFound, dictName, code);
}

View file

@ -12,6 +12,7 @@ public enum DefaultManagementErrors implements IErrorEnumId {
RecordAlreadyPresent(11002L),
OnlyBalancingOrdersAllowed(11003L),
OnlyBalancingOrdersAllowedForChanging(11004L),
IncorrectFieldValue(11005L),
;
private final Long id;

View file

@ -106,6 +106,9 @@ public class OrderCurrencyListener extends QueueConsumer implements Initializing
callback(OrderCurrencyUpdateRequest.class)
.setFunction(this::orderCurrencyUpdate)
.forDestination(Consts.ORDER_CURRENCY_UPDATE, callbacks::put);
callback(OrderCurrencyUpdateRequest.class)
.setFunction(this::orderCurrencyUpdateStatus)
.forDestination(Consts.ORDER_CURRENCY_STATUS_UPDATE, callbacks::put);
callback(OrderCurrencyUpdateRequest.class)
.setFunction(this::updateOvernightType)
.forDestination(Consts.ORDER_OVERNIGHT_TYPE_UPDATE, callbacks::put);
@ -148,6 +151,27 @@ public class OrderCurrencyListener extends QueueConsumer implements Initializing
return null;
}
private RequestInfoUpdate orderCurrencyUpdateStatus(BaseRequest<OrderCurrencyUpdateRequest> req) {
OrderCurrencyUpdateRequest payload = req.getRequestPayload();
IValidator validator = orderCurrencyUpdateValidator.apply(payload);
Optional<EnumMessage> error = validator.tillFirstError();
if (error.isPresent()) {
return new RequestInfoUpdate(req.getId(), Status.Error, msgResolver.resolve(error.get()));
}
OrderCurrency order = validator.getStored(OrderCurrencyValidationStored.OrderCurrency);
if (payload.getSecurityId() != null) {
order.setSecurityId(payload.getSecurityId());
}
order.setPrice(payload.getPrice());
order.setQuantityLot(BigDecimal.valueOf(payload.getQuantityLot()));
order.setSide(payload.getSide());
order.setStatus(payload.getStatus());
order.setComment(payload.getComment());
log.info("updating OrderCurrency[{}]", order.getId());
orderCurrencyImdg.update(order);
return null;
}
private RequestInfoUpdate updateOvernightType(BaseRequest<OrderCurrencyUpdateRequest> req) {
OrderCurrencyUpdateRequest payload = req.getRequestPayload();
IValidator validator = overnightTypeUpdateValidator.apply(payload);

View file

@ -4,7 +4,7 @@ import ru.spcex.platform.utils.enumeration.IEnumKey;
public enum OrderStatus implements IEnumKey {
NEW("NEW"), PTFL("PTFL"), FILL("FILL"), CNCL("CNCL"), REPL("REPL"), REJECTED("RJCT"),
CREATED("CRET");
CREATED("CRET"), HOLD("HOLD");
private final String key;

View file

@ -145,6 +145,7 @@ public interface Consts {
String OVERNIGHT_SETTINGS_UPDATE = "overnight-settings-update";
String ORDER_CURRENCY_UPDATE = "order-currency-update";
String ORDER_CURRENCY_STATUS_UPDATE = "order-currency-status-update";
String ORDER_OVERNIGHT_TYPE_UPDATE = "order-overnight-type-update";
String ORDER_CURRENCY_COMPANY_NEW = "order-currency-company-new";
String ORDER_CURRENCY_COMPANY_UPDATE = "order-currency-company-update";