Commit 97f2eeda authored by Philippe Fonzin's avatar Philippe Fonzin

Merge branch 'master' into kafka

parents 6b1668b0 dcb3abf1
...@@ -32,4 +32,5 @@ build/ ...@@ -32,4 +32,5 @@ build/
### VS Code ### ### VS Code ###
.vscode/ .vscode/
/frontend/node_modules/ /frontend/node_modules/
\ No newline at end of file /frontend/src/config/
\ No newline at end of file
...@@ -38,3 +38,6 @@ ...@@ -38,3 +38,6 @@
- Order status update screen mark orders as fulfilled or cancelled - Order status update screen mark orders as fulfilled or cancelled
- Order search - Order search
- Order information page - Order information page
#### API Documentation
https://documenter.getpostman.com/view/7402212/TzRNGATe
This diff is collapsed.
...@@ -9,6 +9,7 @@ ...@@ -9,6 +9,7 @@
"axios": "^0.21.1", "axios": "^0.21.1",
"react": "^17.0.2", "react": "^17.0.2",
"react-dom": "^17.0.2", "react-dom": "^17.0.2",
"react-google-login": "^5.2.2",
"react-icons": "^4.2.0", "react-icons": "^4.2.0",
"react-redux": "^7.2.4", "react-redux": "^7.2.4",
"react-scripts": "4.0.3", "react-scripts": "4.0.3",
......
import Login from "./components/session/Login";
import Logout from "./components/session/Logout";
import Header from "./components/header/Header"; import Header from "./components/header/Header";
import Footer from "./components/footer/Footer"; import Footer from "./components/footer/Footer";
import OrderIndex from "./components/order/OrderIndex" import OrderIndex from "./components/order/OrderIndex"
...@@ -5,9 +7,11 @@ import OrderIndex from "./components/order/OrderIndex" ...@@ -5,9 +7,11 @@ import OrderIndex from "./components/order/OrderIndex"
const App = () => { const App = () => {
return ( return (
<div className="app"> <div className="app">
<Header /> <Login />
<OrderIndex /> <Logout />
<Footer /> <Header />
<OrderIndex />
<Footer />
</div> </div>
); );
} }
......
...@@ -4,9 +4,9 @@ export const RECEIVE_ORDERS = 'RECEIVE_ORDERS'; ...@@ -4,9 +4,9 @@ export const RECEIVE_ORDERS = 'RECEIVE_ORDERS';
export const RECEIVE_ORDER = 'RECEIVE_ORDER'; export const RECEIVE_ORDER = 'RECEIVE_ORDER';
export const UPDATE_ORDER = 'UPDATE_ORDER'; export const UPDATE_ORDER = 'UPDATE_ORDER';
const receiveOrders = (payload) => ({ const receiveOrders = (orders) => ({
type: RECEIVE_ORDERS, type: RECEIVE_ORDERS,
payload, orders,
}) })
const receiveOrder = (order) => ({ const receiveOrder = (order) => ({
...@@ -32,8 +32,9 @@ export const createOrder = (order) => (dispatch) => ...@@ -32,8 +32,9 @@ export const createOrder = (order) => (dispatch) =>
dispatch(receiveOrder(res)) dispatch(receiveOrder(res))
}); });
export const editOrder = (order) => (dispatch) => export const editOrder = (order) => (dispatch) => {
OrderAPIUtil.editOrder(order) OrderAPIUtil.editOrder(order)
.then(res => { .then(res => {
dispatch(updateOrder(res)) dispatch(updateOrder(res))
}); });
\ No newline at end of file }
\ No newline at end of file
import React from "react";
import { connect } from "react-redux";
import { editOrder } from "../../actions/order_actions";
const OrderButtons = ({ order, editOrder }) => {
// const { id, orderId, status, orderItems, createdAt, modifiedAt } = order;
const handleUpdate = (action) => {
console.log(action);
if (action === "FULFILL") {
editOrder({ ...order, status: "FULFILLED"})
} else if (action === "CANCEL") {
editOrder({ ...order, status: "CANCELLED" });
}
}
const fulfill = (
<button onClick={() => handleUpdate("FULFILL")}>Fulfill</button>
)
const cancel = (
<button onClick={() => handleUpdate("CANCEL")}>Cancel</button>
)
return (
<div>
{fulfill} {cancel}
</div>
);
};
const mapStateToProps = (state) => ({});
const mapDispatchToProps = (dispatch) => ({
editOrder: (order) => dispatch(editOrder(order)),
});
export default connect(mapStateToProps, mapDispatchToProps)(OrderButtons);
...@@ -23,17 +23,16 @@ const OrderIndex = ({ ...@@ -23,17 +23,16 @@ const OrderIndex = ({
<h1>Order Index</h1> <h1>Order Index</h1>
<button onClick={createOrder}>Create New Order</button> <button onClick={createOrder}>Create New Order</button>
<button onClick={editOrder}>Update Order</button> <button onClick={editOrder}>Update Order</button>
{orders.allIds.map(orderId => {
<br />
<br />
{orders.allIds.map((orderId) => {
const order = orders.byId[orderId]; const order = orders.byId[orderId];
return ( return <OrderIndexItem key={order.id} order={order} />;
<OrderIndexItem
key={order.id}
order={order}
/>
)
})} })}
</div> </div>
) );
} }
......
import React from 'react'; import React from 'react';
import OrderButtons from './OrderButtons';
const OrderIndexItem = ({ order }) => { const OrderIndexItem = ({ order }) => {
const {
id,
orderId,
status,
orderItems,
createdAt,
modifiedAt
} = order;
const actions = ( status === "RECEIVED" ?
<OrderButtons order={order} />
:
<div>{status}</div>)
return ( return (
<div> <div>
{order.orderId} {order.status} <div>{`Order #: ${orderId}`}</div>
{actions}
</div> </div>
) )
}; };
......
import React from 'react';
import { GoogleLogin } from "react-google-login";
import keys from '../../config/keys_dev'
const clientId = keys.clientId;
const Login = () => {
const responseGoogle = (response) => {
console.log(response);
};
return (
<div>
<GoogleLogin
clientId={clientId}
buttonText="Login with Google"
onSuccess={responseGoogle}
onFailure={responseGoogle}
cookiePolicy={"single_host_origin"}
// isSignedIn={true}
/>
</div>
);
}
export default Login;
\ No newline at end of file
import React from "react";
import { GoogleLogout } from "react-google-login";
import keys from "../../config/keys_dev";
const clientId = keys.clientId;
const Logout = () => {
const responseGoogle = (response) => {
console.log(response);
};
return (
<div>
<GoogleLogout
clientId={clientId}
buttonText="Logout"
onLogoutSuccess={responseGoogle}
isSignedIn={true}
/>
</div>
);
};
export default Logout;
...@@ -13,13 +13,21 @@ const OrdersReducer = (oldState = initialState, action) => { ...@@ -13,13 +13,21 @@ const OrdersReducer = (oldState = initialState, action) => {
Object.freeze(oldState); Object.freeze(oldState);
const newState = { ...oldState }; const newState = { ...oldState };
const order = action.order || null; const order = action.order || null;
switch (action.type) { switch (action.type) {
case RECEIVE_ORDERS: case RECEIVE_ORDERS:
return action.payload; const orderState = {
byId: {},
allIds: [],
};
Object.keys(action.orders).forEach( wareId => {
orderState.allIds.push(wareId);
orderState.byId[wareId] = action.orders[wareId];
})
return orderState;
case RECEIVE_ORDER: case RECEIVE_ORDER:
newState.byId[order.id] = order; newState.byId[order.id] = order;
newState.allIds.unshift(order.id); newState.allIds.push(order.id);
return newState; return newState;
case UPDATE_ORDER: case UPDATE_ORDER:
newState.byId[order.id] = order; newState.byId[order.id] = order;
......
// import axios from 'axios'; // import axios from 'axios';
const RECEIVED = "RECEIVED";
// const FULFILLED = "FULFILLED";
// const CANCELLED = "CANCELLED";
const sampleGetAll = { const sampleGetAll = {
allIds: ["1", "2", "3"], // allIds: ["1", "2", "3"],
byId: { // byId: {
"1": { 1: {
id: "1", id: "1",
orderId: "o1", orderId: "o1",
status: "unfulfilled", status: RECEIVED,
}, orderItems: [
"2": { {
id: "2", itemId: "17",
orderId: "o2", itemName: "Item 1",
status: "unfulfilled", itemQuantity: 4,
}, itemPrice: 17.99,
"3": { itemSku: 8765309,
id: "3", },
orderId: "o3", {
status: "unfulfilled", itemId: "18",
}, itemName: "Item 2",
itemQuantity: 42,
itemPrice: 17.99,
itemSku: 8715309,
},
],
},
2: {
id: "2",
orderId: "o2",
status: RECEIVED,
orderItems: [
{
itemId: "17",
itemName: "Item 1",
itemQuantity: 3,
itemPrice: 17.99,
itemSku: 8765309,
},
{
itemId: "18",
itemName: "Item 2",
itemQuantity: 41,
itemPrice: 17.99,
itemSku: 8715309,
},
],
},
3: {
id: "3",
orderId: "o3",
status: RECEIVED,
orderItems: [
{
itemId: "17",
itemName: "Item 1",
itemQuantity: 2,
itemPrice: 17.99,
itemSku: 8765309,
},
{
itemId: "18",
itemName: "Item 2",
itemQuantity: 40,
itemPrice: 17.99,
itemSku: 8715309,
},
],
}, },
// },
}; };
const sampleNew = { const sampleNew = {
id: "4", id: "4",
orderId: "o4", orderId: "o4",
status: "unfulfilled", status: RECEIVED,
};
const sampleUpdateFul = {
id: "3",
orderId: "o3",
status: "fulfilled",
};
const sampleUpdateCan = {
id: "2",
orderId: "o2",
status: "cancelled",
}; };
const getAllPromise = new Promise( (resolve, reject) => { const getAllPromise = new Promise( (resolve, reject) => {
...@@ -45,12 +85,6 @@ const getAllPromise = new Promise( (resolve, reject) => { ...@@ -45,12 +85,6 @@ const getAllPromise = new Promise( (resolve, reject) => {
const createNewPromise = new Promise( (resolve, reject) => { const createNewPromise = new Promise( (resolve, reject) => {
resolve(sampleNew) resolve(sampleNew)
}) })
const updateFulfillPromise = new Promise( (resolve, reject) => {
resolve(sampleUpdateFul)
})
const updateCancelPromise = new Promise( (resolve, reject) => {
resolve(sampleUpdateCan)
})
export const getOrders = () => { export const getOrders = () => {
return getAllPromise; return getAllPromise;
...@@ -61,7 +95,9 @@ export const createOrder = (order) => { ...@@ -61,7 +95,9 @@ export const createOrder = (order) => {
} }
export const editOrder = (order) => { export const editOrder = (order) => {
return updateFulfillPromise; return new Promise( (resolve, reject) => {
resolve(order);
})
} }
// export const getOrders =() => { // export const getOrders =() => {
......
...@@ -63,7 +63,17 @@ ...@@ -63,7 +63,17 @@
<scope>test</scope> <scope>test</scope>
</dependency> </dependency>
<dependency> <groupId>org.mongodb</groupId> <artifactId>mongodb-driver-sync</artifactId> <version>4.0.5</version> </dependency> <dependency>
<groupId>org.mongodb</groupId>
<artifactId>mongodb-driver-sync</artifactId>
<version>4.0.5</version>
</dependency>
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<scope>test</scope>
</dependency>
</dependencies> </dependencies>
<build> <build>
......
...@@ -14,14 +14,28 @@ public class WarehouseController { ...@@ -14,14 +14,28 @@ public class WarehouseController {
@Autowired @Autowired
WarehouseOrderService orderService; WarehouseOrderService orderService;
@CrossOrigin
@GetMapping(value = "/orders") @GetMapping(value = "/orders")
public Flux<WarehouseOrder> getOrders() { public Flux<WarehouseOrder> getOrders() {
return orderService.getOrders(); return orderService.getOrders();
} }
@CrossOrigin
@GetMapping("/orders/{id}")
public Mono<WarehouseOrder> findStudent(@PathVariable String id){
return orderService.findOrderById(id);
}
@CrossOrigin
@PostMapping(value = "/orders") @PostMapping(value = "/orders")
public Mono<WarehouseOrder> createOrder(@RequestBody WarehouseOrder order) { public Mono<WarehouseOrder> createOrder(@RequestBody WarehouseOrder order) {
return orderService.createOrder(order); return orderService.createOrder(order);
} }
@CrossOrigin
@PutMapping(value = "/orders/{id}")
public Mono<WarehouseOrder> updateOrder(@RequestBody WarehouseOrder order, @PathVariable(value = "id") String id) {
return orderService.updateOrder(order, id);
}
} }
package com.ascendfinalproject.warehouse.models;
import lombok.Getter;
import lombok.Setter;
import java.util.HashMap;
import java.util.List;
@Getter
@Setter
public class OrderResponse {
private List<String> allIds;
private HashMap<String, WarehouseOrder> byId;
public void appendId(String id) {
allIds.add(id);
}
}
...@@ -3,7 +3,6 @@ package com.ascendfinalproject.warehouse.services; ...@@ -3,7 +3,6 @@ package com.ascendfinalproject.warehouse.services;
import com.ascendfinalproject.warehouse.models.WarehouseOrder; import com.ascendfinalproject.warehouse.models.WarehouseOrder;
import com.ascendfinalproject.warehouse.repositories.WarehouseOrderRepository; import com.ascendfinalproject.warehouse.repositories.WarehouseOrderRepository;
import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.repository.ReactiveMongoRepository;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import reactor.core.publisher.Flux; import reactor.core.publisher.Flux;
import reactor.core.publisher.Mono; import reactor.core.publisher.Mono;
...@@ -14,12 +13,34 @@ public class WarehouseOrderService { ...@@ -14,12 +13,34 @@ public class WarehouseOrderService {
@Autowired @Autowired
WarehouseOrderRepository orderRepository; WarehouseOrderRepository orderRepository;
public Mono<WarehouseOrder> findOrderById(String id) {
return orderRepository.findById(id);
}
public Flux<WarehouseOrder> getOrders() { public Flux<WarehouseOrder> getOrders() {
return orderRepository.findAll(); return orderRepository.findAll();
// OrderResponse response = new OrderResponse();
// orderRepository.findAll()
// .flatMap(order -> {
// response.appendId(order.getId());
// response.getById().put(order.getId(), order);
// });
//
// return response;
} }
public Mono<WarehouseOrder> createOrder(WarehouseOrder order) { public Mono<WarehouseOrder> createOrder(WarehouseOrder order) {
return orderRepository.save(order); return orderRepository.save(order);
} }
public Mono<WarehouseOrder> updateOrder(WarehouseOrder order, String id) {
return orderRepository.findById(id)
.flatMap(existingOrder -> {
existingOrder.setOrderId(order.getOrderId());
existingOrder.setStatus(order.getStatus());
return orderRepository.save(existingOrder);
});
}
} }
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