Commit fdd09a24 authored by Sumaiyya Burney's avatar Sumaiyya Burney

Merge branch 'dev' into 'master'

Done!

See merge request !14
parents 3bb65f90 15e00df8
File added
......@@ -3,7 +3,6 @@ target/
!.mvn/wrapper/maven-wrapper.jar
!**/src/main/**/target/
!**/src/test/**/target/
### STS ###
.apt_generated
.classpath
......@@ -31,3 +30,5 @@ build/
### VS Code ###
.vscode/
secret.properties
......@@ -3,3 +3,15 @@ COPY target/inventory-0.0.1-SNAPSHOT.jar /usr/local/lib/inventory.jar
EXPOSE 8080
ENTRYPOINT ["java","-jar","/usr/local/lib/inventory.jar"]
# For local testing, comment the top part out and uncomment the bottom
# DO NOT commit to GL with the top part commented and/or the bottom part uncommnted!!!!!!
#FROM maven:3.6.0-jdk-11-slim AS build
#COPY src /home/app/src
#COPY pom.xml /home/app
#RUN mvn -f /home/app/pom.xml clean package -DskipTests
#
#FROM openjdk:11-jre-slim
#COPY --from=build /home/app/target/inventory-0.0.1-SNAPSHOT.jar /usr/local/lib/inventory.jar
#EXPOSE 8080
#ENTRYPOINT ["java","-jar","/usr/local/lib/inventory.jar"]
\ No newline at end of file
apiVersion: apps/v1
kind: Deployment
metadata:
name: afp-products-deployment
spec:
replicas: 2
selector:
matchLabels:
app: afp-products
template:
metadata:
labels:
app: afp-products
spec:
containers:
- name: afp-products-container
image: nexus.mynisum.com/afp-products:latest
imagePullPolicy: Always
ports:
- containerPort: 8080
env:
- name: PORT
value: "8080"
imagePullSecrets:
- name: registry-creds
---
apiVersion: v1
kind: Service
metadata:
name: afp-products-service
spec:
type: LoadBalancer
ports:
- port: 8080
targetPort: 8080
selector:
app: afp-products
\ No newline at end of file
......@@ -6,7 +6,7 @@
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.4.5</version>
<relativePath/> <!-- lookup parent from repository -->
<relativePath/> <!-- lookup parent from com.nisum.ascend.inventory.repository -->
</parent>
<groupId>com.nisum.ascend</groupId>
<artifactId>inventory</artifactId>
......@@ -29,7 +29,10 @@
<groupId>org.springframework.kafka</groupId>
<artifactId>spring-kafka</artifactId>
</dependency>
<dependency>
<groupId>io.projectreactor.kafka</groupId>
<artifactId>reactor-kafka</artifactId>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
......@@ -50,6 +53,12 @@
<artifactId>spring-kafka-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>io.springfox</groupId>
<artifactId>springfox-boot-starter</artifactId>
<version>3.0.0</version>
</dependency>
</dependencies>
<build>
......
File added
package com.nisum.ascend.inventory.configuration;
import com.nisum.ascend.inventory.dto.Order;
import com.nisum.ascend.inventory.dto.WareHouseOrder;
import lombok.extern.slf4j.Slf4j;
import org.apache.kafka.clients.consumer.ConsumerConfig;
import org.apache.kafka.clients.producer.ProducerConfig;
import org.apache.kafka.common.serialization.StringDeserializer;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.kafka.support.serializer.JsonDeserializer;
import reactor.kafka.receiver.KafkaReceiver;
import reactor.kafka.receiver.ReceiverOptions;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
@Configuration
@Slf4j
public class KafkaReceiverConfig {
@Value("${kafka.consumer.bootstrap-servers}")
private String bootstrapServers;
@Value("${kafka.consumer.group-id}")
private String groupId;
@Bean("kafkaWarehouseOrderReceiver")
public KafkaReceiver<String, String> kafkaWarehouseOrderEventReceiver(
@Value("${kafka.WAREHOUSETOPIC.input}") String posLogTopic) {
ReceiverOptions<String, String> receiverOptions = ReceiverOptions.create(WarehouseOrderEventReceiverConfig());
receiverOptions.maxCommitAttempts(3);
return KafkaReceiver.create(receiverOptions.addAssignListener(Collection::iterator)
.subscription(Collections.singleton(posLogTopic)));
}
private Map<String, Object> WarehouseOrderEventReceiverConfig() {
Map<String, Object> config = new HashMap<>();
config.put(ConsumerConfig.GROUP_ID_CONFIG, groupId);
config.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapServers);
config.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
config.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
return config;
}
@Bean("kafkaOrderReceiver")
public KafkaReceiver<String, String> kafkaOrderEventReceiver(
@Value("${kafka.ORDERTOPIC.input}") String posLogTopic) {
ReceiverOptions<String, String> receiverOptions = ReceiverOptions.create(OrderEventReceiverConfig());
receiverOptions.maxCommitAttempts(3);
return KafkaReceiver.create(receiverOptions.addAssignListener(Collection::iterator)
.subscription(Collections.singleton(posLogTopic)));
}
private Map<String, Object> OrderEventReceiverConfig() {
Map<String, Object> config = new HashMap<>();
config.put(ConsumerConfig.GROUP_ID_CONFIG, groupId);
config.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapServers);
config.put(ConsumerConfig.KEY_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
config.put(ConsumerConfig.VALUE_DESERIALIZER_CLASS_CONFIG, StringDeserializer.class);
return config;
}
}
\ No newline at end of file
package com.nisum.ascend.inventory.configuration;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.reactive.config.EnableWebFlux;
import org.springframework.web.reactive.config.WebFluxConfigurer;
@Configuration
@EnableWebFlux
public class WebFluxConfig implements WebFluxConfigurer {
}
package com.nisum.ascend.inventory.controller;
import com.nisum.ascend.inventory.exception.ResourceAlreadyExistsException;
import com.nisum.ascend.inventory.model.Product;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import com.nisum.ascend.inventory.service.ProductService;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import reactor.core.publisher.Mono;
import reactor.core.publisher.Flux;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.reactive.function.server.ServerResponse;
import reactor.core.publisher.Mono;
import com.nisum.ascend.inventory.service.ProductService;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
@CrossOrigin(origins = "*")
@RestController
@RequestMapping("/api/products")
public class ProductController {
@Autowired
ProductService productService;
@DeleteMapping(value = "/{sku}")
public Mono<ResponseEntity<Void>> deleteProduct(@PathVariable String sku) {
return productService.removeProductBySku(sku)
.map(res -> ResponseEntity.ok().<Void>build())
.defaultIfEmpty(ResponseEntity.notFound().build());
}
@GetMapping("/{sku}")
public ResponseEntity<Mono<Product>> getProductBySku(@PathVariable String sku) {
Mono<Product> monoProd = productService.getProductBySku(sku);
HttpStatus status = monoProd != null ? HttpStatus.OK : HttpStatus.NOT_FOUND;
return new ResponseEntity<>(monoProd, status);
}
@GetMapping()
public ResponseEntity<Flux<Product>> getAllProducts() {
return ResponseEntity.ok(productService.findAllProducts());
}
@PutMapping("/{sku}")
public Mono<ResponseEntity<Product>> updateProduct(@PathVariable String sku, @RequestBody Product product){
return productService.updateProductBySku(sku, product)
.map(updatedProduct -> ResponseEntity.ok(updatedProduct))
.defaultIfEmpty(ResponseEntity.badRequest().build());
}
@PostMapping("")
public Mono<Product> postProduct(@RequestBody Product product) {
return productService.createProduct(product).onErrorMap(throwable -> new ResourceAlreadyExistsException());
}
}
\ No newline at end of file
package com.nisum.ascend.inventory.dto;
import lombok.Data;
@Data
public class CustomerAddress {
private String street;
private String city;
private String state;
private String zip;
}
package com.nisum.ascend.inventory.dto;
import lombok.Data;
@Data
public class Item {
private String itemId;
private String itemName;
private String itemSku;
private int itemQuantity;
private double itemPrice;
}
package com.nisum.ascend.inventory.dto;
import lombok.Data;
import java.time.LocalDate;
import java.util.List;
@Data
public class Order {
private String id;
private long orderUpdatedAt;
private long orderCreatedAt;
private String customerId;
private String customerEmailAddress;
private String orderStatus;
List<Item> orderItems;
private String orderTrackingCode;
private CustomerAddress customerAddress;
}
package com.nisum.ascend.inventory.dto;
import com.nisum.ascend.inventory.dto.Item;
import lombok.Data;
import java.util.Date;
import java.util.List;
@Data
public class WareHouseOrder {
private String id;
private String orderId;
private String status;
private Date createdAt;
private Date modifiedAt;
private List<Item> orderItems;
private String address;
}
package com.nisum.ascend.inventory.exception;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ResponseStatus;
@ResponseStatus(value = HttpStatus.NOT_ACCEPTABLE)
public class ResourceAlreadyExistsException extends RuntimeException {
public ResourceAlreadyExistsException() {
super("A resource with the provided SKU already exists");
}
}
package com.nisum.ascend.inventory.exception;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ResponseStatus;
@ResponseStatus(value = HttpStatus.NOT_FOUND)
public class ResourceNotFoundException extends Exception{
HttpStatus status;
public ResourceNotFoundException(HttpStatus status, String message) {
super(message);
this.status = status;
}
}
package com.nisum.ascend.inventory.exception;
import com.mongodb.DuplicateKeyException;
import org.springframework.core.annotation.Order;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Component;
import org.springframework.web.server.ServerWebExchange;
import org.springframework.web.server.WebExceptionHandler;
import reactor.core.publisher.Mono;
@Component
@Order(-2)
class RestWebExceptionHandler implements WebExceptionHandler {
@Override
public Mono<Void> handle(ServerWebExchange exchange, Throwable ex) {
if (ex instanceof ResourceAlreadyExistsException) {
exchange.getResponse().setStatusCode(HttpStatus.NOT_ACCEPTABLE);
// marks the response as complete and forbids writing to it
return exchange.getResponse().setComplete();
}
return Mono.error(ex);
}
}
package com.nisum.ascend.inventory.model;
import lombok.Getter;
import lombok.Setter;
import org.springframework.data.annotation.Id;
import org.springframework.data.mongodb.core.index.Indexed;
import org.springframework.data.mongodb.core.mapping.Document;
@Getter
@Setter
@Document(collection = "products")
public class Product {
@Id
private String id;
@Indexed(unique=true)
private String sku;
private String upc;
private String productName;
private String productDescription;
private float price;
private int availableStock;
private int blockedStock;
private int fulfilledStock;
private String productImageUrl;
private String brand;
private String category;
public Product() {}
public Product(String sku, String upc, String productName, String productDescription, float price, int availableStock,
String productImageUrl, String brand, String category) {
this.sku = sku;
this.upc = upc;
this.productName = productName;
this.productDescription = productDescription;
this.price = price;
this.availableStock = availableStock;
this.blockedStock = 0;
this.fulfilledStock = 0;
this.productImageUrl = productImageUrl;
this.brand = brand;
this.category = category;
}
}
package com.nisum.ascend.inventory.repository;
import com.nisum.ascend.inventory.model.Product;
import org.springframework.data.mongodb.repository.Query;
import org.springframework.data.mongodb.repository.ReactiveMongoRepository;
import org.springframework.stereotype.Repository;
import reactor.core.publisher.Mono;
@Repository
public interface ProductRepository extends ReactiveMongoRepository<Product, String> {
Mono<Product> findBySku(String sku);
}
package com.nisum.ascend.inventory.service;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.nisum.ascend.inventory.dto.Item;
import com.nisum.ascend.inventory.dto.Order;
import com.nisum.ascend.inventory.dto.WareHouseOrder;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.boot.context.event.ApplicationStartedEvent;
import org.springframework.context.event.EventListener;
import org.springframework.stereotype.Component;
import reactor.kafka.receiver.KafkaReceiver;
import java.util.List;
@Component
@Slf4j
public class KafkaListenerService {
@Autowired
@Qualifier("kafkaWarehouseOrderReceiver")
private KafkaReceiver<String, String> kafkaWarehouseOrderReceiver;
@Autowired
@Qualifier("kafkaOrderReceiver")
private KafkaReceiver<String, String> kafkaOrderReceiver;
@Autowired
private ProductService productService;
@EventListener(ApplicationStartedEvent.class)
public void consumeWarehouseOrderStatus() {
kafkaWarehouseOrderReceiver.receive()
.doOnNext(record -> log.info("record: {}", record))
.doOnNext(record -> onWarehouseOrderStatusReceived(record.value()))
.doOnError(throwable -> System.out.println(throwable.getMessage()))
.subscribe();
}
private void onWarehouseOrderStatusReceived(String warehouseOrderString) {
try {
ObjectMapper objectMapper = new ObjectMapper();
WareHouseOrder warehouseOrder = objectMapper.readValue(warehouseOrderString, WareHouseOrder.class);
List<Item> itemList = warehouseOrder.getOrderItems();
String status = warehouseOrder.getStatus();
log.info("Received this data: {}", warehouseOrder);
log.info("recieved this list: {}", itemList);
for (Item item : itemList) {
productService.updateProductInventoryBySkuWareHouse(item.getItemSku(), status, item.getItemQuantity()).subscribe();
}
} catch (Exception e) {
log.error("error", e);
}
}
@EventListener(ApplicationStartedEvent.class)
public void consumeOrderStatus() {
kafkaOrderReceiver.receive()
.doOnNext(record -> log.info("record: {}", record))
.doOnNext(record -> onOrderStatusReceived(record.value()))
.doOnError(throwable -> System.out.println(throwable.getMessage()))
.subscribe();
}
private void onOrderStatusReceived(String orderString) {
try {
ObjectMapper objectMapper = new ObjectMapper();
Order order = objectMapper.readValue(orderString, Order.class);
List<Item> itemList = order.getOrderItems();
String status = order.getOrderStatus();
log.info("Received this data: {}", order);
log.info("recieved this list: {}", itemList);
for (Item item : itemList) {
productService.updateProductInventoryBySkuOrder(item.getItemSku(), status, item.getItemQuantity()).block();
}
} catch (Exception e) {
log.error("error", e);
}
}
}
package com.nisum.ascend.inventory.service;
import com.nisum.ascend.inventory.dto.Item;
import com.nisum.ascend.inventory.exception.ResourceNotFoundException;
import com.nisum.ascend.inventory.model.Product;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Service;
import reactor.core.publisher.Flux;
import com.nisum.ascend.inventory.repository.ProductRepository;
import reactor.core.publisher.Mono;
import java.util.ArrayList;
import java.util.List;
@Service
public class ProductService {
@Autowired
ProductRepository productRepository;
public Mono<Product> removeProductBySku(String sku) {
return productRepository
.findBySku(sku)
.flatMap(existingProduct -> productRepository.delete(existingProduct)
.then(Mono.just(existingProduct)))
.switchIfEmpty(Mono.error(new ResourceNotFoundException(HttpStatus.NOT_FOUND, "Product Not Found")));
}
public Mono<Product> getProductBySku(String sku){
return productRepository.findBySku(sku)
.switchIfEmpty(Mono.error(new ResourceNotFoundException(HttpStatus.NOT_FOUND, "product not found")));
}
public Flux<Product> findAllProducts() {
return productRepository.findAll();
}
public Mono<Product> updateProductBySku(String sku, Product product){
return productRepository.findBySku(sku)
.flatMap(dbProduct -> {
dbProduct.setUpc(product.getUpc());
dbProduct.setProductName(product.getProductName());
dbProduct.setProductDescription(product.getProductDescription());
dbProduct.setBrand(product.getBrand());
dbProduct.setCategory(product.getCategory());
dbProduct.setPrice(product.getPrice());
dbProduct.setAvailableStock(product.getAvailableStock());
dbProduct.setProductImageUrl(product.getProductImageUrl());
return productRepository.save(dbProduct);
});
}
public Mono<Product> createProduct(Product product) {
return productRepository.save(product);
}
public Mono<Product> updateProductInventoryBySkuWareHouse(String sku, String status, int itemQuantity) {
System.out.printf("sku = %s, status = %s, itemquanity = %d \n", sku, status, itemQuantity);
if (status.equals("CANCELLED")) {
return productRepository.findBySku(sku)
.flatMap(dbProduct -> {
dbProduct.setBlockedStock(dbProduct.getBlockedStock() - itemQuantity);
dbProduct.setAvailableStock(dbProduct.getAvailableStock() + itemQuantity);
return productRepository.save(dbProduct);
});
}
else if (status.equals("FULFILLED")){
return productRepository.findBySku(sku)
.flatMap(dbProduct -> {
dbProduct.setBlockedStock(dbProduct.getBlockedStock() - itemQuantity);
dbProduct.setFulfilledStock(dbProduct.getFulfilledStock() + itemQuantity);
return productRepository.save(dbProduct);
});
}
else return productRepository.findBySku(sku);
}
public Mono<Product> updateProductInventoryBySkuOrder(String sku, String status, int itemQuantity) {
System.out.printf("sku = %s, status = %s, itemquanity = %d \n", sku, status, itemQuantity);
// should only process RECEIVED
if (status.equals("RECEIVED")) {
return productRepository.findBySku(sku)
.flatMap(dbProduct -> {
dbProduct.setAvailableStock(dbProduct.getAvailableStock() - itemQuantity);
dbProduct.setBlockedStock(dbProduct.getBlockedStock() + itemQuantity);
return productRepository.save(dbProduct);
});
}
else return productRepository.findBySku(sku);
}
}
spring.data.mongodb.uri=mongodb+srv://admin:${db.password}@inventory-promotions.d4nfz.mongodb\
.net/${spring.data.mongodb.database}?retryWrites=true&w=majority
spring.data.mongodb.database=test
server.port=8083
spring.data.mongodb.uri=mongodb+srv://admin:${db.password}@inventory-promotions.d4nfz.mongodb\
.net/${spring.data.mongodb.database}?retryWrites=true&w=majority
spring.data.mongodb.database=products-promotions-DB
kafka.consumer.acks=all
kafka.consumer.bootstrap-servers=localhost:9092
kafka.consumer.group-id=PRODUCT
kafka.WAREHOUSETOPIC.input=WMOS_ORDER_UPDATE
kafka.ORDERTOPIC.input=OMS_ORDER_UPDATE
db.password=wHXHvtngAwKVdjZl
\ No newline at end of file
package com.nisum.ascend.inventory.controller;
import com.nisum.ascend.inventory.model.Product;
import com.nisum.ascend.inventory.repository.ProductRepository;
import com.nisum.ascend.inventory.service.ProductService;
import com.nisum.ascend.inventory.controller.ProductController;
import com.nisum.ascend.inventory.model.Product;
import lombok.extern.slf4j.Slf4j;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.extension.ExtendWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.reactive.AutoConfigureWebTestClient;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.http.ResponseEntity;
import org.mockito.Mock;
import org.springframework.boot.test.mock.mockito.MockBean;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.test.annotation.DirtiesContext;
import org.springframework.test.context.ActiveProfiles;
import org.springframework.test.context.junit.jupiter.SpringExtension;
import org.springframework.test.web.reactive.server.WebTestClient;
import org.springframework.web.bind.annotation.ResponseBody;
import reactor.core.publisher.Mono;
import static org.junit.jupiter.api.Assertions.*;
import org.springframework.web.reactive.function.client.WebClient;
import java.util.List;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertTrue;
import reactor.core.publisher.Mono;
import java.util.Random;
import java.util.UUID;
import static org.junit.jupiter.api.Assertions.*;
@ExtendWith(SpringExtension.class)
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
@DirtiesContext
@AutoConfigureWebTestClient
@ActiveProfiles("test")
@Slf4j
class ProductControllerTest {
@Autowired
private WebTestClient webTestClient;
@BeforeEach
public void setup(){
}
@Test
void testProductInvalidSkuNotFound() {
webTestClient
.get()
.uri("/api/products/".concat("{sku}"), "invalid")
.exchange()
.expectStatus()
.isNotFound();
}
@Test
void testProductBySkuFound() {
String sku = "000001";
webTestClient.get()
.uri("/api/products/".concat("/{sku}"), sku)
.exchange()
.expectStatus()
.isOk()
.expectBody()
.jsonPath("$.sku", sku);
}
@Test
void testFindAllProducts(){
webTestClient.get()
.uri("/api/products")
.exchange()
.expectStatus().isOk()
.expectHeader().contentType(MediaType.APPLICATION_JSON_VALUE)
.expectBodyList(Product.class)
.consumeWith(product ->{
List<Product> products = product.getResponseBody();
assert products != null;
products.forEach(p ->{
assertNotNull(p.getSku());
assertNotNull(p.getUpc());
System.out.println("Product SKU: " + p.getSku());
System.out.println("Product UPC: " + p.getUpc());
});
});
}
/*
If you want to do this test, make sure to insert the following in MongoDB Atlas:
,
"sku": "SH=1123",
"upc":"3d2dsd9cm",
"productName":"Blue Sweater",
"productDescription":"A Nice red sweater",
"price":23.99,
"availableStock":45,
"blockedStock":0,
"productImageUrl":"",
"brand":"SweatCo",
"category":"Sweatshirts"
*/
@Test
public void testDeleteProduct(){
Product deleteLater = new Product("SH=1123", "3d2dsd9cm", "Blue Sweater", "A nice red sweater", 23.99f, 45,
"", "SweatCo", "Sweatshirts");
webTestClient.get()
.uri("/api/products".concat("/{productSku}"), deleteLater.getSku())
.exchange()
.expectStatus().isNotFound();
webTestClient.post()
.uri("/api/products")
.contentType(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.body(Mono.just(deleteLater), Product.class)
.exchange()
.expectStatus().isOk()
.expectBody(Product.class);
webTestClient.delete()
.uri("/api/products".concat("/{productSku}"), deleteLater.getSku())
.accept(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.exchange()
.expectStatus().isOk()
.expectBody(Void.class);
webTestClient.get()
.uri("/api/products".concat("/{productSku}"), deleteLater.getSku())
.exchange()
.expectStatus().isNotFound();
// String sku = "SH=1123";
// webTestClient.delete().uri("/api/products".concat("/{sku}"),sku)
// .accept(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
// .exchange()
// .expectStatus().isOk()
// .expectBody(Void.class);
//
// System.out.println("Deletion Successful. Ending test...");
}
@Test
void postProduct() {
String sku = "SH=" + UUID.randomUUID();
Product product = new Product(sku, "3d2dsd9cm", "Red Sweater",
"A Nice red sweater", (float) 23.99, 45, "",
"SweatCo", "Sweatshirts");
webTestClient.post().uri("/api/products")
.contentType(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.body(Mono.just(product), Product.class)
.exchange()
.expectStatus().isOk()
.expectBody()
.jsonPath("$.sku", sku);
}
@Test
public void updateProduct(){
Random rd = new Random();
float newPrice = rd.nextFloat()*100;
String sku = "SKU-PUT";
Product product = new Product(sku, "3d2dsd9cm", "Blue Sweater",
"A Nice red sweater", newPrice, 45, "",
"SweatCo", "Sweatshirts");
webTestClient.put().uri("/api/products".concat("/{sku}"),sku)
.contentType(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.accept(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.body(Mono.just(product),Product.class)
.exchange()
.expectStatus().isOk()
.expectBody()
.jsonPath("$.price").isEqualTo(newPrice);
}
@Test
public void updateProduct_notFound(){
double newPrice = 49.99;
String sku = "SH=2021";
Product product = new Product(sku, "3d2dsd9cm", "Blue Sweater",
"A Nice red sweater", 23.99f, 45, "",
"SweatCo", "Sweatshirts");
webTestClient.put().uri("/api/products".concat("/{sku}"),sku)
.contentType(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.accept(MediaType.valueOf(MediaType.APPLICATION_JSON_VALUE))
.body(Mono.just(product),Product.class)
.exchange()
.expectStatus().isBadRequest();
}
}
\ No newline at end of file
server.port=8080
spring.data.mongodb.uri=mongodb+srv://admin:${db.password}@inventory-promotions.d4nfz.mongodb\
.net/${spring.data.mongodb.database}?retryWrites=true&w=majority
spring.data.mongodb.database=test
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment