Skip to content

Commit

Permalink
MODTLR-10 Basic implementation and tests
Browse files Browse the repository at this point in the history
  • Loading branch information
OleksandrVidinieiev committed Jan 24, 2024
1 parent d0cb1c0 commit 2805baa
Show file tree
Hide file tree
Showing 20 changed files with 745 additions and 25 deletions.
4 changes: 3 additions & 1 deletion descriptors/ModuleDescriptor-template.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,9 @@
"methods": ["POST"],
"pathPattern": "/tlr/ecs-tlr",
"permissionsRequired": ["tlr.ecs-tlr.post"],
"modulePermissions": []
"modulePermissions": [
"circulation.requests.item.post"
]
}
]
},
Expand Down
5 changes: 5 additions & 0 deletions pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -105,6 +105,11 @@
<scope>provided</scope>
</dependency>

<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webflux</artifactId>
</dependency>

<!-- Test dependencies -->
<dependency>
<groupId>org.springframework.boot</groupId>
Expand Down
13 changes: 13 additions & 0 deletions src/main/java/org/folio/client/CirculationClient.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package org.folio.client;

import org.folio.domain.dto.Request;
import org.folio.spring.config.FeignClientConfiguration;
import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.web.bind.annotation.PostMapping;

@FeignClient(name = "circulation", url = "${folio.okapi-url}", configuration = FeignClientConfiguration.class)
public interface CirculationClient {

@PostMapping("/circulation/requests")
Request createTitleLevelRequest(Request request);
}
2 changes: 1 addition & 1 deletion src/main/java/org/folio/controller/EcsTlrController.java
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,6 @@ public ResponseEntity<EcsTlr> getEcsTlrById(UUID requestId) {
public ResponseEntity<EcsTlr> postEcsTlr(EcsTlr ecsTlr) {
log.debug("postEcsTlr:: parameters ecsTlr: {}", ecsTlr);

return ResponseEntity.status(CREATED).body(ecsTlrService.post(ecsTlr));
return ResponseEntity.status(CREATED).body(ecsTlrService.create(ecsTlr));
}
}
15 changes: 9 additions & 6 deletions src/main/java/org/folio/domain/mapper/EcsTlrMapper.java
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package org.folio.domain.mapper;

import org.folio.domain.dto.EcsTlr;
import org.folio.domain.dto.Request;
import org.folio.domain.entity.EcsTlrEntity;
import org.mapstruct.Mapper;
import org.mapstruct.Mapping;
Expand Down Expand Up @@ -36,17 +37,19 @@ default EcsTlr.FulfillmentPreferenceEnum mapFulfillmentPreference(String fulfill
}

