Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: added Pagination for Wishlist #893

Open
wants to merge 6 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 3 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
6 changes: 6 additions & 0 deletions .changeset/light-cows-protect.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"vue-demo-store": minor
"@shopware-pwa/composables-next": patch
---

I added a paginatin for order history page.
6 changes: 6 additions & 0 deletions .changeset/tough-queens-swim.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
---
"vue-demo-store": minor
"@shopware-pwa/composables-next": patch
---

I have added a pagination for wishlist page. I made a changes to variable name to get the proper context of it.
41 changes: 36 additions & 5 deletions packages/composables/src/useCustomerOrders.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { ref } from "vue";
import type { Ref } from "vue";
import { ref, computed } from "vue";
import type { Ref, ComputedRef } from "vue";
import { useShopwareContext } from "#imports";
import type { Schemas } from "#shopware";

Expand All @@ -13,11 +13,22 @@ export type UseCustomerOrdersReturn = {
*
* In order to change a page with additional parameters please use `loadOrders` method.
*/
changeCurrentPage(pageNumber: number | string): Promise<void>;
changeCurrentPage(
pageNumber: number | string,
limit: number | string,
): Promise<void>;
/**
* Fetches the orders list and assigns the result to the `orders` property
*/
loadOrders(parameters?: Schemas["Criteria"]): Promise<void>;
/**
* Current page number
*/
getCurrentPage: ComputedRef<number>;
/**
* total pages count
*/
getTotalPagesCount: ComputedRef<number>;
};

/**
Expand All @@ -30,6 +41,12 @@ export function useCustomerOrders(): UseCustomerOrdersReturn {

const orders: Ref<Schemas["Order"][]> = ref([]);

const currentPage = ref<number>(1);

const totalOrderItemsCount: Ref<number> = ref(0);

const limit = ref<number>(15);

const loadOrders = async (
parameters: Schemas["Criteria"] = {},
): Promise<void> => {
Expand All @@ -38,14 +55,28 @@ export function useCustomerOrders(): UseCustomerOrdersReturn {
parameters,
);
orders.value = fetchedOrders.orders.elements;
totalOrderItemsCount.value = fetchedOrders.orders.total!;
};

const changeCurrentPage = async (pageNumber: number | string) =>
await loadOrders({ page: +pageNumber });
const changeCurrentPage = async (
pageNumber: number | string,
currentLimit: string | number,
) => {
limit.value = +currentLimit;
await loadOrders({ page: +pageNumber, limit: +currentLimit });
};

const getCurrentPage = computed(() => currentPage.value);

const getTotalPagesCount = computed(() =>
Math.ceil(totalOrderItemsCount.value / +limit.value),
);

return {
orders,
changeCurrentPage,
loadOrders,
getCurrentPage,
getTotalPagesCount,
};
}
4 changes: 2 additions & 2 deletions packages/composables/src/useSyncWishlist.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@
vm.getWishlistProducts();
vm.removeFromWishlistSync("some-id");
// Mocked value
expect(vm.count).toBe(vm.count);
expect(vm.totalWishlistItemsCount).toBe(vm.totalWishlistItemsCount);
});
});

Expand All @@ -38,7 +38,7 @@
const { vm } = useSetup(() => useSyncWishlist());

vm.getWishlistProducts();
expect(vm.count).toBe(0);
expect(vm.totalWishlistItemsCount).toBe(0);

Check failure on line 41 in packages/composables/src/useSyncWishlist.test.ts

View workflow job for this annotation

GitHub Actions / Test

src/useSyncWishlist.test.ts > useSyncWishlist > methods > getWishlistProducts > getWishlistProducts

AssertionError: expected 15 to be +0 // Object.is equality - Expected + Received - 0 + 15 ❯ src/useSyncWishlist.test.ts:41:44
expect(vm.items.length).toBe(0);
});
});
Expand Down
19 changes: 12 additions & 7 deletions packages/composables/src/useSyncWishlist.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,15 @@ import { ref, computed } from "vue";
import type { Ref, ComputedRef } from "vue";
import { useShopwareContext } from "#imports";
import { ApiClientError } from "@shopware/api-client";
import type { RequestParameters } from "#shopware";

export type UseSyncWishlistReturn = {
/**
* Get products from wishlist
*/
getWishlistProducts(): void;
getWishlistProducts(
defaultPaginationCriteria?: RequestParameters<"searchPage">,
): void;
/**
* Merge products with wishlist already existing in API wishlist
*/
Expand All @@ -27,10 +30,11 @@ export type UseSyncWishlistReturn = {
/**
* Wishlist items count
*/
count: ComputedRef<number>;
totalWishlistItemsCount: Ref<number>;
};

