diff --git a/locale/defaultMessages.json b/locale/defaultMessages.json index 8b76c3867..d7ee7dfb4 100644 --- a/locale/defaultMessages.json +++ b/locale/defaultMessages.json @@ -1293,7 +1293,7 @@ "string": "Cancel" }, "src_dot_cancelled": { - "context": "order status", + "context": "payment status", "string": "Cancelled" }, "src_dot_cannotFullfillUnpaidOrder": { @@ -5456,6 +5456,13 @@ "context": "order status", "string": "Partially returned" }, + "src_dot_paymentStatus": { + "string": "Payment status" + }, + "src_dot_pending": { + "context": "payment status", + "string": "Pending" + }, "src_dot_permissionGroups": { "context": "permission groups section name", "string": "Permission Groups" @@ -6699,6 +6706,10 @@ "context": "payment status", "string": "Fully refunded" }, + "src_dot_refused": { + "context": "payment status", + "string": "Refused" + }, "src_dot_remove": { "context": "button", "string": "Remove" diff --git a/src/intl.ts b/src/intl.ts index e5b503a53..f610600dc 100644 --- a/src/intl.ts +++ b/src/intl.ts @@ -99,6 +99,9 @@ export const commonMessages = defineMessages({ status: { defaultMessage: "Status" }, + paymentStatus: { + defaultMessage: "Payment status" + }, summary: { defaultMessage: "Summary" }, @@ -347,6 +350,83 @@ export const sectionNames = defineMessages({ } }); +export const commonStatusMessages = defineMessages({ + cancelled: { + defaultMessage: "Cancelled", + description: "payment status" + } +}); + +export const orderStatusMessages = defineMessages({ + draft: { + defaultMessage: "Draft", + description: "order status" + }, + fulfilled: { + defaultMessage: "Fulfilled", + description: "order status" + }, + partiallyFulfilled: { + defaultMessage: "Partially fulfilled", + description: "order status" + }, + partiallyReturned: { + defaultMessage: "Partially returned", + description: "order status" + }, + readyToCapture: { + defaultMessage: "Ready to capture", + description: "order status" + }, + readyToFulfill: { + defaultMessage: "Ready to fulfill", + description: "order status" + }, + returned: { + defaultMessage: "Returned", + description: "order status" + }, + unconfirmed: { + defaultMessage: "Unconfirmed", + description: "order status" + }, + unfulfilled: { + defaultMessage: "Unfulfilled", + description: "order status" + } +}); + +export const paymentStatusMessages = defineMessages({ + paid: { + defaultMessage: "Fully paid", + description: "payment status" + }, + partiallyPaid: { + defaultMessage: "Partially paid", + description: "payment status" + }, + partiallyRefunded: { + defaultMessage: "Partially refunded", + description: "payment status" + }, + refunded: { + defaultMessage: "Fully refunded", + description: "payment status" + }, + unpaid: { + defaultMessage: "Unpaid", + description: "payment status" + }, + pending: { + defaultMessage: "Pending", + description: "payment status" + }, + refused: { + defaultMessage: "Refused", + description: "payment status" + } +}); + export function translateBoolean(value: boolean, intl: IntlShape): string { return value ? intl.formatMessage(commonMessages.yes) diff --git a/src/misc.ts b/src/misc.ts index 5d593cda5..81ddee293 100644 --- a/src/misc.ts +++ b/src/misc.ts @@ -1,7 +1,7 @@ import { ThemeType } from "@saleor/macaw-ui"; import moment from "moment-timezone"; import { MutationFunction, MutationResult } from "react-apollo"; -import { defineMessages, IntlShape } from "react-intl"; +import { IntlShape } from "react-intl"; import urlJoin from "url-join"; import { ConfirmButtonTransitionState } from "./components/ConfirmButton"; @@ -9,6 +9,11 @@ import { StatusType } from "./components/StatusChip/types"; import { StatusLabelProps } from "./components/StatusLabel"; import { APP_MOUNT_URI } from "./config"; import { AddressType, AddressTypeInput } from "./customers/types"; +import { + commonStatusMessages, + orderStatusMessages, + paymentStatusMessages +} from "./intl"; import { MutationResultAdditionalProps, PartialMutationProviderOutput, @@ -69,29 +74,6 @@ export function weight(value: string) { export const removeDoubleSlashes = (url: string) => url.replace(/([^:]\/)\/+/g, "$1"); -const paymentStatusMessages = defineMessages({ - paid: { - defaultMessage: "Fully paid", - description: "payment status" - }, - partiallyPaid: { - defaultMessage: "Partially paid", - description: "payment status" - }, - partiallyRefunded: { - defaultMessage: "Partially refunded", - description: "payment status" - }, - refunded: { - defaultMessage: "Fully refunded", - description: "payment status" - }, - unpaid: { - defaultMessage: "Unpaid", - description: "payment status" - } -}); - export const transformPaymentStatus = ( status: string, intl: IntlShape @@ -100,74 +82,50 @@ export const transformPaymentStatus = ( case PaymentChargeStatusEnum.PARTIALLY_CHARGED: return { localized: intl.formatMessage(paymentStatusMessages.partiallyPaid), - status: "error" + status: StatusType.ERROR }; case PaymentChargeStatusEnum.FULLY_CHARGED: return { localized: intl.formatMessage(paymentStatusMessages.paid), - status: "success" + status: StatusType.SUCCESS }; case PaymentChargeStatusEnum.PARTIALLY_REFUNDED: return { localized: intl.formatMessage(paymentStatusMessages.partiallyRefunded), - status: "error" + status: StatusType.ERROR }; case PaymentChargeStatusEnum.FULLY_REFUNDED: return { localized: intl.formatMessage(paymentStatusMessages.refunded), - status: "success" + status: StatusType.SUCCESS }; - default: + case PaymentChargeStatusEnum.PENDING: + return { + localized: intl.formatMessage(paymentStatusMessages.pending), + status: StatusType.NEUTRAL + }; + case PaymentChargeStatusEnum.REFUSED: + return { + localized: intl.formatMessage(paymentStatusMessages.refused), + status: StatusType.ERROR + }; + case PaymentChargeStatusEnum.CANCELLED: + return { + localized: intl.formatMessage(commonStatusMessages.cancelled), + status: StatusType.ERROR + }; + case PaymentChargeStatusEnum.NOT_CHARGED: return { localized: intl.formatMessage(paymentStatusMessages.unpaid), - status: "error" + status: StatusType.ERROR }; } + return { + localized: status, + status: StatusType.ERROR + }; }; -export const orderStatusMessages = defineMessages({ - cancelled: { - defaultMessage: "Cancelled", - description: "order status" - }, - draft: { - defaultMessage: "Draft", - description: "order status" - }, - fulfilled: { - defaultMessage: "Fulfilled", - description: "order status" - }, - partiallyFulfilled: { - defaultMessage: "Partially fulfilled", - description: "order status" - }, - partiallyReturned: { - defaultMessage: "Partially returned", - description: "order status" - }, - readyToCapture: { - defaultMessage: "Ready to capture", - description: "order status" - }, - readyToFulfill: { - defaultMessage: "Ready to fulfill", - description: "order status" - }, - returned: { - defaultMessage: "Returned", - description: "order status" - }, - unconfirmed: { - defaultMessage: "Unconfirmed", - description: "order status" - }, - unfulfilled: { - defaultMessage: "Unfulfilled", - description: "order status" - } -}); - export const transformOrderStatus = ( status: string, intl: IntlShape @@ -190,7 +148,7 @@ export const transformOrderStatus = ( }; case OrderStatus.CANCELED: return { - localized: intl.formatMessage(orderStatusMessages.cancelled), + localized: intl.formatMessage(commonStatusMessages.cancelled), status: StatusType.ERROR }; case OrderStatus.DRAFT: diff --git a/src/orders/components/OrderListPage/filters.ts b/src/orders/components/OrderListPage/filters.ts index a47826db7..52b564016 100644 --- a/src/orders/components/OrderListPage/filters.ts +++ b/src/orders/components/OrderListPage/filters.ts @@ -1,9 +1,16 @@ import { IFilter } from "@saleor/components/Filter"; import { MultiAutocompleteChoiceType } from "@saleor/components/MultiAutocompleteSelectField"; import { commonMessages } from "@saleor/intl"; -import { orderStatusMessages } from "@saleor/misc"; +import { + commonStatusMessages, + orderStatusMessages, + paymentStatusMessages +} from "@saleor/intl"; import { FilterOpts, MinMax } from "@saleor/types"; -import { OrderStatusFilter } from "@saleor/types/globalTypes"; +import { + OrderStatusFilter, + PaymentChargeStatusEnum +} from "@saleor/types/globalTypes"; import { createDateField, createOptionsField, @@ -15,6 +22,7 @@ export enum OrderFilterKeys { created = "created", customer = "customer", status = "status", + paymentStatus = "paymentStatus", channel = "channel" } @@ -22,6 +30,7 @@ export interface OrderListFilterOpts { created: FilterOpts; customer: FilterOpts; status: FilterOpts; + paymentStatus: FilterOpts; channel?: FilterOpts; } @@ -69,7 +78,7 @@ export function createFilterStructure( true, [ { - label: intl.formatMessage(orderStatusMessages.cancelled), + label: intl.formatMessage(commonStatusMessages.cancelled), value: OrderStatusFilter.CANCELED }, { @@ -91,11 +100,58 @@ export function createFilterStructure( { label: intl.formatMessage(orderStatusMessages.readyToFulfill), value: OrderStatusFilter.READY_TO_FULFILL + }, + { + label: intl.formatMessage(orderStatusMessages.unconfirmed), + value: OrderStatusFilter.UNCONFIRMED } ] ), active: opts.status.active }, + { + ...createOptionsField( + OrderFilterKeys.paymentStatus, + intl.formatMessage(commonMessages.paymentStatus), + opts.paymentStatus.value, + true, + [ + { + label: intl.formatMessage(paymentStatusMessages.paid), + value: PaymentChargeStatusEnum.FULLY_CHARGED + }, + { + label: intl.formatMessage(paymentStatusMessages.partiallyPaid), + value: PaymentChargeStatusEnum.PARTIALLY_CHARGED + }, + { + label: intl.formatMessage(paymentStatusMessages.unpaid), + value: PaymentChargeStatusEnum.NOT_CHARGED + }, + { + label: intl.formatMessage(paymentStatusMessages.refunded), + value: PaymentChargeStatusEnum.FULLY_REFUNDED + }, + { + label: intl.formatMessage(paymentStatusMessages.partiallyRefunded), + value: PaymentChargeStatusEnum.PARTIALLY_REFUNDED + }, + { + label: intl.formatMessage(commonStatusMessages.cancelled), + value: PaymentChargeStatusEnum.CANCELLED + }, + { + label: intl.formatMessage(paymentStatusMessages.pending), + value: PaymentChargeStatusEnum.PENDING + }, + { + label: intl.formatMessage(paymentStatusMessages.refused), + value: PaymentChargeStatusEnum.REFUSED + } + ] + ), + active: opts.paymentStatus.active + }, ...(opts?.channel?.value.length ? [ { diff --git a/src/orders/urls.ts b/src/orders/urls.ts index 891c96ac3..e2fda1747 100644 --- a/src/orders/urls.ts +++ b/src/orders/urls.ts @@ -27,6 +27,7 @@ export enum OrderListUrlFiltersEnum { } export enum OrderListUrlFiltersWithMultipleValues { status = "status", + paymentStatus = "paymentStatus", channel = "channel" } diff --git a/src/orders/views/OrderList/__snapshots__/filters.test.ts.snap b/src/orders/views/OrderList/__snapshots__/filters.test.ts.snap index 08299a901..ff0b79b43 100644 --- a/src/orders/views/OrderList/__snapshots__/filters.test.ts.snap +++ b/src/orders/views/OrderList/__snapshots__/filters.test.ts.snap @@ -6,6 +6,10 @@ Object { "createdFrom": "2019-12-09", "createdTo": "2019-12-38", "customer": "email@example.com", + "paymentStatus": Array [ + "FULLY_CHARGED", + "PARTIALLY_CHARGED", + ], "status": Array [ "FULFILLED", "PARTIALLY_FULFILLED", @@ -13,4 +17,4 @@ Object { } `; -exports[`Filtering URL params should not be empty if active filters are present 2`] = `"customer=email%40example.com&createdFrom=2019-12-09&createdTo=2019-12-38&status%5B%5D=FULFILLED&status%5B%5D=PARTIALLY_FULFILLED"`; +exports[`Filtering URL params should not be empty if active filters are present 2`] = `"customer=email%40example.com&createdFrom=2019-12-09&createdTo=2019-12-38&status%5B%5D=FULFILLED&status%5B%5D=PARTIALLY_FULFILLED&paymentStatus%5B%5D=FULLY_CHARGED&paymentStatus%5B%5D=PARTIALLY_CHARGED"`; diff --git a/src/orders/views/OrderList/filters.test.ts b/src/orders/views/OrderList/filters.test.ts index 14a8c99e6..92c5a8ba2 100644 --- a/src/orders/views/OrderList/filters.test.ts +++ b/src/orders/views/OrderList/filters.test.ts @@ -1,7 +1,10 @@ import { date } from "@saleor/fixtures"; import { createFilterStructure } from "@saleor/orders/components/OrderListPage"; import { OrderListUrlFilters } from "@saleor/orders/urls"; -import { OrderStatusFilter } from "@saleor/types/globalTypes"; +import { + OrderStatusFilter, + PaymentChargeStatusEnum +} from "@saleor/types/globalTypes"; import { getFilterQueryParams } from "@saleor/utils/filters"; import { stringifyQs } from "@saleor/utils/urls"; import { getExistingKeys, setFilterOptsStatus } from "@test/filters"; @@ -64,6 +67,13 @@ describe("Filtering URL params", () => { OrderStatusFilter.FULFILLED, OrderStatusFilter.PARTIALLY_FULFILLED ] + }, + paymentStatus: { + active: false, + value: [ + PaymentChargeStatusEnum.FULLY_CHARGED, + PaymentChargeStatusEnum.PARTIALLY_CHARGED + ] } }); diff --git a/src/orders/views/OrderList/filters.ts b/src/orders/views/OrderList/filters.ts index 67a5c31e6..eb3645f2c 100644 --- a/src/orders/views/OrderList/filters.ts +++ b/src/orders/views/OrderList/filters.ts @@ -8,7 +8,8 @@ import { import { IFilterElement } from "../../../components/Filter"; import { OrderFilterInput, - OrderStatusFilter + OrderStatusFilter, + PaymentChargeStatusEnum } from "../../../types/globalTypes"; import { createFilterTabUtils, @@ -60,6 +61,14 @@ export function getFilterOpts( findValueInEnum(status, OrderStatusFilter) ) || [] ) + }, + paymentStatus: { + active: params?.paymentStatus !== undefined, + value: dedupeFilter( + params.paymentStatus?.map(paymentStatus => + findValueInEnum(paymentStatus, PaymentChargeStatusEnum) + ) || [] + ) } }; } @@ -75,7 +84,12 @@ export function getFilterVariables( }), customer: params.customer, search: params.query, - status: params?.status?.map(status => findInEnum(status, OrderStatusFilter)) + status: params?.status?.map(status => + findInEnum(status, OrderStatusFilter) + ), + paymentStatus: params?.paymentStatus?.map(paymentStatus => + findInEnum(paymentStatus, PaymentChargeStatusEnum) + ) }; } @@ -99,6 +113,13 @@ export function getFilterQueryParam( OrderStatusFilter ); + case OrderFilterKeys.paymentStatus: + return getMultipleEnumValueQueryParam( + filter, + OrderListUrlFiltersWithMultipleValues.paymentStatus, + PaymentChargeStatusEnum + ); + case OrderFilterKeys.channel: return getMultipleValueQueryParam( filter, diff --git a/src/storybook/__snapshots__/Stories.test.ts.snap b/src/storybook/__snapshots__/Stories.test.ts.snap index ac8b440fc..caf359561 100644 --- a/src/storybook/__snapshots__/Stories.test.ts.snap +++ b/src/storybook/__snapshots__/Stories.test.ts.snap @@ -130599,9 +130599,7 @@ exports[`Storyshots Views / Orders / Order details no payment 1`] = ` >
- Unpaid -
+ /> diff --git a/src/storybook/stories/orders/OrderListPage.tsx b/src/storybook/stories/orders/OrderListPage.tsx index 6234ba90a..a2b20208a 100644 --- a/src/storybook/stories/orders/OrderListPage.tsx +++ b/src/storybook/stories/orders/OrderListPage.tsx @@ -2,7 +2,10 @@ import OrderListPage, { OrderListPageProps } from "@saleor/orders/components/OrderListPage"; import { OrderListUrlSortField } from "@saleor/orders/urls"; -import { OrderStatusFilter } from "@saleor/types/globalTypes"; +import { + OrderStatusFilter, + PaymentChargeStatusEnum +} from "@saleor/types/globalTypes"; import { storiesOf } from "@storybook/react"; import React from "react"; @@ -46,6 +49,13 @@ const props: OrderListPageProps = { status: { active: false, value: [OrderStatusFilter.CANCELED, OrderStatusFilter.FULFILLED] + }, + paymentStatus: { + active: false, + value: [ + PaymentChargeStatusEnum.CANCELLED, + PaymentChargeStatusEnum.FULLY_CHARGED + ] } }, limits,