Skip to content

Commit

Permalink
Merge pull request #27 from deco-sites/feature/admin-signin-order-dis…
Browse files Browse the repository at this point in the history
…count

created login for admin, dashboard to display orders
  • Loading branch information
baufaker authored Apr 22, 2024
2 parents ce83048 + ab5d377 commit 8a50d00
Show file tree
Hide file tree
Showing 15 changed files with 681 additions and 126 deletions.
81 changes: 81 additions & 0 deletions actions/adminGetOrders.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
import { Product } from "deco-sites/ecannadeco/components/ui/CheckoutUpsellModal.tsx";

export interface Props {
token: string;
params?: {
status?: string;
page: number;
limit: number;
};
}

export interface Sku {
_id: string;
name: string;
product: string | Product;
}

export interface Order {
_id: string;
value: number;
type: string;
status:
| "PAID"
| "PENDING"
| "CANCELED"
| "IN_PRODUCTION"
| "PENDING_SHIPPING"
| "SHIPPED"
| "DELIVERED";
subscription: string;
payment: string;
created_at: string;
updated_at: string;
items: {
sku: Sku;
quantity: number;
}[];
}

export interface PaginationOrderResponse {
docs: Order[];
totalDocs: number;
totalPages: number;
page: number;
limit?: number;
pagingCounter?: number;
hasPrevPage: boolean;
hasNextPage: boolean;
}

const adminGetOrders = async (
{ token, params }: Props,
_req: Request,
): Promise<PaginationOrderResponse> => {
let url = `http://localhost:3000/admin/orders/`;

if (params) {
const query = `?limit=${params.limit}&page=${params.page}${
params.status && `&status=${params.status}`
}`;
url = `http://localhost:3000/admin/orders${query}`;
}

try {
const response = await fetch(url, {
method: "GET",
headers: {
"Content-Type": "application/json",
Authorization: token,
},
});

const res = await response.json();
return res;
} catch (e) {
// console.log({ e });
return e;
}
};

export default adminGetOrders;
30 changes: 30 additions & 0 deletions actions/cognitoAdminSignIn.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
export interface Props {
email: string;
password: string;
}

const signInCognito = async (
props: Props,
_req: Request,
): Promise<unknown | null> => {
try {
const response = await fetch("http://localhost:3000/admin/sign-in", {
method: "POST",
headers: {
"Content-Type": "application/json",
},
body: JSON.stringify({
email: props.email,
password: props.password,
}),
});

const res = await response.json();
return res;
} catch (e) {
// console.log({ e });
return e;
}
};

export default signInCognito;
3 changes: 3 additions & 0 deletions actions/getUserOrders.ts
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,9 @@ export interface Order {
sku: Sku;
quantity: number;
}[];
user_data?: {
email: string;
};
}

