From d582e222ce5fd1fe58de223a83e464ec634a2d90 Mon Sep 17 00:00:00 2001 From: k4rli Date: Mon, 11 Aug 2025 09:21:40 +0300 Subject: [PATCH] feat(MED-105): update order details redirect and shown page --- .../cart/montonio-callback/actions.ts | 4 +- .../montonio-callback/client-component.tsx | 4 +- .../cart/montonio-callback/page.tsx | 1 - .../order/[orderId]/confirmed/page.tsx | 43 +++++++++++---- .../(dashboard)/order/[orderId]/page.tsx | 52 +++++++++++++++++++ app/home/(user)/(dashboard)/order/page.tsx | 33 ++++++++++-- .../(user)/_components/order/cart-totals.tsx | 6 +-- .../_components/order/order-completed.tsx | 27 ---------- .../_components/order/order-details.tsx | 38 +++----------- .../(user)/_components/order/order-item.tsx | 7 +-- .../(user)/_components/order/order-items.tsx | 8 +-- .../(user)/_components/orders/orders-item.tsx | 11 ++-- .../_components/orders/orders-table.tsx | 9 ++-- app/home/(user)/_components/orders/types.ts | 3 +- lib/services/order.service.ts | 16 +++++- public/locales/en/cart.json | 3 ++ public/locales/en/orders.json | 11 +++- public/locales/et/cart.json | 3 ++ public/locales/et/orders.json | 11 +++- 19 files changed, 185 insertions(+), 105 deletions(-) create mode 100644 app/home/(user)/(dashboard)/order/[orderId]/page.tsx delete mode 100644 app/home/(user)/_components/order/order-completed.tsx diff --git a/app/home/(user)/(dashboard)/cart/montonio-callback/actions.ts b/app/home/(user)/(dashboard)/cart/montonio-callback/actions.ts index e48ac85..63a9bb9 100644 --- a/app/home/(user)/(dashboard)/cart/montonio-callback/actions.ts +++ b/app/home/(user)/(dashboard)/cart/montonio-callback/actions.ts @@ -91,7 +91,7 @@ export async function processMontonioCallback(orderToken: string) { const medusaOrder = await placeOrder(cartId, { revalidateCacheTags: false }); const orderedAnalysisElements = await getOrderedAnalysisElementsIds({ medusaOrder }); - await createOrder({ medusaOrder, orderedAnalysisElements }); + const orderId = await createOrder({ medusaOrder, orderedAnalysisElements }); const { productTypes } = await listProductTypes(); const analysisPackagesType = productTypes.find(({ metadata }) => metadata?.handle === ANALYSIS_PACKAGES_TYPE_HANDLE); @@ -122,7 +122,7 @@ export async function processMontonioCallback(orderToken: string) { // Send order to Medipost (no await to avoid blocking) sendOrderToMedipost({ medusaOrderId, orderedAnalysisElements }); - return { success: true }; + return { success: true, orderId }; } catch (error) { console.error("Failed to place order", error); throw new Error(`Failed to place order, message=${error}`); diff --git a/app/home/(user)/(dashboard)/cart/montonio-callback/client-component.tsx b/app/home/(user)/(dashboard)/cart/montonio-callback/client-component.tsx index f90efa4..c388a6d 100644 --- a/app/home/(user)/(dashboard)/cart/montonio-callback/client-component.tsx +++ b/app/home/(user)/(dashboard)/cart/montonio-callback/client-component.tsx @@ -29,8 +29,8 @@ export default function MontonioCallbackClient({ orderToken, error }: { setHasProcessed(true); try { - await processMontonioCallback(orderToken); - router.push('/home/order'); + const { orderId } = await processMontonioCallback(orderToken); + router.push(`/home/order/${orderId}/confirmed`); } catch (error) { console.error("Failed to place order", error); router.push('/home/cart/montonio-callback/error'); diff --git a/app/home/(user)/(dashboard)/cart/montonio-callback/page.tsx b/app/home/(user)/(dashboard)/cart/montonio-callback/page.tsx index 6893a97..d4f54f4 100644 --- a/app/home/(user)/(dashboard)/cart/montonio-callback/page.tsx +++ b/app/home/(user)/(dashboard)/cart/montonio-callback/page.tsx @@ -7,7 +7,6 @@ export default async function MontonioCallbackPage({ searchParams }: { }) { const orderToken = (await searchParams)['order-token']; - console.log('orderToken', orderToken); if (!orderToken) { return ; } diff --git a/app/home/(user)/(dashboard)/order/[orderId]/confirmed/page.tsx b/app/home/(user)/(dashboard)/order/[orderId]/confirmed/page.tsx index 2ca1b55..f49e5cb 100644 --- a/app/home/(user)/(dashboard)/order/[orderId]/confirmed/page.tsx +++ b/app/home/(user)/(dashboard)/order/[orderId]/confirmed/page.tsx @@ -1,13 +1,16 @@ -import { notFound } from 'next/navigation'; +import { redirect } from 'next/navigation'; +import { PageBody, PageHeader } from '@kit/ui/page'; -import { retrieveOrder } from '~/medusa/lib/data/orders'; import { createI18nServerInstance } from '@/lib/i18n/i18n.server'; -import OrderCompleted from '@/app/home/(user)/_components/order/order-completed'; import { withI18n } from '~/lib/i18n/with-i18n'; - -type Props = { - params: Promise<{ orderId: string }>; -}; +import { getOrder } from '~/lib/services/order.service'; +import { retrieveOrder } from '@lib/data/orders'; +import pathsConfig from '~/config/paths.config'; +import Divider from "@modules/common/components/divider" +import OrderDetails from '@/app/home/(user)/_components/order/order-details'; +import OrderItems from '@/app/home/(user)/_components/order/order-items'; +import CartTotals from '@/app/home/(user)/_components/order/cart-totals'; +import { Trans } from '@kit/ui/trans'; export async function generateMetadata() { const { t } = await createI18nServerInstance(); @@ -17,15 +20,33 @@ export async function generateMetadata() { }; } -async function OrderConfirmedPage(props: Props) { +async function OrderConfirmedPage(props: { + params: Promise<{ orderId: string }>; +}) { const params = await props.params; - const order = await retrieveOrder(params.orderId).catch(() => null); + const order = await getOrder({ orderId: Number(params.orderId) }).catch(() => null); if (!order) { - return notFound(); + redirect(pathsConfig.app.myOrders); } - return ; + const medusaOrder = await retrieveOrder(order.medusa_order_id).catch(() => null); + if (!medusaOrder) { + redirect(pathsConfig.app.myOrders); + } + + return ( + + } /> + +
+ + + + +
+
+ ); } export default withI18n(OrderConfirmedPage); diff --git a/app/home/(user)/(dashboard)/order/[orderId]/page.tsx b/app/home/(user)/(dashboard)/order/[orderId]/page.tsx new file mode 100644 index 0000000..b9e8597 --- /dev/null +++ b/app/home/(user)/(dashboard)/order/[orderId]/page.tsx @@ -0,0 +1,52 @@ +import { redirect } from 'next/navigation'; +import { PageBody, PageHeader } from '@kit/ui/page'; + +import { createI18nServerInstance } from '@/lib/i18n/i18n.server'; +import { withI18n } from '~/lib/i18n/with-i18n'; +import { getOrder } from '~/lib/services/order.service'; +import { retrieveOrder } from '@lib/data/orders'; +import pathsConfig from '~/config/paths.config'; +import Divider from "@modules/common/components/divider" +import OrderDetails from '@/app/home/(user)/_components/order/order-details'; +import OrderItems from '@/app/home/(user)/_components/order/order-items'; +import CartTotals from '@/app/home/(user)/_components/order/cart-totals'; +import { Trans } from '@kit/ui/trans'; + +export async function generateMetadata() { + const { t } = await createI18nServerInstance(); + + return { + title: t('cart:order.title'), + }; +} + +async function OrderConfirmedPage(props: { + params: Promise<{ orderId: string }>; +}) { + const params = await props.params; + + const order = await getOrder({ orderId: Number(params.orderId) }).catch(() => null); + if (!order) { + redirect(pathsConfig.app.myOrders); + } + + const medusaOrder = await retrieveOrder(order.medusa_order_id).catch(() => null); + if (!medusaOrder) { + redirect(pathsConfig.app.myOrders); + } + + return ( + + } /> + +
+ + + + +
+
+ ); +} + +export default withI18n(OrderConfirmedPage); diff --git a/app/home/(user)/(dashboard)/order/page.tsx b/app/home/(user)/(dashboard)/order/page.tsx index 97144af..7b038fe 100644 --- a/app/home/(user)/(dashboard)/order/page.tsx +++ b/app/home/(user)/(dashboard)/order/page.tsx @@ -10,6 +10,7 @@ import { HomeLayoutPageHeader } from '../../_components/home-page-header'; import OrdersTable from '../../_components/orders/orders-table'; import { withI18n } from '~/lib/i18n/with-i18n'; import type { IOrderLineItem } from '../../_components/orders/types'; +import { getOrders } from '~/lib/services/order.service'; export async function generateMetadata() { const { t } = await createI18nServerInstance(); @@ -20,7 +21,8 @@ export async function generateMetadata() { } async function OrdersPage() { - const orders = await listOrders().catch(() => null); + const orders = await listOrders(); + const localOrders = await getOrders(); const { productTypes } = await listProductTypes(); if (!orders || !productTypes) { @@ -30,13 +32,38 @@ async function OrdersPage() { const analysisPackagesType = productTypes.find(({ metadata }) => metadata?.handle === 'analysis-packages'); const analysisPackageOrders: IOrderLineItem[] = orders.flatMap(({ id, items, payment_status, fulfillment_status }) => items ?.filter((item) => item.product_type_id === analysisPackagesType?.id) - .map((item) => ({ item, orderId: id, orderStatus: `${payment_status}/${fulfillment_status}` })) + .map((item) => { + const localOrder = localOrders.find((order) => order.medusa_order_id === id); + if (!localOrder) { + return null; + } + return { + item, + medusaOrderId: id, + orderId: localOrder?.id, + orderStatus: localOrder.status, + analysis_element_ids: localOrder.analysis_element_ids, + } + }) + .filter((order) => order !== null) || []); const otherOrders: IOrderLineItem[] = orders .filter(({ items }) => items?.some((item) => item.product_type_id !== analysisPackagesType?.id)) .flatMap(({ id, items, payment_status, fulfillment_status }) => items - ?.map((item) => ({ item, orderId: id, orderStatus: `${payment_status}/${fulfillment_status}` })) + ?.map((item) => { + const localOrder = localOrders.find((order) => order.medusa_order_id === id); + if (!localOrder) { + return null; + } + return { + item, + medusaOrderId: id, + orderId: localOrder.id, + orderStatus: localOrder.status, + } + }) + .filter((order) => order !== null) || []); return ( diff --git a/app/home/(user)/_components/order/cart-totals.tsx b/app/home/(user)/_components/order/cart-totals.tsx index dc25aad..2df2237 100644 --- a/app/home/(user)/_components/order/cart-totals.tsx +++ b/app/home/(user)/_components/order/cart-totals.tsx @@ -6,8 +6,8 @@ import React from "react" import { useTranslation } from "react-i18next" import { Trans } from '@kit/ui/trans'; -export default function CartTotals({ order }: { - order: StoreOrder +export default function CartTotals({ medusaOrder }: { + medusaOrder: StoreOrder }) { const { i18n: { language } } = useTranslation() const { @@ -17,7 +17,7 @@ export default function CartTotals({ order }: { tax_total, discount_total, gift_card_total, - } = order + } = medusaOrder return (
diff --git a/app/home/(user)/_components/order/order-completed.tsx b/app/home/(user)/_components/order/order-completed.tsx deleted file mode 100644 index f7529a0..0000000 --- a/app/home/(user)/_components/order/order-completed.tsx +++ /dev/null @@ -1,27 +0,0 @@ -import { Trans } from '@kit/ui/trans'; -import { PageBody, PageHeader } from '@kit/ui/page'; -import { StoreOrder } from "@medusajs/types" -import Divider from "@modules/common/components/divider" - -import CartTotals from "./cart-totals" -import OrderDetails from "./order-details" -import OrderItems from "./order-items" - -export default async function OrderCompleted({ - order, -}: { - order: StoreOrder, -}) { - return ( - - } /> - -
- - - - -
-
- ) -} diff --git a/app/home/(user)/_components/order/order-details.tsx b/app/home/(user)/_components/order/order-details.tsx index e6bc6cf..b750c85 100644 --- a/app/home/(user)/_components/order/order-details.tsx +++ b/app/home/(user)/_components/order/order-details.tsx @@ -1,47 +1,21 @@ -import { StoreOrder } from "@medusajs/types" import { Trans } from '@kit/ui/trans'; +import { formatDate } from 'date-fns'; +import { AnalysisOrder } from "~/lib/services/order.service"; -export default function OrderDetails({ order, showStatus }: { - order: StoreOrder - showStatus?: boolean +export default function OrderDetails({ order }: { + order: AnalysisOrder }) { - const formatStatus = (str: string) => { - const formatted = str.split("_").join(" ") - - return formatted.slice(0, 1).toUpperCase() + formatted.slice(1) - } - return (
:{" "} - {new Date(order.created_at).toLocaleDateString()} + {formatDate(order.created_at, 'dd.MM.yyyy HH:mm')} - : {order.display_id} + : {order.medusa_order_id} - - {showStatus && ( - <> - - :{" "} - - {formatStatus(order.fulfillment_status)} - - - - :{" "} - - {formatStatus(order.payment_status)} - - - - )}
) } diff --git a/app/home/(user)/_components/order/order-item.tsx b/app/home/(user)/_components/order/order-item.tsx index 4cd4e7a..cad98e6 100644 --- a/app/home/(user)/_components/order/order-item.tsx +++ b/app/home/(user)/_components/order/order-item.tsx @@ -1,7 +1,7 @@ import { StoreCartLineItem, StoreOrderLineItem } from "@medusajs/types" import { TableCell, TableRow } from "@kit/ui/table" -import LineItemOptions from "@modules/common/components/line-item-options" +// import LineItemOptions from "@modules/common/components/line-item-options" import LineItemPrice from "@modules/common/components/line-item-price" import LineItemUnitPrice from "@modules/common/components/line-item-unit-price" @@ -9,6 +9,7 @@ export default function OrderItem({ item, currencyCode }: { item: StoreCartLineItem | StoreOrderLineItem currencyCode: string }) { + const partnerLocationName = item.metadata?.partner_location_name; return ( {/* @@ -22,9 +23,9 @@ export default function OrderItem({ item, currencyCode }: { className="txt-medium-plus text-ui-fg-base" data-testid="product-name" > - {item.product_title}{` (${item.metadata?.partner_location_name ?? "-"})`} + {item.product_title}{` ${partnerLocationName ? `(${partnerLocationName})` : ''}`} - + {/* */} diff --git a/app/home/(user)/_components/order/order-items.tsx b/app/home/(user)/_components/order/order-items.tsx index 25dbe31..5375314 100644 --- a/app/home/(user)/_components/order/order-items.tsx +++ b/app/home/(user)/_components/order/order-items.tsx @@ -7,10 +7,10 @@ import OrderItem from "./order-item" import { Heading } from "@kit/ui/heading" import { Trans } from '@kit/ui/trans'; -export default function OrderItems({ order }: { - order: StoreOrder +export default function OrderItems({ medusaOrder }: { + medusaOrder: StoreOrder }) { - const items = order.items + const items = medusaOrder.items return (
@@ -27,7 +27,7 @@ export default function OrderItems({ order }: { )) : repeat(5).map((i) => )} diff --git a/app/home/(user)/_components/orders/orders-item.tsx b/app/home/(user)/_components/orders/orders-item.tsx index 2d80f7d..ea8943d 100644 --- a/app/home/(user)/_components/orders/orders-item.tsx +++ b/app/home/(user)/_components/orders/orders-item.tsx @@ -6,6 +6,7 @@ import { Eye } from "lucide-react"; import Link from "next/link"; import { formatDate } from "date-fns"; import { IOrderLineItem } from "./types"; +import { Trans } from '@kit/ui/trans'; export default function OrdersItem({ orderItem }: { orderItem: IOrderLineItem, @@ -22,15 +23,13 @@ export default function OrdersItem({ orderItem }: { {formatDate(orderItem.item.created_at, 'dd.MM.yyyy HH:mm')} - {orderItem.orderStatus && ( - - {orderItem.orderStatus} - - )} + + + - +