const _wishlistItems: Ref<string[]> = ref([]);
const totalWishlistItemsCount: Ref<number> = ref(15);

/**
* Composable to manage wishlist via API
Expand All @@ -39,7 +43,6 @@ const _wishlistItems: Ref<string[]> = ref([]);
*/
export function useSyncWishlist(): UseSyncWishlistReturn {
const { apiClient } = useShopwareContext();

async function addToWishlistSync(id: string) {
await apiClient.invoke(
"addProductOnWishlist post /customer/wishlist/add/{productId}",
Expand All @@ -62,15 +65,18 @@ export function useSyncWishlist(): UseSyncWishlistReturn {
* Fetch wishlist items
* Only for logged-in users
*/
async function getWishlistProducts() {
async function getWishlistProducts(
defaultSearchCriteria?: RequestParameters<"searchPage">,
) {
try {
const response = await apiClient.invoke(
"readCustomerWishlist post /customer/wishlist",
{},
{ ...defaultSearchCriteria },
);
_wishlistItems.value = [
...response.products.elements.map((element) => element.id),
];
totalWishlistItemsCount.value = response.products.total!;
} catch (e) {
if (e instanceof ApiClientError) {
// If 404 ignore printing error and reset wishlist
Expand All @@ -90,14 +96,13 @@ export function useSyncWishlist(): UseSyncWishlistReturn {
}

const items = computed(() => _wishlistItems.value);
const count = computed(() => items.value.length);

return {
getWishlistProducts,
addToWishlistSync,
removeFromWishlistSync,
mergeWishlistProducts,
items,
count,
totalWishlistItemsCount,
};
}
4 changes: 2 additions & 2 deletions packages/composables/src/useWishlist.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
const { vm } = useSetup(() => useWishlist());

expect(vm.items.length).toBe(1);
expect(vm.count).toBe(1);
expect(vm.totalWishlistItemsCount).toBe(1);

Check failure on line 20 in packages/composables/src/useWishlist.test.ts

View workflow job for this annotation

GitHub Actions / Test

src/useWishlist.test.ts > useWishlist - not logged in user > mergeWishlistProducts

AssertionError: expected 15 to be 1 // Object.is equality - Expected + Received - 1 + 15 ❯ src/useWishlist.test.ts:20:40
await vm.clearWishlist();
await vm.getWishlistProducts();
await vm.mergeWishlistProducts();
Expand All @@ -29,7 +29,7 @@
const { vm } = useSetup(() => useWishlist());

expect(vm.items.length).toBe(1);
expect(vm.count).toBe(1);
expect(vm.totalWishlistItemsCount).toBe(1);

Check failure on line 32 in packages/composables/src/useWishlist.test.ts

View workflow job for this annotation

GitHub Actions / Test

src/useWishlist.test.ts > useWishlist - logged in user > mergeWishlistProducts

AssertionError: expected 15 to be 1 // Object.is equality - Expected + Received - 1 + 15 ❯ src/useWishlist.test.ts:32:40
await vm.clearWishlist();
await vm.getWishlistProducts();
await vm.mergeWishlistProducts();
Expand Down
62 changes: 53 additions & 9 deletions packages/composables/src/useWishlist.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
/**
* Template composable
*/
import { computed } from "vue";
import type { ComputedRef } from "vue";
import { computed, ref } from "vue";
import type { ComputedRef, Ref } from "vue";
import { useUser, useLocalWishlist, useSyncWishlist } from "#imports";
import type { RequestParameters } from "#shopware";

export type UseWishlistReturn = {
/**
Expand All @@ -23,9 +24,26 @@ export type UseWishlistReturn = {
*/
items: ComputedRef<string[]>;
/**
* Wishlist items count
* Changes the current page number
* @param pageNumber - page number to change to
* @returns
*/
count: ComputedRef<number>;
changeCurrentPage(
page: number,
query?: RequestParameters<"searchPage">,
): Promise<void>;
/**
* Current page number
*/
getCurrentPage: ComputedRef<number>;
/**
* total pages count
*/
getTotalPagesCount: ComputedRef<number>;
/**
* total wishlist items count
*/
totalWishlistItemsCount: Ref<number>;
};

/**
Expand All @@ -38,7 +56,6 @@ export function useWishlist(): UseWishlistReturn {
const canSyncWishlist = computed(
() => isLoggedIn.value && !isGuestSession.value,
);

const {
getWishlistProducts: getWishlistProductsLocal,
items: itemsLocal,
Expand All @@ -50,16 +67,39 @@ export function useWishlist(): UseWishlistReturn {
items: itemsSync,
mergeWishlistProducts: mergeWishlistProductsSync,
removeFromWishlistSync,
totalWishlistItemsCount,
} = useSyncWishlist();

const currentPage = ref<number>(1);
const limit = ref<number>(15);

const getWishlistProducts = async () => {
if (canSyncWishlist.value) {
await getWishlistProductsSync();
await getWishlistProductsSync({
page: currentPage.value,
limit: limit.value,
p: currentPage.value,
} as unknown as RequestParameters<"searchPage">);
} else {
await getWishlistProductsLocal();
}
};

const changeCurrentPage = async (
page: number,
query: RequestParameters<"searchPage">,
) => {
currentPage.value = page;
if (query.limit) {
limit.value = +query.limit;
}
await getWishlistProductsSync({ ...query, page });
};

const getTotalPagesCount = computed(() =>
Math.ceil(totalWishlistItemsCount.value / +limit.value),
);

const clearWishlist = async () => {
if (canSyncWishlist.value) {
await Promise.all(items.value.map((id) => removeFromWishlistSync(id)));
Expand All @@ -74,19 +114,23 @@ export function useWishlist(): UseWishlistReturn {
await mergeWishlistProductsSync(itemsLocal.value);
clearWishlist();
}
getWishlistProductsSync();
await getWishlistProductsSync();
};

const items = computed(() =>
canSyncWishlist.value ? itemsSync.value : itemsLocal.value,
);
const count = computed(() => items.value.length);

const getCurrentPage = computed(() => currentPage.value);

return {
mergeWishlistProducts,
getWishlistProducts,
clearWishlist,
items,
count,
changeCurrentPage,
getCurrentPage,
getTotalPagesCount,
totalWishlistItemsCount,
};
}
4 changes: 2 additions & 2 deletions templates/vue-demo-store/components/layout/LayoutHeader.vue
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<script setup lang="ts">
const { count } = useCart();
const { count: wishlistCount } = useWishlist();
const { totalWishlistItemsCount: wishlistCount } = useWishlist();
const localePath = useLocalePath();
const { formatLink } = useInternationalization(localePath);

Expand Down Expand Up @@ -51,7 +51,7 @@ const sidebarController = useModal();
class="w-7 h-7 i-carbon-favorite text-secondary-600 hover:text-primary hover:animate-count-infinite hover:animate-heart-beat"
/>
<span
v-if="wishlistCount > 0"
v-if="wishlistCount"
class="text-3 font-sm text-white absolute bg-red-600 rounded-full min-w-5 min-h-5 top-0 right-0 leading-5"
>
{{ wishlistCount }}
Expand Down