@Named("RequestTypeToString")
default String mapRequestTypeToString(EcsTlr.RequestTypeEnum requestTypeEnum) {
return requestTypeEnum != null ? requestTypeEnum.getValue() : null;
default String mapRequestType(EcsTlr.RequestTypeEnum requestType) {
return requestType != null ? requestType.getValue() : null;
}

@Named("RequestLevelToString")
default String mapRequestLevelToString(EcsTlr.RequestLevelEnum requestLevelEnum) {
return requestLevelEnum != null ? requestLevelEnum.getValue() : null;
default String mapRequestLevel(EcsTlr.RequestLevelEnum requestLevel) {
return requestLevel != null ? requestLevel.getValue() : null;
}

@Named("FulfillmentPreferenceToString")
default String mapFulfillmentPreferenceToString(EcsTlr.FulfillmentPreferenceEnum fulfillmentPreferenceEnum) {
return fulfillmentPreferenceEnum != null ? fulfillmentPreferenceEnum.getValue() : null;
default String mapFulfillmentPreference(EcsTlr.FulfillmentPreferenceEnum fulfillmentPreference) {
return fulfillmentPreference != null ? fulfillmentPreference.getValue() : null;
}

Request mapDtoToRequest(EcsTlr ecsTlr);
}
2 changes: 1 addition & 1 deletion src/main/java/org/folio/service/EcsTlrService.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,5 @@

public interface EcsTlrService {
Optional<EcsTlr> get(UUID requestId);
EcsTlr post(EcsTlr ecsTlr);
EcsTlr create(EcsTlr ecsTlr);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package org.folio.service;

import java.util.concurrent.Callable;

public interface TenantScopedExecutionService {

<T> T execute(String tenantId, Callable<T> action);
}
13 changes: 11 additions & 2 deletions src/main/java/org/folio/service/impl/EcsTlrServiceImpl.java
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,12 @@
import java.util.Optional;
import java.util.UUID;

import org.folio.client.CirculationClient;
import org.folio.domain.dto.EcsTlr;
import org.folio.domain.dto.Request;
import org.folio.domain.mapper.EcsTlrMapper;
import org.folio.repository.EcsTlrRepository;
import org.folio.service.TenantScopedExecutionService;
import org.folio.service.EcsTlrService;
import org.springframework.stereotype.Service;

Expand All @@ -19,6 +22,8 @@ public class EcsTlrServiceImpl implements EcsTlrService {

private final EcsTlrRepository ecsTlrRepository;
private final EcsTlrMapper requestsMapper;
private final CirculationClient circulationClient;
private final TenantScopedExecutionService tenantScopedExecutionService;

@Override
public Optional<EcsTlr> get(UUID id) {
Expand All @@ -29,8 +34,12 @@ public Optional<EcsTlr> get(UUID id) {
}

@Override
public EcsTlr post(EcsTlr ecsTlr) {
log.debug("post:: parameters ecsTlr: {}", () -> ecsTlr);
public EcsTlr create(EcsTlr ecsTlr) {
log.debug("create:: parameters ecsTlr: {}", () -> ecsTlr);
Request mappedRequest = requestsMapper.mapDtoToRequest(ecsTlr);
Request cretedRequest = tenantScopedExecutionService.execute("dummy-tenant", // TODO: replace with real tenantId
() -> circulationClient.createTitleLevelRequest(mappedRequest));
log.info("create:: title-level request created: {}", cretedRequest.getId());

return requestsMapper.mapEntityToDto(ecsTlrRepository.save(
requestsMapper.mapDtoToEntity(ecsTlr)));
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
package org.folio.service.impl;

import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.concurrent.Callable;

import org.folio.service.TenantScopedExecutionService;
import org.folio.spring.FolioExecutionContext;
import org.folio.spring.FolioModuleMetadata;
import org.folio.spring.integration.XOkapiHeaders;
import org.folio.spring.scope.FolioExecutionContextSetter;
import org.springframework.stereotype.Service;

import lombok.RequiredArgsConstructor;
import lombok.extern.log4j.Log4j2;

@Service
@RequiredArgsConstructor
@Log4j2
public class TenantScopedExecutionServiceImpl implements TenantScopedExecutionService {

private final FolioModuleMetadata moduleMetadata;
private final FolioExecutionContext executionContext;

@Override
public <T> T execute(String tenantId, Callable<T> action) {
log.info("execute:: tenantId={}", tenantId);
Map<String, Collection<String>> headers = executionContext.getAllHeaders();
headers.put(XOkapiHeaders.TENANT, List.of(tenantId));

try (var x = new FolioExecutionContextSetter(moduleMetadata, headers)) {
return action.call();
} catch (Exception e) {
log.error("execute:: tenantId={}", tenantId, e);
throw new RuntimeException(e);
}
}
}
4 changes: 4 additions & 0 deletions src/main/resources/application.yml
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,10 @@ folio:
enabled: true
environment: ${ENV:folio}
okapi-url: ${OKAPI_URL:http://okapi:9130}
logging:
feign:
enabled: true
level: full
management:
endpoints:
web:
Expand Down
4 changes: 3 additions & 1 deletion src/main/resources/swagger.api/ecs-tlr.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,9 @@ components:
ecs-tlr:
$ref: 'schemas/EcsTlr.yaml#/EcsTlr'
errorResponse:
$ref: schemas/errors.json
$ref: 'schemas/errors.json'
request:
$ref: 'schemas/request.json'
parameters:
requestId:
name: requestId
Expand Down
57 changes: 57 additions & 0 deletions src/main/resources/swagger.api/schemas/override-blocks.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
{
"$schema": "http://json-schema.org/draft-04/schema#",
"type": "object",
"description": "Blocks to override (e.g. during checkout or renewal)",
"properties": {
"itemNotLoanableBlock": {
"description": "'Item not loanable' block",
"type": "object",
"properties": {
"dueDate": {
"description": "Due date for a new loan",
"type": "string",
"format": "date-time"
}
},
"additionalProperties": false,
"required": [
"dueDate"
]
},
"patronBlock": {
"description": "Automated patron block",
"type": "object",
"additionalProperties": false
},
"itemLimitBlock": {
"description": "Item limit block",
"type": "object",
"additionalProperties": false
},
"renewalBlock": {
"description": "Renewal block",
"type": "object",
"additionalProperties": false
},
"renewalDueDateRequiredBlock": {
"description": "Override renewal block which requires due date field",
"type": "object",
"properties": {
"dueDate": {
"description": "Due date for a new loan",
"type": "string",
"format": "date-time"
}
},
"additionalProperties": false,
"required": [
"dueDate"
]
},
"comment": {
"description": "Reason for override",
"type": "string"
}
},
"additionalProperties": false
}
35 changes: 35 additions & 0 deletions src/main/resources/swagger.api/schemas/request-search-index.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
{
"$schema": "http://json-schema.org/draft-04/schema#",
"description": "Request fields used for search",
"type": "object",
"properties": {
"callNumberComponents": {
"type": "object",
"description": "Effective call number components",
"properties": {
"callNumber": {
"type": "string",
"description": "Effective Call Number is an identifier assigned to an item or its holding and associated with the item."
},
"prefix": {
"type": "string",
"description": "Effective Call Number Prefix is the prefix of the identifier assigned to an item or its holding and associated with the item."
},
"suffix": {
"type": "string",
"description": "Effective Call Number Suffix is the suffix of the identifier assigned to an item or its holding and associated with the item."
}
},
"additionalProperties": false
},
"shelvingOrder": {
"type": "string",
"description": "A system generated normalization of the call number that allows for call number sorting in reports and search results"
},
"pickupServicePointName": {
"description": "The name of the request pickup service point",
"type": "string"
}
},
"additionalProperties": false
}
Loading

0 comments on commit 2805baa

Please sign in to comment.