export interface PaginationOrderResponse {
Expand Down
222 changes: 222 additions & 0 deletions components/ui/AdminOrders.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,222 @@
/**
* This component was made to control if user is logged in to access pages
*/
// import type { SectionProps } from "deco/types.ts";
// import { useUI } from "../../sdk/useUI.ts";
import { useEffect, useState } from "preact/hooks";
import { invoke } from "../../runtime.ts";
import PageWrap from "./PageWrap.tsx";
import OrderStatus from "./OrderStatus.tsx";
import Icon from "deco-sites/ecannadeco/components/ui/Icon.tsx";
import { format } from "datetime";

import type {
Order,
PaginationOrderResponse,
} from "../../actions/getUserOrders.ts";
import Slider from "./Slider.tsx";
import { useUI } from "../../sdk/useUI.ts";
import SliderJS from "../../islands/SliderJS.tsx";

const OrderItem = (
{ productName, userEmail, productPrice, created_at, status }: {
userEmail: string;
productName: string;
productPrice: string;
created_at: string;
status:
| "PAID"
| "PENDING"
| "CANCELED"
| "IN_PRODUCTION"
| "PENDING_SHIPPING"
| "SHIPPED"
| "DELIVERED";
},
) => {
return (
<li class="p-3 bg-[#cacaca] flex justify-between items-center rounded-md text-[10px] sm:text-xs md:text-sm">
<div class="w-[40%] flex justify-start truncate pr-4">
<span>{userEmail}</span>
</div>
<div class="w-[20%] flex flex-col justify-start">
<span>{productName}</span>
<span>{"RS " + productPrice}</span>
</div>
<div class="w-[20%] flex justify-center">
<span>
{created_at}
</span>
</div>
<div class="w-[20%] flex justify-end">
<OrderStatus status={status} />
</div>
</li>
);
};

function AdminOrders() {
const [isLoading, setIsLoading] = useState(true);
const [orders, setOrders] = useState<Order[]>();
const [limit, setLimit] = useState<number>();
const [hasNextPage, setHasNextPage] = useState<boolean>(false);
const [hasPrevPage, setHasPrevPage] = useState<boolean>(false);
const [page, setPage] = useState<number>();
const [totalPages, setTotalPages] = useState<number>();
const [statusSearch, setStatusSearch] = useState("");

useEffect(() => {
setIsLoading(true);

try {
invoke["deco-sites/ecannadeco"].actions.adminGetOrders({
token: localStorage.getItem("AdminAccessToken") || "",
}).then((r) => {
setPage(r.page);
setTotalPages(r.totalPages);
setLimit(r.limit);
setHasNextPage(r.hasNextPage);
setHasPrevPage(r.hasPrevPage);
setOrders(r.docs);

console.log({ r });

setIsLoading(false);
});
} catch (e) {
setIsLoading(false);
alert(
"Não foi possível recuperar Pedidos..",
);
}
}, []); // Passando um array de dependências vazio

const handleGetOrders = (pageParam: number, status?: string) => {
const accessToken = localStorage.getItem("AdminAccessToken") || "";
setIsLoading(true);

try {
invoke["deco-sites/ecannadeco"].actions.adminGetOrders({
token: accessToken,
params: {
status: status,
page: pageParam,
limit: limit || 25,
},
}).then((r) => {
const res = r as { message?: string; errors?: Array<unknown> };
if (res.message) {
throw new Error(res.message);
}
setPage(r.page);
setTotalPages(r.totalPages);
setLimit(r.limit);
setHasNextPage(r.hasNextPage);
setHasPrevPage(r.hasPrevPage);
console.log({ docs: r.docs });
setOrders(r.docs);
setIsLoading(false);
});
} catch (e) {
alert(
"Não foi possível carregar usuários. Tente novamente mais tarde ou contecte o suporte.",
);
setIsLoading(false);
}
};

return (
<PageWrap>
{isLoading
? <span class="loading loading-spinner text-green-600"></span>
: (
<div class="flex flex-col gap-5 w-full">
<div class="flex justify-center">
<h3 class="text-2xl text-[#8b8b8b] font-semibold text-center">
Pedidos Do Sistema
</h3>
</div>
<div class="my-5">
<select
value={statusSearch}
onChange={(e) => {
setStatusSearch(e.currentTarget.value);
handleGetOrders(1, e.currentTarget.value);
}}
class="select select-primary h-[35px] rounded-full max-w-xs text-[#8b8b8b] border-none disabled:bg-[#e3e3e3] bg-white"
>
<option disabled selected>Selecione o Status</option>
<option value="">Todos</option>
<option value="PAID">Pago</option>
<option value="PENDING">Pendente</option>
<option value="CANCELED">Cancelado</option>
<option value="IN_PRODUCTION">Em Produção</option>
<option value="PENDING_SHIPPING">Envio Pendente</option>
<option value="SHIPPED">Enviado</option>
<option value="DELIVERED">Entregue</option>
</select>
</div>
<div>
<div class="flex pb-2 px-2 border-b border-[#cdcdcd] mb-4">
<div class="w-[40%] flex justify-start">
<span class="text-xs">Paciente</span>
</div>
<div class="w-[20%] flex justify-start">
<span class="text-xs">Produto</span>
</div>
<div class="w-[20%] flex justify-center">
<span class="text-xs">
Data
</span>
</div>
<div class="w-[20%] flex justify-end">
<span class="text-xs">Status</span>
</div>
</div>
<ul class="flex flex-col gap-2">
{orders && orders.map((o) => {
return (
<OrderItem
userEmail={o.user_data?.email || ""}
productName={o.items[0].sku.name}
productPrice={(o.value / 100).toFixed(2)}
created_at={format(new Date(o.created_at), "dd/MM/yyyy")}
status={o.status}
/>
);
})}
</ul>
{/* pagination */}
<div class="flex justify-center mt-4">
<div>
{hasPrevPage && (
<Icon
onClick={() => handleGetOrders(page! - 1)}
id="ChevronLeft"
size={19}
/>
)}
</div>
<div>
<span class="text-xs">
{`Página ${page}/${totalPages}`}
</span>
</div>
<div>
{hasNextPage && (
<Icon
onClick={() => handleGetOrders(page! + 1)}
id="ChevronRight"
size={19}
/>
)}
</div>
</div>
</div>
</div>
)}
</PageWrap>
);
}

export default AdminOrders;
Loading

0 comments on commit 8a50d00

Please sign in to comment.