hey-pharmacist-ecommerce 1.1.35 → 1.1.36
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/index.js +13 -10
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +13 -10
- package/dist/index.mjs.map +1 -1
- package/package.json +1 -1
- package/src/components/AccountOrdersTab.tsx +3 -1
- package/src/components/CartItem.tsx +6 -2
- package/src/components/OrderCard.tsx +3 -1
- package/src/components/ProductCard.tsx +6 -1
- package/src/lib/constants/assets.ts +1 -0
- package/src/screens/CheckoutScreen.tsx +6 -4
- package/src/screens/OrderDetailScreen.tsx +5 -1
- package/src/screens/ProductDetailScreen.tsx +3 -1
- package/src/screens/ShopScreen.tsx +3 -1
- package/src/screens/WishlistScreen.tsx +3 -1
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "hey-pharmacist-ecommerce",
|
|
3
|
-
"version": "1.1.
|
|
3
|
+
"version": "1.1.36",
|
|
4
4
|
"description": "Production-ready, multi-tenant e‑commerce UI + API adapter for Next.js with auth, carts, checkout, orders, theming, and pharmacist-focused UX.",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"module": "dist/index.mjs",
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React from 'react';
|
|
4
6
|
import { Package, Truck } from 'lucide-react';
|
|
5
7
|
import { useCurrentOrders } from '@/hooks/useOrders';
|
|
@@ -102,7 +104,7 @@ export function AccountOrdersTab() {
|
|
|
102
104
|
<div key={item.productVariantId || index} className="flex items-center gap-3">
|
|
103
105
|
<div className="relative w-12 h-12 rounded-lg bg-slate-100 shrink-0 overflow-hidden">
|
|
104
106
|
<Image
|
|
105
|
-
src={item?.productVariantData?.media?.[0]?.file ||
|
|
107
|
+
src={item?.productVariantData?.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
106
108
|
alt={item?.productVariantData?.name || 'Product image'}
|
|
107
109
|
fill
|
|
108
110
|
className="object-cover"
|
|
@@ -1,8 +1,11 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React, { useState } from 'react';
|
|
4
6
|
import { motion } from 'framer-motion';
|
|
5
7
|
import { Minus, Plus, Trash2 } from 'lucide-react';
|
|
8
|
+
|
|
6
9
|
import { formatPrice } from '@/lib/utils/format';
|
|
7
10
|
import { useCart } from '@/providers/CartProvider';
|
|
8
11
|
import Image from 'next/image';
|
|
@@ -52,10 +55,11 @@ export function CartItem({ item }: CartItemProps) {
|
|
|
52
55
|
|
|
53
56
|
|
|
54
57
|
<div className="flex gap-4 pr-8">
|
|
55
|
-
|
|
58
|
+
|
|
59
|
+
|
|
56
60
|
<div className="w-28 h-28 rounded-[16px] overflow-hidden bg-gray-50 shrink-0">
|
|
57
61
|
<Image
|
|
58
|
-
src={item.productVariantData.media[0]?.file ||
|
|
62
|
+
src={item.productVariantData.media[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
59
63
|
alt={item.productVariantData.name}
|
|
60
64
|
className="w-full h-full object-cover"
|
|
61
65
|
height={112}
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React, { useRef, useState } from 'react';
|
|
4
6
|
import { motion, useMotionValue, useTransform } from 'framer-motion';
|
|
5
7
|
import { CreditCard, Star, Trash2 } from 'lucide-react';
|
|
@@ -106,7 +108,7 @@ export function OrderCard({ order, onDelete }: OrderCardProps) {
|
|
|
106
108
|
<div key={item.productVariantId || item._id} className="flex items-center gap-2 text-sm">
|
|
107
109
|
<div className="relative w-12 h-12 rounded-sm bg-gray-100 shrink-0 overflow-hidden">
|
|
108
110
|
<Image
|
|
109
|
-
src={item?.productVariantData?.media?.[0]?.file ||
|
|
111
|
+
src={item?.productVariantData?.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
110
112
|
alt={item?.productVariantData?.name || 'Product image'}
|
|
111
113
|
fill
|
|
112
114
|
className="object-cover"
|
|
@@ -13,6 +13,7 @@ import { useBasePath } from '@/providers/BasePathProvider';
|
|
|
13
13
|
import { QuickViewModal } from './QuickViewModal';
|
|
14
14
|
import { useNotification } from '@/providers/NotificationProvider';
|
|
15
15
|
import { useAuth } from '@/providers/AuthProvider';
|
|
16
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
16
17
|
|
|
17
18
|
interface ProductCardProps {
|
|
18
19
|
product: Product;
|
|
@@ -157,8 +158,12 @@ export function ProductCard({
|
|
|
157
158
|
return selectedVariant ? selectedVariant.inventoryCount : product.variants?.[0]?.inventoryCount;
|
|
158
159
|
}, [selectedVariant, product.variants]);
|
|
159
160
|
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
// ... (inside component)
|
|
164
|
+
|
|
160
165
|
const imageSource = useMemo(() => {
|
|
161
|
-
const src = selectedVariantImage || selectedVariant?.media?.[0]?.file || product.media?.[0]?.file ||
|
|
166
|
+
const src = selectedVariantImage || selectedVariant?.media?.[0]?.file || product.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC;
|
|
162
167
|
return {
|
|
163
168
|
src,
|
|
164
169
|
alt: product.name || 'Product image'
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const PLACEHOLDER_IMAGE_SRC = `data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iNDAwIiBoZWlnaHQ9IjQwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KICA8cmVjdCB3aWR0aD0iMTAwJSIgaGVpZ2h0PSIxMDAlIiBmaWxsPSIjZjNmNGY2Ii8+CiAgPHRleHQgeD0iNTAlIiB5PSI1MCUiIGZvbnQtZmFtaWx5PSJBcmlhbCIgZm9udC1zaXplPSIyNCIgZmlsbD0iIzljYTNhZiIgdGV4dC1hbmNob3I9Im1pZGRsZSIgZG9taW5hbnQtYmFzZWxpbmU9Im1pZGRsZSI+Tm8gSW1hZ2U8L3RleHQ+CiAgPHJlY3QgeD0iMTUwIiB5PSIxMjAiIHdpZHRoPSIxMDAiIGhlaWdodD0iMTAwIiBzdHJva2U9IiM5Y2EzYWYiIHN0cm9rZS13aWR0aD0iNCIgZmlsbD0ibm9uZSIgcng9IjgiLz4KICA8cGF0aCBkPSJNMTUwIDE4MCBMMTcwIDE2MCBMMjAwIDE5MCBMMjIwIDE3MCBMMjUwIDIwMCBMMjUwIDIyMCBMMTUwIDIyMCBaIiBmaWxsPSIjOWNhM2FmIiBvcGFjaXR5PSIwLjUiLz4KPC9zdmc+`;
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React, { useState, useEffect } from 'react';
|
|
4
6
|
import { motion } from 'framer-motion';
|
|
5
7
|
import { useForm } from 'react-hook-form';
|
|
@@ -868,7 +870,7 @@ export function CheckoutScreen() {
|
|
|
868
870
|
{/* Provider Logo */}
|
|
869
871
|
<div className="shrink-0">
|
|
870
872
|
<Image
|
|
871
|
-
src={rate.providerImage75 ||
|
|
873
|
+
src={rate.providerImage75 || PLACEHOLDER_IMAGE_SRC}
|
|
872
874
|
alt={rate.provider}
|
|
873
875
|
className="w-12 h-12 rounded-lg object-contain bg-white border border-gray-200 p-1"
|
|
874
876
|
onError={(e: any) => {
|
|
@@ -987,7 +989,7 @@ export function CheckoutScreen() {
|
|
|
987
989
|
{cart?.cartBody?.items?.map((item: any) => (
|
|
988
990
|
<div key={item.productVariantId || item.id} className="flex gap-3">
|
|
989
991
|
<div className="w-16 h-16 rounded-xl overflow-hidden bg-white shrink-0">
|
|
990
|
-
<Image src={item.productVariantData?.media?.[0]?.file ||
|
|
992
|
+
<Image src={item.productVariantData?.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC} alt={item.productVariantData.name} className="w-full h-full object-cover" height={200} width={200} />
|
|
991
993
|
</div>
|
|
992
994
|
<div className="flex-1 min-w-0">
|
|
993
995
|
<p className="font-['Poppins',sans-serif] font-medium text-[12px] text-[#2B4B7C] mb-1">
|
|
@@ -1008,8 +1010,8 @@ export function CheckoutScreen() {
|
|
|
1008
1010
|
|
|
1009
1011
|
{/* Coupon Code Section */}
|
|
1010
1012
|
<div className="mb-6">
|
|
1011
|
-
<CouponCodeInput
|
|
1012
|
-
userId={user?.id}
|
|
1013
|
+
<CouponCodeInput
|
|
1014
|
+
userId={user?.id}
|
|
1013
1015
|
className="mb-4"
|
|
1014
1016
|
/>
|
|
1015
1017
|
</div>
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React from 'react';
|
|
4
6
|
import { motion } from 'framer-motion';
|
|
5
7
|
import {
|
|
@@ -143,9 +145,11 @@ export function OrderDetailScreen({ id }: OrderDetailScreenProps) {
|
|
|
143
145
|
<div className="divide-y divide-slate-100">
|
|
144
146
|
{items.map((item, idx) => (
|
|
145
147
|
<div key={item._id || idx} className="p-6 flex gap-6 group hover:bg-slate-50/50 transition-colors">
|
|
148
|
+
|
|
149
|
+
|
|
146
150
|
<div className="relative w-20 h-20 bg-slate-100 rounded-2xl overflow-hidden shrink-0 border border-slate-100 group-hover:scale-105 transition-transform duration-300">
|
|
147
151
|
<Image
|
|
148
|
-
src={item.productVariantData?.media?.[0]?.file ||
|
|
152
|
+
src={item.productVariantData?.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
149
153
|
alt={item.productVariantData?.name || 'Item'}
|
|
150
154
|
fill
|
|
151
155
|
className="object-cover"
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React, { useEffect, useState, useMemo } from 'react';
|
|
4
6
|
import { motion } from 'framer-motion';
|
|
5
7
|
import {
|
|
@@ -555,7 +557,7 @@ export function ProductDetailScreen({ productId }: ProductDetailScreenProps) {
|
|
|
555
557
|
const variantImage = variant.media?.[0]?.file
|
|
556
558
|
|| product.media?.[0]?.file
|
|
557
559
|
|| product.images?.[0]
|
|
558
|
-
||
|
|
560
|
+
|| PLACEHOLDER_IMAGE_SRC;
|
|
559
561
|
return (
|
|
560
562
|
<button
|
|
561
563
|
key={variant._id}
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import {
|
|
4
6
|
useCallback,
|
|
5
7
|
useEffect,
|
|
@@ -1126,7 +1128,7 @@ export function ShopScreen({ initialFilters = {}, categoryName }: ShopScreenProp
|
|
|
1126
1128
|
>
|
|
1127
1129
|
<div className="relative h-48 w-full overflow-hidden rounded-2xl bg-gray-100 md:h-40 md:w-40">
|
|
1128
1130
|
<Image
|
|
1129
|
-
src={product.media?.[0]?.file ||
|
|
1131
|
+
src={product.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
1130
1132
|
alt={product.name}
|
|
1131
1133
|
fill
|
|
1132
1134
|
className="object-cover transition duration-500 group-hover:scale-105"
|
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
|
|
3
|
+
import { PLACEHOLDER_IMAGE_SRC } from '@/lib/constants/assets';
|
|
4
|
+
|
|
3
5
|
import React, { useEffect, useMemo, useState } from 'react';
|
|
4
6
|
import { motion, AnimatePresence } from 'framer-motion';
|
|
5
7
|
import {
|
|
@@ -347,7 +349,7 @@ export default function WishlistScreen() {
|
|
|
347
349
|
<div className="relative h-28 w-full overflow-hidden rounded-2xl bg-white sm:w-40">
|
|
348
350
|
<Image
|
|
349
351
|
fill
|
|
350
|
-
src={product.media?.[0]?.file ||
|
|
352
|
+
src={product.media?.[0]?.file || PLACEHOLDER_IMAGE_SRC}
|
|
351
353
|
alt={product.name || 'Wishlist item'}
|
|
352
354
|
className="h-full w-full object-cover"
|
|
353
355
|
/>
|