Refactor order section translations (#123)
* Refactor translations in order section * Ensure ID uniqueness * Update pot file
This commit is contained in:
parent
f78e5aea31
commit
3d2d56e227
36 changed files with 3045 additions and 1001 deletions
1546
locale/messages.pot
1546
locale/messages.pot
File diff suppressed because it is too large
Load diff
36
src/intl.ts
36
src/intl.ts
|
@ -50,45 +50,41 @@ export const commonMessages = defineMessages({
|
||||||
});
|
});
|
||||||
|
|
||||||
export const buttonMessages = defineMessages({
|
export const buttonMessages = defineMessages({
|
||||||
|
back: {
|
||||||
|
defaultMessage: "Back",
|
||||||
|
description: "button"
|
||||||
|
},
|
||||||
cancel: {
|
cancel: {
|
||||||
defaultMessage: "Cancel",
|
defaultMessage: "Cancel",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "cancel"
|
|
||||||
},
|
},
|
||||||
confirm: {
|
confirm: {
|
||||||
defaultMessage: "Confirm",
|
defaultMessage: "Confirm",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "confirm"
|
|
||||||
},
|
},
|
||||||
edit: {
|
edit: {
|
||||||
defaultMessage: "Edit",
|
defaultMessage: "Edit",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "edit"
|
|
||||||
},
|
},
|
||||||
manage: {
|
manage: {
|
||||||
defaultMessage: "Manage",
|
defaultMessage: "Manage",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "manage"
|
|
||||||
},
|
},
|
||||||
remove: {
|
remove: {
|
||||||
defaultMessage: "Remove",
|
defaultMessage: "Remove",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "remove"
|
|
||||||
},
|
},
|
||||||
save: {
|
save: {
|
||||||
defaultMessage: "Save",
|
defaultMessage: "Save",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "save"
|
|
||||||
},
|
},
|
||||||
show: {
|
show: {
|
||||||
defaultMessage: "Show",
|
defaultMessage: "Show",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "show"
|
|
||||||
},
|
},
|
||||||
undo: {
|
undo: {
|
||||||
defaultMessage: "Undo",
|
defaultMessage: "Undo",
|
||||||
description: "button",
|
description: "button"
|
||||||
id: "undo"
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -113,10 +109,18 @@ export const sectionNames = defineMessages({
|
||||||
defaultMessage: "Customers",
|
defaultMessage: "Customers",
|
||||||
description: "customers section name"
|
description: "customers section name"
|
||||||
},
|
},
|
||||||
|
draftOrders: {
|
||||||
|
defaultMessage: "Draft Orders",
|
||||||
|
description: "draft orders section name"
|
||||||
|
},
|
||||||
navigation: {
|
navigation: {
|
||||||
defaultMessage: "Navigation",
|
defaultMessage: "Navigation",
|
||||||
description: "navigation section name"
|
description: "navigation section name"
|
||||||
},
|
},
|
||||||
|
orders: {
|
||||||
|
defaultMessage: "Orders",
|
||||||
|
description: "orders section name"
|
||||||
|
},
|
||||||
pages: {
|
pages: {
|
||||||
defaultMessage: "Pages",
|
defaultMessage: "Pages",
|
||||||
description: "pages section name"
|
description: "pages section name"
|
||||||
|
|
|
@ -5,6 +5,7 @@ import DialogContent from "@material-ui/core/DialogContent";
|
||||||
import DialogTitle from "@material-ui/core/DialogTitle";
|
import DialogTitle from "@material-ui/core/DialogTitle";
|
||||||
import { createStyles, withStyles, WithStyles } from "@material-ui/core/styles";
|
import { createStyles, withStyles, WithStyles } from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import AddressEdit from "@saleor/components/AddressEdit";
|
import AddressEdit from "@saleor/components/AddressEdit";
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
|
@ -12,10 +13,10 @@ import ConfirmButton, {
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import useStateFromProps from "@saleor/hooks/useStateFromProps";
|
import useStateFromProps from "@saleor/hooks/useStateFromProps";
|
||||||
|
import { buttonMessages } from "@saleor/intl";
|
||||||
import { maybe } from "@saleor/misc";
|
import { maybe } from "@saleor/misc";
|
||||||
import createSingleAutocompleteSelectHandler from "@saleor/utils/handlers/singleAutocompleteSelectChangeHandler";
|
import createSingleAutocompleteSelectHandler from "@saleor/utils/handlers/singleAutocompleteSelectChangeHandler";
|
||||||
import { AddressTypeInput } from "../../../customers/types";
|
import { AddressTypeInput } from "../../../customers/types";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { UserError } from "../../../types";
|
import { UserError } from "../../../types";
|
||||||
|
|
||||||
const styles = createStyles({
|
const styles = createStyles({
|
||||||
|
@ -52,6 +53,7 @@ const OrderAddressEditDialog = withStyles(styles, {
|
||||||
onClose,
|
onClose,
|
||||||
onConfirm
|
onConfirm
|
||||||
}: OrderAddressEditDialogProps) => {
|
}: OrderAddressEditDialogProps) => {
|
||||||
|
const intl = useIntl();
|
||||||
const [countryDisplayName, setCountryDisplayName] = useStateFromProps(
|
const [countryDisplayName, setCountryDisplayName] = useStateFromProps(
|
||||||
maybe(
|
maybe(
|
||||||
() => countries.find(country => address.country === country.code).label
|
() => countries.find(country => address.country === country.code).label
|
||||||
|
@ -80,8 +82,14 @@ const OrderAddressEditDialog = withStyles(styles, {
|
||||||
<>
|
<>
|
||||||
<DialogTitle>
|
<DialogTitle>
|
||||||
{variant === "billing"
|
{variant === "billing"
|
||||||
? i18n.t("Edit billing address", { context: "title" })
|
? intl.formatMessage({
|
||||||
: i18n.t("Edit shipping address", { context: "title" })}
|
defaultMessage: "Edit billing address",
|
||||||
|
description: "dialog header"
|
||||||
|
})
|
||||||
|
: intl.formatMessage({
|
||||||
|
defaultMessage: "Edit shipping address",
|
||||||
|
description: "dialog header"
|
||||||
|
})}
|
||||||
</DialogTitle>
|
</DialogTitle>
|
||||||
<DialogContent className={classes.overflow}>
|
<DialogContent className={classes.overflow}>
|
||||||
<AddressEdit
|
<AddressEdit
|
||||||
|
@ -95,7 +103,7 @@ const OrderAddressEditDialog = withStyles(styles, {
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions>
|
<DialogActions>
|
||||||
<Button onClick={onClose}>
|
<Button onClick={onClose}>
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
</Button>
|
</Button>
|
||||||
<ConfirmButton
|
<ConfirmButton
|
||||||
transitionState={confirmButtonState}
|
transitionState={confirmButtonState}
|
||||||
|
@ -104,7 +112,7 @@ const OrderAddressEditDialog = withStyles(styles, {
|
||||||
onClick={submit}
|
onClick={submit}
|
||||||
type="submit"
|
type="submit"
|
||||||
>
|
>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</ConfirmButton>
|
</ConfirmButton>
|
||||||
</DialogActions>
|
</DialogActions>
|
||||||
</>
|
</>
|
||||||
|
|
|
@ -1,10 +1,10 @@
|
||||||
import DialogContentText from "@material-ui/core/DialogContentText";
|
import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ActionDialog from "@saleor/components/ActionDialog";
|
import ActionDialog from "@saleor/components/ActionDialog";
|
||||||
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
||||||
import ControlledCheckbox from "@saleor/components/ControlledCheckbox";
|
import ControlledCheckbox from "@saleor/components/ControlledCheckbox";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
|
|
||||||
export interface OrderBulkCancelDialogProps {
|
export interface OrderBulkCancelDialogProps {
|
||||||
confirmButtonState: ConfirmButtonTransitionState;
|
confirmButtonState: ConfirmButtonTransitionState;
|
||||||
|
@ -17,6 +17,7 @@ export interface OrderBulkCancelDialogProps {
|
||||||
const OrderBulkCancelDialog: React.StatelessComponent<
|
const OrderBulkCancelDialog: React.StatelessComponent<
|
||||||
OrderBulkCancelDialogProps
|
OrderBulkCancelDialogProps
|
||||||
> = ({ confirmButtonState, numberOfOrders, open, onClose, onConfirm }) => {
|
> = ({ confirmButtonState, numberOfOrders, open, onClose, onConfirm }) => {
|
||||||
|
const intl = useIntl();
|
||||||
const [restock, setRestock] = React.useState(true);
|
const [restock, setRestock] = React.useState(true);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
@ -24,23 +25,31 @@ const OrderBulkCancelDialog: React.StatelessComponent<
|
||||||
confirmButtonState={confirmButtonState}
|
confirmButtonState={confirmButtonState}
|
||||||
open={open}
|
open={open}
|
||||||
variant="delete"
|
variant="delete"
|
||||||
title={i18n.t("Cancel Orders")}
|
title={intl.formatMessage({
|
||||||
|
defaultMessage: "Cancel Orders",
|
||||||
|
description: "dialog header"
|
||||||
|
})}
|
||||||
onClose={onClose}
|
onClose={onClose}
|
||||||
onConfirm={() => onConfirm(restock)}
|
onConfirm={() => onConfirm(restock)}
|
||||||
>
|
>
|
||||||
<DialogContentText
|
<DialogContentText>
|
||||||
dangerouslySetInnerHTML={{
|
<FormattedMessage
|
||||||
__html: i18n.t(
|
defaultMessage="Are you sure you want to cancel {counter, plural,
|
||||||
"Are you sure you want to cancel <strong>{{ number }}</strong> orders?",
|
one {this order}
|
||||||
{
|
other {{displayQuantity} orders}
|
||||||
number: numberOfOrders
|
}?"
|
||||||
}
|
values={{
|
||||||
)
|
counter: numberOfOrders,
|
||||||
}}
|
displayQuantity: <strong>{numberOfOrders}</strong>
|
||||||
/>
|
}}
|
||||||
|
/>
|
||||||
|
</DialogContentText>
|
||||||
<ControlledCheckbox
|
<ControlledCheckbox
|
||||||
checked={restock}
|
checked={restock}
|
||||||
label={i18n.t("Release all stock allocated to these orders")}
|
label={intl.formatMessage({
|
||||||
|
defaultMessage: "Release all stock allocated to these orders",
|
||||||
|
description: "switch button"
|
||||||
|
})}
|
||||||
name="restock"
|
name="restock"
|
||||||
onChange={event => setRestock(event.target.value)}
|
onChange={event => setRestock(event.target.value)}
|
||||||
/>
|
/>
|
||||||
|
|
|
@ -11,13 +11,14 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import ControlledCheckbox from "@saleor/components/ControlledCheckbox";
|
import ControlledCheckbox from "@saleor/components/ControlledCheckbox";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
export interface FormData {
|
export interface FormData {
|
||||||
restock: boolean;
|
restock: boolean;
|
||||||
|
@ -50,55 +51,66 @@ const OrderCancelDialog = withStyles(styles, { name: "OrderCancelDialog" })(
|
||||||
open,
|
open,
|
||||||
onSubmit,
|
onSubmit,
|
||||||
onClose
|
onClose
|
||||||
}: OrderCancelDialogProps) => (
|
}: OrderCancelDialogProps) => {
|
||||||
<Dialog onClose={onClose} open={open}>
|
const intl = useIntl();
|
||||||
<Form
|
|
||||||
initial={{
|
return (
|
||||||
restock: true
|
<Dialog onClose={onClose} open={open}>
|
||||||
}}
|
<Form
|
||||||
onSubmit={onSubmit}
|
initial={{
|
||||||
>
|
restock: true
|
||||||
{({ data, change }) => {
|
}}
|
||||||
return (
|
onSubmit={onSubmit}
|
||||||
<>
|
>
|
||||||
<DialogTitle>
|
{({ data, change }) => {
|
||||||
{i18n.t("Cancel order", { context: "title" })}
|
return (
|
||||||
</DialogTitle>
|
<>
|
||||||
<DialogContent>
|
<DialogTitle>
|
||||||
<DialogContentText
|
<FormattedMessage
|
||||||
dangerouslySetInnerHTML={{
|
defaultMessage="Cancel order"
|
||||||
__html: i18n.t(
|
description="dialog header"
|
||||||
"Are you sure you want to cancel order <strong>{{ orderNumber }}</strong>?",
|
/>
|
||||||
{ orderNumber }
|
</DialogTitle>
|
||||||
)
|
<DialogContent>
|
||||||
}}
|
<DialogContentText>
|
||||||
/>
|
<FormattedMessage
|
||||||
<ControlledCheckbox
|
defaultMessage="Are you sure you want to cancel order #{orderNumber}?"
|
||||||
checked={data.restock}
|
values={{
|
||||||
label={i18n.t("Release all stock allocated to this order")}
|
orderNumber
|
||||||
name="restock"
|
}}
|
||||||
onChange={change}
|
/>
|
||||||
/>
|
<ControlledCheckbox
|
||||||
</DialogContent>
|
checked={data.restock}
|
||||||
<DialogActions>
|
label={intl.formatMessage({
|
||||||
<Button onClick={onClose}>
|
defaultMessage:
|
||||||
{i18n.t("Back", { context: "button" })}
|
"Release all stock allocated to this order",
|
||||||
</Button>
|
description: "switch button"
|
||||||
<ConfirmButton
|
})}
|
||||||
transitionState={confirmButtonState}
|
name="restock"
|
||||||
className={classes.deleteButton}
|
onChange={change}
|
||||||
variant="contained"
|
/>
|
||||||
type="submit"
|
</DialogContentText>
|
||||||
>
|
</DialogContent>
|
||||||
{i18n.t("Cancel order", { context: "button" })}
|
<DialogActions>
|
||||||
</ConfirmButton>
|
<Button onClick={onClose}>
|
||||||
</DialogActions>
|
<FormattedMessage {...buttonMessages.back} />
|
||||||
</>
|
</Button>
|
||||||
);
|
<ConfirmButton
|
||||||
}}
|
transitionState={confirmButtonState}
|
||||||
</Form>
|
className={classes.deleteButton}
|
||||||
</Dialog>
|
variant="contained"
|
||||||
)
|
type="submit"
|
||||||
|
>
|
||||||
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
|
</ConfirmButton>
|
||||||
|
</DialogActions>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
}}
|
||||||
|
</Form>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
}
|
||||||
);
|
);
|
||||||
OrderCancelDialog.displayName = "OrderCancelDialog";
|
OrderCancelDialog.displayName = "OrderCancelDialog";
|
||||||
export default OrderCancelDialog;
|
export default OrderCancelDialog;
|
||||||
|
|
|
@ -9,6 +9,7 @@ import {
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
import ExternalLink from "@saleor/components/ExternalLink";
|
import ExternalLink from "@saleor/components/ExternalLink";
|
||||||
|
@ -18,10 +19,10 @@ import Link from "@saleor/components/Link";
|
||||||
import SingleAutocompleteSelectField from "@saleor/components/SingleAutocompleteSelectField";
|
import SingleAutocompleteSelectField from "@saleor/components/SingleAutocompleteSelectField";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import useStateFromProps from "@saleor/hooks/useStateFromProps";
|
import useStateFromProps from "@saleor/hooks/useStateFromProps";
|
||||||
|
import { buttonMessages } from "@saleor/intl";
|
||||||
import createSingleAutocompleteSelectHandler from "@saleor/utils/handlers/singleAutocompleteSelectChangeHandler";
|
import createSingleAutocompleteSelectHandler from "@saleor/utils/handlers/singleAutocompleteSelectChangeHandler";
|
||||||
import { SearchCustomers_customers_edges_node } from "../../../containers/SearchCustomers/types/SearchCustomers";
|
import { SearchCustomers_customers_edges_node } from "../../../containers/SearchCustomers/types/SearchCustomers";
|
||||||
import { customerUrl } from "../../../customers/urls";
|
import { customerUrl } from "../../../customers/urls";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { createHref, maybe } from "../../../misc";
|
import { createHref, maybe } from "../../../misc";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
|
|
||||||
|
@ -74,6 +75,8 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
onProfileView,
|
onProfileView,
|
||||||
onShippingAddressEdit
|
onShippingAddressEdit
|
||||||
}: OrderCustomerProps) => {
|
}: OrderCustomerProps) => {
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const user = maybe(() => order.user);
|
const user = maybe(() => order.user);
|
||||||
|
|
||||||
const [userDisplayName, setUserDisplayName] = useStateFromProps(
|
const [userDisplayName, setUserDisplayName] = useStateFromProps(
|
||||||
|
@ -88,7 +91,10 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
return (
|
return (
|
||||||
<Card>
|
<Card>
|
||||||
<CardTitle
|
<CardTitle
|
||||||
title={i18n.t("Customer")}
|
title={intl.formatMessage({
|
||||||
|
defaultMessage: "Customer",
|
||||||
|
description: "section header"
|
||||||
|
})}
|
||||||
toolbar={
|
toolbar={
|
||||||
!!canEditCustomer && (
|
!!canEditCustomer && (
|
||||||
<Button
|
<Button
|
||||||
|
@ -97,7 +103,7 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
disabled={!onCustomerEdit}
|
disabled={!onCustomerEdit}
|
||||||
onClick={toggleEditMode}
|
onClick={toggleEditMode}
|
||||||
>
|
>
|
||||||
{i18n.t("Edit")}
|
{intl.formatMessage(buttonMessages.edit)}
|
||||||
</Button>
|
</Button>
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
@ -133,7 +139,9 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
displayValue={userDisplayName}
|
displayValue={userDisplayName}
|
||||||
fetchChoices={fetchUsers}
|
fetchChoices={fetchUsers}
|
||||||
loading={loading}
|
loading={loading}
|
||||||
placeholder={i18n.t("Search Customers")}
|
placeholder={intl.formatMessage({
|
||||||
|
defaultMessage: "Search Customers"
|
||||||
|
})}
|
||||||
onChange={handleUserChange}
|
onChange={handleUserChange}
|
||||||
name="query"
|
name="query"
|
||||||
value={data.query}
|
value={data.query}
|
||||||
|
@ -142,7 +150,9 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
}}
|
}}
|
||||||
</Form>
|
</Form>
|
||||||
) : user === null ? (
|
) : user === null ? (
|
||||||
<Typography>{i18n.t("Anonymous user")}</Typography>
|
<Typography>
|
||||||
|
<FormattedMessage defaultMessage="Anonymous user" />
|
||||||
|
</Typography>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
<Typography className={classes.userEmail}>
|
<Typography className={classes.userEmail}>
|
||||||
|
@ -154,14 +164,21 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
href={createHref(customerUrl(user.id))}
|
href={createHref(customerUrl(user.id))}
|
||||||
onClick={onProfileView}
|
onClick={onProfileView}
|
||||||
>
|
>
|
||||||
{i18n.t("View Profile")}
|
<FormattedMessage
|
||||||
|
defaultMessage="View Profile"
|
||||||
|
description="link"
|
||||||
|
/>
|
||||||
</Link>
|
</Link>
|
||||||
</div>
|
</div>
|
||||||
{/* TODO: Uncomment it after adding ability to filter
|
{/* TODO: Uncomment it after adding ability to filter
|
||||||
orders by customer */}
|
orders by customer */}
|
||||||
{/* <div>
|
{/* <div>
|
||||||
<Link underline={false} href={}>{i18n.t("View Orders")}</Link>
|
<Link underline={false} href={}>
|
||||||
</div> */}
|
<FormattedMessage defaultMessage="View Orders"
|
||||||
|
description="link"
|
||||||
|
/>
|
||||||
|
</Link>
|
||||||
|
</div> */}
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
</CardContent>
|
</CardContent>
|
||||||
|
@ -169,14 +186,23 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
<CardContent>
|
<CardContent>
|
||||||
<div className={classes.sectionHeader}>
|
<div className={classes.sectionHeader}>
|
||||||
<Typography className={classes.sectionHeaderTitle}>
|
<Typography className={classes.sectionHeaderTitle}>
|
||||||
{i18n.t("Contact information")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Contact information"
|
||||||
|
description="subheader"
|
||||||
|
/>
|
||||||
</Typography>
|
</Typography>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
{maybe(() => order.userEmail) === undefined ? (
|
{maybe(() => order.userEmail) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : order.userEmail === null ? (
|
) : order.userEmail === null ? (
|
||||||
<Typography>{i18n.t("Not set")}</Typography>
|
<Typography>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Not set"
|
||||||
|
description="customer is not set in draft order"
|
||||||
|
id="orderCustomerCustomerNotSet"
|
||||||
|
/>
|
||||||
|
</Typography>
|
||||||
) : (
|
) : (
|
||||||
<ExternalLink
|
<ExternalLink
|
||||||
href={`mailto:${maybe(() => order.userEmail)}`}
|
href={`mailto:${maybe(() => order.userEmail)}`}
|
||||||
|
@ -190,7 +216,7 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
<CardContent>
|
<CardContent>
|
||||||
<div className={classes.sectionHeader}>
|
<div className={classes.sectionHeader}>
|
||||||
<Typography className={classes.sectionHeaderTitle}>
|
<Typography className={classes.sectionHeaderTitle}>
|
||||||
{i18n.t("Shipping Address")}
|
<FormattedMessage defaultMessage="Shipping Address" />
|
||||||
</Typography>
|
</Typography>
|
||||||
{canEditAddresses && (
|
{canEditAddresses && (
|
||||||
<div className={classes.sectionHeaderToolbar}>
|
<div className={classes.sectionHeaderToolbar}>
|
||||||
|
@ -200,7 +226,7 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
onClick={onShippingAddressEdit}
|
onClick={onShippingAddressEdit}
|
||||||
disabled={!onShippingAddressEdit && user === undefined}
|
disabled={!onShippingAddressEdit && user === undefined}
|
||||||
>
|
>
|
||||||
{i18n.t("Edit")}
|
<FormattedMessage {...buttonMessages.edit} />
|
||||||
</Button>
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
@ -208,7 +234,13 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
{shippingAddress === undefined ? (
|
{shippingAddress === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : shippingAddress === null ? (
|
) : shippingAddress === null ? (
|
||||||
<Typography>{i18n.t("Not set")}</Typography>
|
<Typography>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Not set"
|
||||||
|
description="shipping address is not set in draft order"
|
||||||
|
id="orderCustomerShippingAddressNotSet"
|
||||||
|
/>
|
||||||
|
</Typography>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
{shippingAddress.companyName && (
|
{shippingAddress.companyName && (
|
||||||
|
@ -243,7 +275,7 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
<CardContent>
|
<CardContent>
|
||||||
<div className={classes.sectionHeader}>
|
<div className={classes.sectionHeader}>
|
||||||
<Typography className={classes.sectionHeaderTitle}>
|
<Typography className={classes.sectionHeaderTitle}>
|
||||||
{i18n.t("Billing Address")}
|
<FormattedMessage defaultMessage="Billing Address" />
|
||||||
</Typography>
|
</Typography>
|
||||||
{canEditAddresses && (
|
{canEditAddresses && (
|
||||||
<div className={classes.sectionHeaderToolbar}>
|
<div className={classes.sectionHeaderToolbar}>
|
||||||
|
@ -253,7 +285,7 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
onClick={onBillingAddressEdit}
|
onClick={onBillingAddressEdit}
|
||||||
disabled={!onBillingAddressEdit && user === undefined}
|
disabled={!onBillingAddressEdit && user === undefined}
|
||||||
>
|
>
|
||||||
{i18n.t("Edit")}
|
<FormattedMessage {...buttonMessages.edit} />
|
||||||
</Button>
|
</Button>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
@ -261,9 +293,20 @@ const OrderCustomer = withStyles(styles, { name: "OrderCustomer" })(
|
||||||
{billingAddress === undefined ? (
|
{billingAddress === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : billingAddress === null ? (
|
) : billingAddress === null ? (
|
||||||
<Typography>{i18n.t("Not set")}</Typography>
|
<Typography>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Not set"
|
||||||
|
description="no address is set in draft order"
|
||||||
|
id="orderCustomerBillingAddressNotSet"
|
||||||
|
/>
|
||||||
|
</Typography>
|
||||||
) : maybe(() => shippingAddress.id) === billingAddress.id ? (
|
) : maybe(() => shippingAddress.id) === billingAddress.id ? (
|
||||||
<Typography>{i18n.t("Same as shipping address")}</Typography>
|
<Typography>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Same as shipping address"
|
||||||
|
description="billing address"
|
||||||
|
/>
|
||||||
|
</Typography>
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
{billingAddress.companyName && (
|
{billingAddress.companyName && (
|
||||||
|
|
|
@ -10,12 +10,13 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import { SingleAutocompleteSelectField } from "@saleor/components/SingleAutocompleteSelectField";
|
import { SingleAutocompleteSelectField } from "@saleor/components/SingleAutocompleteSelectField";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
const styles = (theme: Theme) =>
|
const styles = (theme: Theme) =>
|
||||||
createStyles({
|
createStyles({
|
||||||
|
@ -76,7 +77,12 @@ const OrderCustomerEditDialog = withStyles(styles, {
|
||||||
: [];
|
: [];
|
||||||
return (
|
return (
|
||||||
<Dialog onClose={onClose} open={open} classes={{ paper: classes.dialog }}>
|
<Dialog onClose={onClose} open={open} classes={{ paper: classes.dialog }}>
|
||||||
<DialogTitle>{i18n.t("Edit customer details")}</DialogTitle>
|
<DialogTitle>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Edit customer details"
|
||||||
|
description="dialog header"
|
||||||
|
/>
|
||||||
|
</DialogTitle>
|
||||||
<DialogContent className={classes.root}>
|
<DialogContent className={classes.root}>
|
||||||
<SingleAutocompleteSelectField
|
<SingleAutocompleteSelectField
|
||||||
choices={choices}
|
choices={choices}
|
||||||
|
@ -91,7 +97,7 @@ const OrderCustomerEditDialog = withStyles(styles, {
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions>
|
<DialogActions>
|
||||||
<Button onClick={onClose}>
|
<Button onClick={onClose}>
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
</Button>
|
</Button>
|
||||||
<ConfirmButton
|
<ConfirmButton
|
||||||
transitionState={confirmButtonState}
|
transitionState={confirmButtonState}
|
||||||
|
@ -99,7 +105,7 @@ const OrderCustomerEditDialog = withStyles(styles, {
|
||||||
variant="contained"
|
variant="contained"
|
||||||
onClick={onConfirm}
|
onClick={onConfirm}
|
||||||
>
|
>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</ConfirmButton>
|
</ConfirmButton>
|
||||||
</DialogActions>
|
</DialogActions>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
|
|
|
@ -2,10 +2,10 @@ import Card from "@material-ui/core/Card";
|
||||||
import CardContent from "@material-ui/core/CardContent";
|
import CardContent from "@material-ui/core/CardContent";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
|
|
||||||
interface OrderCustomerNoteProps {
|
interface OrderCustomerNoteProps {
|
||||||
note: string;
|
note: string;
|
||||||
|
@ -13,24 +13,29 @@ interface OrderCustomerNoteProps {
|
||||||
|
|
||||||
export const OrderCustomerNote: React.StatelessComponent<
|
export const OrderCustomerNote: React.StatelessComponent<
|
||||||
OrderCustomerNoteProps
|
OrderCustomerNoteProps
|
||||||
> = ({ note }) => (
|
> = ({ note }) => {
|
||||||
<Card>
|
const intl = useIntl();
|
||||||
<CardTitle
|
|
||||||
title={i18n.t("Notes", {
|
return (
|
||||||
context: "customer notes"
|
<Card>
|
||||||
})}
|
<CardTitle
|
||||||
/>
|
title={intl.formatMessage({
|
||||||
<CardContent>
|
defaultMessage: "Notes",
|
||||||
{note === undefined ? (
|
description: "notes about customer, header"
|
||||||
<Skeleton />
|
})}
|
||||||
) : note === "" ? (
|
/>
|
||||||
<Typography color="textSecondary">
|
<CardContent>
|
||||||
{i18n.t("No notes from customer")}
|
{note === undefined ? (
|
||||||
</Typography>
|
<Skeleton />
|
||||||
) : (
|
) : note === "" ? (
|
||||||
<Typography>{note}</Typography>
|
<Typography color="textSecondary">
|
||||||
)}
|
<FormattedMessage defaultMessage="No notes from customer" />
|
||||||
</CardContent>
|
</Typography>
|
||||||
</Card>
|
) : (
|
||||||
);
|
<Typography>{note}</Typography>
|
||||||
|
)}
|
||||||
|
</CardContent>
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
};
|
||||||
export default OrderCustomerNote;
|
export default OrderCustomerNote;
|
||||||
|
|
|
@ -6,6 +6,7 @@ import {
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { useIntl } from "react-intl";
|
||||||
|
|
||||||
import AppHeader from "@saleor/components/AppHeader";
|
import AppHeader from "@saleor/components/AppHeader";
|
||||||
import CardMenu from "@saleor/components/CardMenu";
|
import CardMenu from "@saleor/components/CardMenu";
|
||||||
|
@ -15,7 +16,7 @@ import { DateTime } from "@saleor/components/Date";
|
||||||
import Grid from "@saleor/components/Grid";
|
import Grid from "@saleor/components/Grid";
|
||||||
import PageHeader from "@saleor/components/PageHeader";
|
import PageHeader from "@saleor/components/PageHeader";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import i18n from "../../../i18n";
|
import { sectionNames } from "@saleor/intl";
|
||||||
import { maybe, renderCollection } from "../../../misc";
|
import { maybe, renderCollection } from "../../../misc";
|
||||||
import { OrderStatus } from "../../../types/globalTypes";
|
import { OrderStatus } from "../../../types/globalTypes";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
|
@ -81,6 +82,8 @@ const OrderDetailsPage = withStyles(styles, { name: "OrderDetailsPage" })(
|
||||||
onShippingAddressEdit,
|
onShippingAddressEdit,
|
||||||
onProfileView
|
onProfileView
|
||||||
}: OrderDetailsPageProps) => {
|
}: OrderDetailsPageProps) => {
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const canCancel = maybe(() => order.status) !== OrderStatus.CANCELED;
|
const canCancel = maybe(() => order.status) !== OrderStatus.CANCELED;
|
||||||
const canEditAddresses = maybe(() => order.status) !== OrderStatus.CANCELED;
|
const canEditAddresses = maybe(() => order.status) !== OrderStatus.CANCELED;
|
||||||
const canFulfill = maybe(() => order.status) !== OrderStatus.CANCELED;
|
const canFulfill = maybe(() => order.status) !== OrderStatus.CANCELED;
|
||||||
|
@ -90,7 +93,9 @@ const OrderDetailsPage = withStyles(styles, { name: "OrderDetailsPage" })(
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Container>
|
<Container>
|
||||||
<AppHeader onBack={onBack}>{i18n.t("Orders")}</AppHeader>
|
<AppHeader onBack={onBack}>
|
||||||
|
{intl.formatMessage(sectionNames.orders)}
|
||||||
|
</AppHeader>
|
||||||
<PageHeader
|
<PageHeader
|
||||||
className={classes.header}
|
className={classes.header}
|
||||||
title={maybe(() => order.number) ? "#" + order.number : undefined}
|
title={maybe(() => order.number) ? "#" + order.number : undefined}
|
||||||
|
@ -99,7 +104,10 @@ const OrderDetailsPage = withStyles(styles, { name: "OrderDetailsPage" })(
|
||||||
<CardMenu
|
<CardMenu
|
||||||
menuItems={[
|
menuItems={[
|
||||||
{
|
{
|
||||||
label: i18n.t("Cancel order", { context: "button" }),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Cancel order",
|
||||||
|
description: "button"
|
||||||
|
}),
|
||||||
onSelect: onOrderCancel
|
onSelect: onOrderCancel
|
||||||
}
|
}
|
||||||
]}
|
]}
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
import DialogContentText from "@material-ui/core/DialogContentText";
|
import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ActionDialog from "@saleor/components/ActionDialog";
|
import ActionDialog from "@saleor/components/ActionDialog";
|
||||||
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
|
|
||||||
export interface OrderDraftCancelDialogProps {
|
export interface OrderDraftCancelDialogProps {
|
||||||
confirmButtonState: ConfirmButtonTransitionState;
|
confirmButtonState: ConfirmButtonTransitionState;
|
||||||
|
@ -15,29 +15,31 @@ export interface OrderDraftCancelDialogProps {
|
||||||
|
|
||||||
const OrderDraftCancelDialog: React.StatelessComponent<
|
const OrderDraftCancelDialog: React.StatelessComponent<
|
||||||
OrderDraftCancelDialogProps
|
OrderDraftCancelDialogProps
|
||||||
> = ({ confirmButtonState, onClose, onConfirm, open, orderNumber }) => (
|
> = ({ confirmButtonState, onClose, onConfirm, open, orderNumber }) => {
|
||||||
<ActionDialog
|
const intl = useIntl();
|
||||||
confirmButtonState={confirmButtonState}
|
|
||||||
onClose={onClose}
|
return (
|
||||||
onConfirm={onConfirm}
|
<ActionDialog
|
||||||
open={open}
|
confirmButtonState={confirmButtonState}
|
||||||
title={i18n.t("Remove draft order", {
|
onClose={onClose}
|
||||||
context: "modal title"
|
onConfirm={onConfirm}
|
||||||
})}
|
open={open}
|
||||||
variant="delete"
|
title={intl.formatMessage({
|
||||||
>
|
defaultMessage: "Remove draft order",
|
||||||
<DialogContentText
|
description: "dialog header"
|
||||||
dangerouslySetInnerHTML={{
|
})}
|
||||||
__html: i18n.t(
|
variant="delete"
|
||||||
"Are you sure you want to remove draft <strong>#{{ number }}</strong>?",
|
>
|
||||||
{
|
<DialogContentText>
|
||||||
context: "modal",
|
<FormattedMessage
|
||||||
number: orderNumber
|
defaultMessage="Are you sure you want to remove draft #{number}?"
|
||||||
}
|
values={{
|
||||||
)
|
orderNumber
|
||||||
}}
|
}}
|
||||||
/>
|
/>
|
||||||
</ActionDialog>
|
</DialogContentText>
|
||||||
);
|
</ActionDialog>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderDraftCancelDialog.displayName = "OrderDraftCancelDialog";
|
OrderDraftCancelDialog.displayName = "OrderDraftCancelDialog";
|
||||||
export default OrderDraftCancelDialog;
|
export default OrderDraftCancelDialog;
|
||||||
|
|
|
@ -2,9 +2,9 @@ import Button from "@material-ui/core/Button";
|
||||||
import Card from "@material-ui/core/Card";
|
import Card from "@material-ui/core/Card";
|
||||||
import CardContent from "@material-ui/core/CardContent";
|
import CardContent from "@material-ui/core/CardContent";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
import OrderDraftDetailsProducts, {
|
import OrderDraftDetailsProducts, {
|
||||||
|
@ -29,34 +29,40 @@ const OrderDraftDetails: React.StatelessComponent<OrderDraftDetailsProps> = ({
|
||||||
onOrderLineChange,
|
onOrderLineChange,
|
||||||
onOrderLineRemove,
|
onOrderLineRemove,
|
||||||
onShippingMethodEdit
|
onShippingMethodEdit
|
||||||
}) => (
|
}) => {
|
||||||
<Card>
|
const intl = useIntl();
|
||||||
<CardTitle
|
|
||||||
title={i18n.t("Order details", {
|
return (
|
||||||
context: "card title"
|
<Card>
|
||||||
})}
|
<CardTitle
|
||||||
toolbar={
|
title={intl.formatMessage({
|
||||||
<Button color="primary" variant="text" onClick={onOrderLineAdd}>
|
defaultMessage: "Order Details",
|
||||||
{i18n.t("Add products", {
|
description: "section header"
|
||||||
context: "button"
|
})}
|
||||||
})}
|
toolbar={
|
||||||
</Button>
|
<Button color="primary" variant="text" onClick={onOrderLineAdd}>
|
||||||
}
|
<FormattedMessage
|
||||||
/>
|
defaultMessage="Add products"
|
||||||
<OrderDraftDetailsProducts
|
description="button"
|
||||||
lines={maybe(() => order.lines)}
|
/>
|
||||||
onOrderLineChange={onOrderLineChange}
|
</Button>
|
||||||
onOrderLineRemove={onOrderLineRemove}
|
}
|
||||||
/>
|
/>
|
||||||
{maybe(() => order.lines.length) !== 0 && (
|
<OrderDraftDetailsProducts
|
||||||
<CardContent>
|
lines={maybe(() => order.lines)}
|
||||||
<OrderDraftDetailsSummary
|
onOrderLineChange={onOrderLineChange}
|
||||||
order={order}
|
onOrderLineRemove={onOrderLineRemove}
|
||||||
onShippingMethodEdit={onShippingMethodEdit}
|
/>
|
||||||
/>
|
{maybe(() => order.lines.length) !== 0 && (
|
||||||
</CardContent>
|
<CardContent>
|
||||||
)}
|
<OrderDraftDetailsSummary
|
||||||
</Card>
|
order={order}
|
||||||
);
|
onShippingMethodEdit={onShippingMethodEdit}
|
||||||
|
/>
|
||||||
|
</CardContent>
|
||||||
|
)}
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderDraftDetails.displayName = "OrderDraftDetails";
|
OrderDraftDetails.displayName = "OrderDraftDetails";
|
||||||
export default OrderDraftDetails;
|
export default OrderDraftDetails;
|
||||||
|
|
|
@ -14,6 +14,7 @@ import TextField from "@material-ui/core/TextField";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import DeleteIcon from "@material-ui/icons/Delete";
|
import DeleteIcon from "@material-ui/icons/Delete";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import { DebounceForm } from "@saleor/components/DebounceForm";
|
import { DebounceForm } from "@saleor/components/DebounceForm";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
|
@ -22,7 +23,6 @@ import Skeleton from "@saleor/components/Skeleton";
|
||||||
import TableCellAvatar, {
|
import TableCellAvatar, {
|
||||||
AVATAR_MARGIN
|
AVATAR_MARGIN
|
||||||
} from "@saleor/components/TableCellAvatar";
|
} from "@saleor/components/TableCellAvatar";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe, renderCollection } from "../../../misc";
|
import { maybe, renderCollection } from "../../../misc";
|
||||||
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
||||||
|
|
||||||
|
@ -89,17 +89,26 @@ const OrderDraftDetailsProducts = withStyles(styles, {
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell className={classes.colName}>
|
<TableCell className={classes.colName}>
|
||||||
<span className={classes.colNameLabel}>
|
<span className={classes.colNameLabel}>
|
||||||
{i18n.t("Product", { context: "table header" })}
|
<FormattedMessage defaultMessage="Product" />
|
||||||
</span>
|
</span>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colQuantity}>
|
<TableCell className={classes.colQuantity}>
|
||||||
{i18n.t("Quantity", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Quantity"
|
||||||
|
description="quantity of ordered products"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colPrice}>
|
<TableCell className={classes.colPrice}>
|
||||||
{i18n.t("Price", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Price"
|
||||||
|
description="price or ordered products"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colTotal}>
|
<TableCell className={classes.colTotal}>
|
||||||
{i18n.t("Total", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="total price of ordered products"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colAction} />
|
<TableCell className={classes.colAction} />
|
||||||
</TableRow>
|
</TableRow>
|
||||||
|
@ -109,7 +118,7 @@ const OrderDraftDetailsProducts = withStyles(styles, {
|
||||||
{maybe(() => lines.length) === 0 ? (
|
{maybe(() => lines.length) === 0 ? (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell colSpan={5}>
|
<TableCell colSpan={5}>
|
||||||
{i18n.t("No Products added to Order")}
|
<FormattedMessage defaultMessage="No Products added to Order" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
) : (
|
) : (
|
||||||
|
|
|
@ -5,11 +5,11 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import Link from "@saleor/components/Link";
|
import Link from "@saleor/components/Link";
|
||||||
import Money from "@saleor/components/Money";
|
import Money from "@saleor/components/Money";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
|
|
||||||
|
@ -39,7 +39,12 @@ const OrderDraftDetailsSummary = withStyles(styles, {
|
||||||
<tr>
|
<tr>
|
||||||
{maybe(() => order.subtotal) ? (
|
{maybe(() => order.subtotal) ? (
|
||||||
<>
|
<>
|
||||||
<td>{i18n.t("Subtotal")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Subtotal"
|
||||||
|
description="subtotal price or an order"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
<Money money={order.subtotal.gross} />
|
<Money money={order.subtotal.gross} />
|
||||||
</td>
|
</td>
|
||||||
|
@ -59,11 +64,16 @@ const OrderDraftDetailsSummary = withStyles(styles, {
|
||||||
order.availableShippingMethods.length > 0 ? (
|
order.availableShippingMethods.length > 0 ? (
|
||||||
<td>
|
<td>
|
||||||
<Link onClick={onShippingMethodEdit}>
|
<Link onClick={onShippingMethodEdit}>
|
||||||
{i18n.t("Add shipping carrier")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Add shipping carrier"
|
||||||
|
description="button"
|
||||||
|
/>
|
||||||
</Link>
|
</Link>
|
||||||
</td>
|
</td>
|
||||||
) : (
|
) : (
|
||||||
<td>{i18n.t("No applicable shipping carriers")}</td>
|
<td>
|
||||||
|
<FormattedMessage defaultMessage="No applicable shipping carriers" />
|
||||||
|
</td>
|
||||||
)
|
)
|
||||||
) : (
|
) : (
|
||||||
<>
|
<>
|
||||||
|
@ -90,7 +100,9 @@ const OrderDraftDetailsSummary = withStyles(styles, {
|
||||||
<tr>
|
<tr>
|
||||||
{maybe(() => order.total.tax) !== undefined ? (
|
{maybe(() => order.total.tax) !== undefined ? (
|
||||||
<>
|
<>
|
||||||
<td>{i18n.t("Taxes (VAT included)")}</td>
|
<td>
|
||||||
|
<FormattedMessage defaultMessage="Taxes (VAT included)" />
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
<Money money={order.total.tax} />
|
<Money money={order.total.tax} />
|
||||||
</td>
|
</td>
|
||||||
|
@ -104,7 +116,12 @@ const OrderDraftDetailsSummary = withStyles(styles, {
|
||||||
<tr>
|
<tr>
|
||||||
{maybe(() => order.total.gross) !== undefined ? (
|
{maybe(() => order.total.gross) !== undefined ? (
|
||||||
<>
|
<>
|
||||||
<td>{i18n.t("Total")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="total price of an order"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
<Money money={order.total.gross} />
|
<Money money={order.total.gross} />
|
||||||
</td>
|
</td>
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
import DialogContentText from "@material-ui/core/DialogContentText";
|
import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, IntlShape, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ActionDialog from "@saleor/components/ActionDialog";
|
import ActionDialog from "@saleor/components/ActionDialog";
|
||||||
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
|
|
||||||
export type OrderDraftFinalizeWarning =
|
export type OrderDraftFinalizeWarning =
|
||||||
| "no-shipping"
|
| "no-shipping"
|
||||||
|
@ -21,18 +21,28 @@ export interface OrderDraftFinalizeDialogProps {
|
||||||
onConfirm: () => void;
|
onConfirm: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
const warningToText = (warning: OrderDraftFinalizeWarning) => {
|
const warningToText = (warning: OrderDraftFinalizeWarning, intl: IntlShape) => {
|
||||||
switch (warning) {
|
switch (warning) {
|
||||||
case "no-shipping":
|
case "no-shipping":
|
||||||
return i18n.t("No shipping address");
|
return intl.formatMessage({
|
||||||
|
defaultMessage: "No shipping address"
|
||||||
|
});
|
||||||
case "no-billing":
|
case "no-billing":
|
||||||
return i18n.t("No billing address");
|
return intl.formatMessage({
|
||||||
|
defaultMessage: "No billing address"
|
||||||
|
});
|
||||||
case "no-user":
|
case "no-user":
|
||||||
return i18n.t("No user information");
|
return intl.formatMessage({
|
||||||
|
defaultMessage: "No user information"
|
||||||
|
});
|
||||||
case "no-shipping-method":
|
case "no-shipping-method":
|
||||||
return i18n.t("Some products require shipping, but no method provided");
|
return intl.formatMessage({
|
||||||
|
defaultMessage: "Some products require shipping, but no method provided"
|
||||||
|
});
|
||||||
case "unnecessary-shipping-method":
|
case "unnecessary-shipping-method":
|
||||||
return i18n.t("Shipping method provided, but no product requires it");
|
return intl.formatMessage({
|
||||||
|
defaultMessage: "Shipping method provided, but no product requires it"
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -45,48 +55,54 @@ const OrderDraftFinalizeDialog: React.StatelessComponent<
|
||||||
onClose,
|
onClose,
|
||||||
onConfirm,
|
onConfirm,
|
||||||
orderNumber
|
orderNumber
|
||||||
}) => (
|
}) => {
|
||||||
<ActionDialog
|
const intl = useIntl();
|
||||||
onClose={onClose}
|
|
||||||
onConfirm={onConfirm}
|
return (
|
||||||
open={open}
|
<ActionDialog
|
||||||
title={i18n.t("Finalize draft order", {
|
onClose={onClose}
|
||||||
context: "modal title"
|
onConfirm={onConfirm}
|
||||||
})}
|
open={open}
|
||||||
confirmButtonLabel={
|
title={intl.formatMessage({
|
||||||
warnings.length > 0 ? i18n.t("Finalize anyway") : i18n.t("Finalize")
|
defaultMessage: "Finalize draft order",
|
||||||
}
|
description: "dialog header"
|
||||||
confirmButtonState={confirmButtonState}
|
})}
|
||||||
variant={warnings.length > 0 ? "delete" : "default"}
|
confirmButtonLabel={
|
||||||
>
|
warnings.length > 0
|
||||||
<DialogContentText component="div">
|
? intl.formatMessage({
|
||||||
{warnings.length > 0 && (
|
defaultMessage: "Finalize anyway",
|
||||||
<>
|
description: "button"
|
||||||
<p>
|
})
|
||||||
{i18n.t(
|
: intl.formatMessage({
|
||||||
"There are missing or incorrect informations about this order:"
|
defaultMessage: "Finalize",
|
||||||
)}
|
description: "button"
|
||||||
</p>
|
})
|
||||||
<ul>
|
}
|
||||||
{warnings.map(warning => (
|
confirmButtonState={confirmButtonState}
|
||||||
<li key={warning}>{warningToText(warning)}</li>
|
variant={warnings.length > 0 ? "delete" : "default"}
|
||||||
))}
|
>
|
||||||
</ul>
|
<DialogContentText component="div">
|
||||||
</>
|
{warnings.length > 0 && (
|
||||||
)}
|
<>
|
||||||
<span
|
<p>
|
||||||
dangerouslySetInnerHTML={{
|
<FormattedMessage defaultMessage="There are missing or incorrect informations about this order:" />
|
||||||
__html: i18n.t(
|
</p>
|
||||||
"Are you sure you want to finalize draft <strong>#{{ number }}</strong>?",
|
<ul>
|
||||||
{
|
{warnings.map(warning => (
|
||||||
context: "modal",
|
<li key={warning}>{warningToText(warning, intl)}</li>
|
||||||
number: orderNumber
|
))}
|
||||||
}
|
</ul>
|
||||||
)
|
</>
|
||||||
}}
|
)}
|
||||||
/>
|
<FormattedMessage
|
||||||
</DialogContentText>
|
defaultMessage="Are you sure you want to finalize draft #{number}?"
|
||||||
</ActionDialog>
|
values={{
|
||||||
);
|
orderNumber
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</DialogContentText>
|
||||||
|
</ActionDialog>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderDraftFinalizeDialog.displayName = "OrderDraftFinalize";
|
OrderDraftFinalizeDialog.displayName = "OrderDraftFinalize";
|
||||||
export default OrderDraftFinalizeDialog;
|
export default OrderDraftFinalizeDialog;
|
||||||
|
|
|
@ -10,6 +10,7 @@ import TableCell from "@material-ui/core/TableCell";
|
||||||
import TableFooter from "@material-ui/core/TableFooter";
|
import TableFooter from "@material-ui/core/TableFooter";
|
||||||
import TableRow from "@material-ui/core/TableRow";
|
import TableRow from "@material-ui/core/TableRow";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import Checkbox from "@saleor/components/Checkbox";
|
import Checkbox from "@saleor/components/Checkbox";
|
||||||
import { DateTime } from "@saleor/components/Date";
|
import { DateTime } from "@saleor/components/Date";
|
||||||
|
@ -17,7 +18,6 @@ import Money from "@saleor/components/Money";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import TableHead from "@saleor/components/TableHead";
|
import TableHead from "@saleor/components/TableHead";
|
||||||
import TablePagination from "@saleor/components/TablePagination";
|
import TablePagination from "@saleor/components/TablePagination";
|
||||||
import i18n from "@saleor/i18n";
|
|
||||||
import {
|
import {
|
||||||
maybe,
|
maybe,
|
||||||
renderCollection,
|
renderCollection,
|
||||||
|
@ -85,6 +85,7 @@ export const OrderDraftList = withStyles(styles, { name: "OrderDraftList" })(
|
||||||
status: transformOrderStatus(order.status)
|
status: transformOrderStatus(order.status)
|
||||||
}))
|
}))
|
||||||
: undefined;
|
: undefined;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Table>
|
<Table>
|
||||||
<TableHead
|
<TableHead
|
||||||
|
@ -96,16 +97,22 @@ export const OrderDraftList = withStyles(styles, { name: "OrderDraftList" })(
|
||||||
toolbar={toolbar}
|
toolbar={toolbar}
|
||||||
>
|
>
|
||||||
<TableCell padding="dense" className={classes.colNumber}>
|
<TableCell padding="dense" className={classes.colNumber}>
|
||||||
{i18n.t("No. of Order", { context: "table header" })}
|
<FormattedMessage defaultMessage="No. of Order" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colDate}>
|
<TableCell padding="dense" className={classes.colDate}>
|
||||||
{i18n.t("Date", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Date"
|
||||||
|
description="order draft creation date"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colCustomer}>
|
<TableCell padding="dense" className={classes.colCustomer}>
|
||||||
{i18n.t("Customer", { context: "table header" })}
|
<FormattedMessage defaultMessage="Customer" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colTotal} padding="dense">
|
<TableCell className={classes.colTotal} padding="dense">
|
||||||
{i18n.t("Total", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="order draft total price"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableHead>
|
</TableHead>
|
||||||
<TableFooter>
|
<TableFooter>
|
||||||
|
@ -185,7 +192,7 @@ export const OrderDraftList = withStyles(styles, { name: "OrderDraftList" })(
|
||||||
() => (
|
() => (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell colSpan={numberOfColumns}>
|
<TableCell colSpan={numberOfColumns}>
|
||||||
{i18n.t("No orders found")}
|
<FormattedMessage defaultMessage="No draft orders found" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
)
|
)
|
||||||
|
|
|
@ -2,10 +2,11 @@ import Button from "@material-ui/core/Button";
|
||||||
import Card from "@material-ui/core/Card";
|
import Card from "@material-ui/core/Card";
|
||||||
import AddIcon from "@material-ui/icons/Add";
|
import AddIcon from "@material-ui/icons/Add";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import Container from "@saleor/components/Container";
|
import Container from "@saleor/components/Container";
|
||||||
import PageHeader from "@saleor/components/PageHeader";
|
import PageHeader from "@saleor/components/PageHeader";
|
||||||
import i18n from "@saleor/i18n";
|
import { sectionNames } from "@saleor/intl";
|
||||||
import { ListActions, PageListProps } from "@saleor/types";
|
import { ListActions, PageListProps } from "@saleor/types";
|
||||||
import { OrderDraftList_draftOrders_edges_node } from "../../types/OrderDraftList";
|
import { OrderDraftList_draftOrders_edges_node } from "../../types/OrderDraftList";
|
||||||
import OrderDraftList from "../OrderDraftList";
|
import OrderDraftList from "../OrderDraftList";
|
||||||
|
@ -18,22 +19,30 @@ const OrderDraftListPage: React.StatelessComponent<OrderDraftListPageProps> = ({
|
||||||
disabled,
|
disabled,
|
||||||
onAdd,
|
onAdd,
|
||||||
...listProps
|
...listProps
|
||||||
}) => (
|
}) => {
|
||||||
<Container>
|
const intl = useIntl();
|
||||||
<PageHeader title={i18n.t("Draft Orders")}>
|
|
||||||
<Button
|
return (
|
||||||
color="primary"
|
<Container>
|
||||||
variant="contained"
|
<PageHeader title={intl.formatMessage(sectionNames.draftOrders)}>
|
||||||
disabled={disabled}
|
<Button
|
||||||
onClick={onAdd}
|
color="primary"
|
||||||
>
|
variant="contained"
|
||||||
{i18n.t("Create order", { context: "button" })} <AddIcon />
|
disabled={disabled}
|
||||||
</Button>
|
onClick={onAdd}
|
||||||
</PageHeader>
|
>
|
||||||
<Card>
|
<FormattedMessage
|
||||||
<OrderDraftList disabled={disabled} {...listProps} />
|
defaultMessage="Create order"
|
||||||
</Card>
|
description="button"
|
||||||
</Container>
|
/>
|
||||||
);
|
<AddIcon />
|
||||||
|
</Button>
|
||||||
|
</PageHeader>
|
||||||
|
<Card>
|
||||||
|
<OrderDraftList disabled={disabled} {...listProps} />
|
||||||
|
</Card>
|
||||||
|
</Container>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderDraftListPage.displayName = "OrderDraftListPage";
|
OrderDraftListPage.displayName = "OrderDraftListPage";
|
||||||
export default OrderDraftListPage;
|
export default OrderDraftListPage;
|
||||||
|
|
|
@ -6,6 +6,7 @@ import {
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { useIntl } from "react-intl";
|
||||||
|
|
||||||
import AppHeader from "@saleor/components/AppHeader";
|
import AppHeader from "@saleor/components/AppHeader";
|
||||||
import CardMenu from "@saleor/components/CardMenu";
|
import CardMenu from "@saleor/components/CardMenu";
|
||||||
|
@ -16,8 +17,8 @@ import Grid from "@saleor/components/Grid";
|
||||||
import PageHeader from "@saleor/components/PageHeader";
|
import PageHeader from "@saleor/components/PageHeader";
|
||||||
import SaveButtonBar from "@saleor/components/SaveButtonBar";
|
import SaveButtonBar from "@saleor/components/SaveButtonBar";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
|
import { sectionNames } from "@saleor/intl";
|
||||||
import { SearchCustomers_customers_edges_node } from "../../../containers/SearchCustomers/types/SearchCustomers";
|
import { SearchCustomers_customers_edges_node } from "../../../containers/SearchCustomers/types/SearchCustomers";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { DraftOrderInput } from "../../../types/globalTypes";
|
import { DraftOrderInput } from "../../../types/globalTypes";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
|
@ -87,69 +88,83 @@ const OrderDraftPage = withStyles(styles, { name: "OrderDraftPage" })(
|
||||||
order,
|
order,
|
||||||
users,
|
users,
|
||||||
usersLoading
|
usersLoading
|
||||||
}: OrderDraftPageProps) => (
|
}: OrderDraftPageProps) => {
|
||||||
<Container>
|
const intl = useIntl();
|
||||||
<AppHeader onBack={onBack}>{i18n.t("Orders")}</AppHeader>
|
|
||||||
<PageHeader
|
return (
|
||||||
className={classes.header}
|
<Container>
|
||||||
title={maybe(() => order.number) ? "#" + order.number : undefined}
|
<AppHeader onBack={onBack}>
|
||||||
>
|
{intl.formatMessage(sectionNames.draftOrders)}
|
||||||
<CardMenu
|
</AppHeader>
|
||||||
menuItems={[
|
<PageHeader
|
||||||
{
|
className={classes.header}
|
||||||
label: i18n.t("Cancel order", { context: "button" }),
|
title={maybe(() => order.number) ? "#" + order.number : undefined}
|
||||||
onSelect: onDraftRemove
|
>
|
||||||
}
|
<CardMenu
|
||||||
]}
|
menuItems={[
|
||||||
|
{
|
||||||
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Cancel order",
|
||||||
|
description: "button"
|
||||||
|
}),
|
||||||
|
onSelect: onDraftRemove
|
||||||
|
}
|
||||||
|
]}
|
||||||
|
/>
|
||||||
|
</PageHeader>
|
||||||
|
<div className={classes.date}>
|
||||||
|
{order && order.created ? (
|
||||||
|
<Typography variant="caption">
|
||||||
|
<DateTime date={order.created} />
|
||||||
|
</Typography>
|
||||||
|
) : (
|
||||||
|
<Skeleton style={{ width: "10em" }} />
|
||||||
|
)}
|
||||||
|
</div>
|
||||||
|
<Grid>
|
||||||
|
<div>
|
||||||
|
<OrderDraftDetails
|
||||||
|
order={order}
|
||||||
|
onOrderLineAdd={onOrderLineAdd}
|
||||||
|
onOrderLineChange={onOrderLineChange}
|
||||||
|
onOrderLineRemove={onOrderLineRemove}
|
||||||
|
onShippingMethodEdit={onShippingMethodEdit}
|
||||||
|
/>
|
||||||
|
<OrderHistory
|
||||||
|
history={maybe(() => order.events)}
|
||||||
|
onNoteAdd={onNoteAdd}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
<div>
|
||||||
|
<OrderCustomer
|
||||||
|
canEditAddresses={true}
|
||||||
|
canEditCustomer={true}
|
||||||
|
order={order}
|
||||||
|
users={users}
|
||||||
|
loading={usersLoading}
|
||||||
|
fetchUsers={fetchUsers}
|
||||||
|
onBillingAddressEdit={onBillingAddressEdit}
|
||||||
|
onCustomerEdit={onCustomerEdit}
|
||||||
|
onShippingAddressEdit={onShippingAddressEdit}
|
||||||
|
onProfileView={onProfileView}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</Grid>
|
||||||
|
<SaveButtonBar
|
||||||
|
state={saveButtonBarState}
|
||||||
|
disabled={disabled || !maybe(() => order.canFinalize)}
|
||||||
|
onCancel={onBack}
|
||||||
|
onSave={onDraftFinalize}
|
||||||
|
labels={{
|
||||||
|
save: intl.formatMessage({
|
||||||
|
defaultMessage: "Finalize",
|
||||||
|
description: "button"
|
||||||
|
})
|
||||||
|
}}
|
||||||
/>
|
/>
|
||||||
</PageHeader>
|
</Container>
|
||||||
<div className={classes.date}>
|
);
|
||||||
{order && order.created ? (
|
}
|
||||||
<Typography variant="caption">
|
|
||||||
<DateTime date={order.created} />
|
|
||||||
</Typography>
|
|
||||||
) : (
|
|
||||||
<Skeleton style={{ width: "10em" }} />
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
<Grid>
|
|
||||||
<div>
|
|
||||||
<OrderDraftDetails
|
|
||||||
order={order}
|
|
||||||
onOrderLineAdd={onOrderLineAdd}
|
|
||||||
onOrderLineChange={onOrderLineChange}
|
|
||||||
onOrderLineRemove={onOrderLineRemove}
|
|
||||||
onShippingMethodEdit={onShippingMethodEdit}
|
|
||||||
/>
|
|
||||||
<OrderHistory
|
|
||||||
history={maybe(() => order.events)}
|
|
||||||
onNoteAdd={onNoteAdd}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<OrderCustomer
|
|
||||||
canEditAddresses={true}
|
|
||||||
canEditCustomer={true}
|
|
||||||
order={order}
|
|
||||||
users={users}
|
|
||||||
loading={usersLoading}
|
|
||||||
fetchUsers={fetchUsers}
|
|
||||||
onBillingAddressEdit={onBillingAddressEdit}
|
|
||||||
onCustomerEdit={onCustomerEdit}
|
|
||||||
onShippingAddressEdit={onShippingAddressEdit}
|
|
||||||
onProfileView={onProfileView}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</Grid>
|
|
||||||
<SaveButtonBar
|
|
||||||
state={saveButtonBarState}
|
|
||||||
disabled={disabled || !maybe(() => order.canFinalize)}
|
|
||||||
onCancel={onBack}
|
|
||||||
onSave={onDraftFinalize}
|
|
||||||
labels={{ save: i18n.t("Finalize", { context: "button" }) }}
|
|
||||||
/>
|
|
||||||
</Container>
|
|
||||||
)
|
|
||||||
);
|
);
|
||||||
OrderDraftPage.displayName = "OrderDraftPage";
|
OrderDraftPage.displayName = "OrderDraftPage";
|
||||||
export default OrderDraftPage;
|
export default OrderDraftPage;
|
||||||
|
|
|
@ -14,6 +14,7 @@ import TableHead from "@material-ui/core/TableHead";
|
||||||
import TableRow from "@material-ui/core/TableRow";
|
import TableRow from "@material-ui/core/TableRow";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardMenu from "@saleor/components/CardMenu";
|
import CardMenu from "@saleor/components/CardMenu";
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
|
@ -23,7 +24,6 @@ import StatusLabel from "@saleor/components/StatusLabel";
|
||||||
import TableCellAvatar, {
|
import TableCellAvatar, {
|
||||||
AVATAR_MARGIN
|
AVATAR_MARGIN
|
||||||
} from "@saleor/components/TableCellAvatar";
|
} from "@saleor/components/TableCellAvatar";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe, renderCollection } from "../../../misc";
|
import { maybe, renderCollection } from "../../../misc";
|
||||||
import { FulfillmentStatus } from "../../../types/globalTypes";
|
import { FulfillmentStatus } from "../../../types/globalTypes";
|
||||||
import { OrderDetails_order_fulfillments } from "../../types/OrderDetails";
|
import { OrderDetails_order_fulfillments } from "../../types/OrderDetails";
|
||||||
|
@ -81,8 +81,14 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
onOrderFulfillmentCancel,
|
onOrderFulfillmentCancel,
|
||||||
onTrackingCodeAdd
|
onTrackingCodeAdd
|
||||||
}: OrderFulfillmentProps) => {
|
}: OrderFulfillmentProps) => {
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const lines = maybe(() => fulfillment.lines);
|
const lines = maybe(() => fulfillment.lines);
|
||||||
const status = maybe(() => fulfillment.status);
|
const status = maybe(() => fulfillment.status);
|
||||||
|
const quantity = lines
|
||||||
|
.map(line => line.quantity)
|
||||||
|
.reduce((prev, curr) => prev + curr, 0);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Card>
|
<Card>
|
||||||
<CardTitle
|
<CardTitle
|
||||||
|
@ -92,16 +98,24 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
label={
|
label={
|
||||||
<>
|
<>
|
||||||
{status === FulfillmentStatus.FULFILLED
|
{status === FulfillmentStatus.FULFILLED
|
||||||
? i18n.t("Fulfilled ({{ quantity }})", {
|
? intl.formatMessage(
|
||||||
quantity: lines
|
{
|
||||||
.map(line => line.quantity)
|
defaultMessage: "Fulfilled ({quantity})",
|
||||||
.reduce((prev, curr) => prev + curr, 0)
|
description: "section header"
|
||||||
})
|
},
|
||||||
: i18n.t("Cancelled ({{ quantity }})", {
|
{
|
||||||
quantity: lines
|
quantity
|
||||||
.map(line => line.quantity)
|
}
|
||||||
.reduce((prev, curr) => prev + curr, 0)
|
)
|
||||||
})}
|
: intl.formatMessage(
|
||||||
|
{
|
||||||
|
defaultMessage: "Fulfilled ({quantity})",
|
||||||
|
description: "section header"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
quantity
|
||||||
|
}
|
||||||
|
)}
|
||||||
<Typography className={classes.orderNumber} variant="body2">
|
<Typography className={classes.orderNumber} variant="body2">
|
||||||
{maybe(
|
{maybe(
|
||||||
() => `#${orderNumber}-${fulfillment.fulfillmentOrder}`
|
() => `#${orderNumber}-${fulfillment.fulfillmentOrder}`
|
||||||
|
@ -122,8 +136,9 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
<CardMenu
|
<CardMenu
|
||||||
menuItems={[
|
menuItems={[
|
||||||
{
|
{
|
||||||
label: i18n.t("Cancel shipment", {
|
label: intl.formatMessage({
|
||||||
context: "button"
|
defaultMessage: "Cancel shipment",
|
||||||
|
description: "button"
|
||||||
}),
|
}),
|
||||||
onSelect: onOrderFulfillmentCancel
|
onSelect: onOrderFulfillmentCancel
|
||||||
}
|
}
|
||||||
|
@ -137,17 +152,29 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell className={classes.colName}>
|
<TableCell className={classes.colName}>
|
||||||
<span className={classes.colNameLabel}>
|
<span className={classes.colNameLabel}>
|
||||||
{i18n.t("Product")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Product"
|
||||||
|
description="product name"
|
||||||
|
/>
|
||||||
</span>
|
</span>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colQuantity}>
|
<TableCell className={classes.colQuantity}>
|
||||||
{i18n.t("Quantity")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Quantity"
|
||||||
|
description="ordered product quantity"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colPrice}>
|
<TableCell className={classes.colPrice}>
|
||||||
{i18n.t("Price")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Price"
|
||||||
|
description="product price"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colTotal}>
|
<TableCell className={classes.colTotal}>
|
||||||
{i18n.t("Total")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="order line total price"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
</TableHead>
|
</TableHead>
|
||||||
|
@ -194,9 +221,12 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
{maybe(() => fulfillment.trackingNumber) && (
|
{maybe(() => fulfillment.trackingNumber) && (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell colSpan={numberOfColumns}>
|
<TableCell colSpan={numberOfColumns}>
|
||||||
{i18n.t("Tracking Number: {{ trackingNumber }}", {
|
<FormattedMessage
|
||||||
trackingNumber: fulfillment.trackingNumber
|
defaultMessage="Tracking Number: {trackingNumber}"
|
||||||
})}
|
values={{
|
||||||
|
trackingNumber: fulfillment.trackingNumber
|
||||||
|
}}
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
)}
|
)}
|
||||||
|
@ -205,7 +235,10 @@ const OrderFulfillment = withStyles(styles, { name: "OrderFulfillment" })(
|
||||||
{status === FulfillmentStatus.FULFILLED && !fulfillment.trackingNumber && (
|
{status === FulfillmentStatus.FULFILLED && !fulfillment.trackingNumber && (
|
||||||
<CardActions>
|
<CardActions>
|
||||||
<Button color="primary" onClick={onTrackingCodeAdd}>
|
<Button color="primary" onClick={onTrackingCodeAdd}>
|
||||||
{i18n.t("Add tracking")}
|
<FormattedMessage
|
||||||
|
defaultMessage="Add tracking"
|
||||||
|
description="fulfillment group tracking number"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
</CardActions>
|
</CardActions>
|
||||||
)}
|
)}
|
||||||
|
|
|
@ -11,13 +11,14 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import { ControlledCheckbox } from "@saleor/components/ControlledCheckbox";
|
import { ControlledCheckbox } from "@saleor/components/ControlledCheckbox";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
export interface FormData {
|
export interface FormData {
|
||||||
restock: boolean;
|
restock: boolean;
|
||||||
|
@ -50,43 +51,56 @@ const OrderFulfillmentCancelDialog = withStyles(styles, {
|
||||||
open,
|
open,
|
||||||
onConfirm,
|
onConfirm,
|
||||||
onClose
|
onClose
|
||||||
}: OrderFulfillmentCancelDialogProps) => (
|
}: OrderFulfillmentCancelDialogProps) => {
|
||||||
<Dialog onClose={onClose} open={open}>
|
const intl = useIntl();
|
||||||
<Form initial={{ restock: true }} onSubmit={onConfirm}>
|
|
||||||
{({ change, data, submit }) => (
|
return (
|
||||||
<>
|
<Dialog onClose={onClose} open={open}>
|
||||||
<DialogTitle>
|
<Form initial={{ restock: true }} onSubmit={onConfirm}>
|
||||||
{i18n.t("Cancel fulfillment", { context: "title" })}
|
{({ change, data, submit }) => (
|
||||||
</DialogTitle>
|
<>
|
||||||
<DialogContent>
|
<DialogTitle>
|
||||||
<DialogContentText>
|
<FormattedMessage
|
||||||
{i18n.t("Are you sure you want to cancel this fulfillment?")}
|
defaultMessage="Cancel Fulfillment"
|
||||||
</DialogContentText>
|
description="dialog header"
|
||||||
<ControlledCheckbox
|
/>
|
||||||
checked={data.restock}
|
</DialogTitle>
|
||||||
label={i18n.t("Restock items?")}
|
<DialogContent>
|
||||||
name="restock"
|
<DialogContentText>
|
||||||
onChange={change}
|
<FormattedMessage defaultMessage="Are you sure you want to cancel this fulfillment?" />
|
||||||
/>
|
</DialogContentText>
|
||||||
</DialogContent>
|
<ControlledCheckbox
|
||||||
<DialogActions>
|
checked={data.restock}
|
||||||
<Button onClick={onClose}>
|
label={intl.formatMessage({
|
||||||
{i18n.t("Back", { context: "button" })}
|
defaultMessage: "Restock items?",
|
||||||
</Button>
|
description: "switch button"
|
||||||
<ConfirmButton
|
})}
|
||||||
transitionState={confirmButtonState}
|
name="restock"
|
||||||
className={classes.deleteButton}
|
onChange={change}
|
||||||
variant="contained"
|
/>
|
||||||
onClick={submit}
|
</DialogContent>
|
||||||
>
|
<DialogActions>
|
||||||
{i18n.t("Cancel fulfillment", { context: "button" })}
|
<Button onClick={onClose}>
|
||||||
</ConfirmButton>
|
<FormattedMessage {...buttonMessages.back} />
|
||||||
</DialogActions>
|
</Button>
|
||||||
</>
|
<ConfirmButton
|
||||||
)}
|
transitionState={confirmButtonState}
|
||||||
</Form>
|
className={classes.deleteButton}
|
||||||
</Dialog>
|
variant="contained"
|
||||||
)
|
onClick={submit}
|
||||||
|
>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Cancel fulfillment"
|
||||||
|
description="button"
|
||||||
|
/>
|
||||||
|
</ConfirmButton>
|
||||||
|
</DialogActions>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</Form>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
}
|
||||||
);
|
);
|
||||||
OrderFulfillmentCancelDialog.displayName = "OrderFulfillmentCancelDialog";
|
OrderFulfillmentCancelDialog.displayName = "OrderFulfillmentCancelDialog";
|
||||||
export default OrderFulfillmentCancelDialog;
|
export default OrderFulfillmentCancelDialog;
|
||||||
|
|
|
@ -16,6 +16,7 @@ import TableHead from "@material-ui/core/TableHead";
|
||||||
import TableRow from "@material-ui/core/TableRow";
|
import TableRow from "@material-ui/core/TableRow";
|
||||||
import TextField from "@material-ui/core/TextField";
|
import TextField from "@material-ui/core/TextField";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
|
@ -25,7 +26,7 @@ import { FormSpacer } from "@saleor/components/FormSpacer";
|
||||||
import TableCellAvatar, {
|
import TableCellAvatar, {
|
||||||
AVATAR_MARGIN
|
AVATAR_MARGIN
|
||||||
} from "@saleor/components/TableCellAvatar";
|
} from "@saleor/components/TableCellAvatar";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
||||||
|
|
||||||
|
@ -83,125 +84,143 @@ const OrderFulfillmentDialog = withStyles(styles, {
|
||||||
lines,
|
lines,
|
||||||
onClose,
|
onClose,
|
||||||
onSubmit
|
onSubmit
|
||||||
}: OrderFulfillmentDialogProps) => (
|
}: OrderFulfillmentDialogProps) => {
|
||||||
<Dialog onClose={onClose} open={open}>
|
const intl = useIntl();
|
||||||
<Form
|
|
||||||
initial={{
|
return (
|
||||||
lines: maybe(
|
<Dialog onClose={onClose} open={open}>
|
||||||
() =>
|
<Form
|
||||||
lines.map(
|
initial={{
|
||||||
product => product.quantity - product.quantityFulfilled
|
lines: maybe(
|
||||||
),
|
() =>
|
||||||
[]
|
lines.map(
|
||||||
),
|
product => product.quantity - product.quantityFulfilled
|
||||||
trackingNumber: ""
|
),
|
||||||
}}
|
[]
|
||||||
onSubmit={onSubmit}
|
),
|
||||||
>
|
trackingNumber: ""
|
||||||
{({ data, change }) => {
|
}}
|
||||||
const handleQuantityChange = (
|
onSubmit={onSubmit}
|
||||||
productIndex: number,
|
>
|
||||||
event: React.ChangeEvent<any>
|
{({ data, change }) => {
|
||||||
) => {
|
const handleQuantityChange = (
|
||||||
const newData = data.lines;
|
productIndex: number,
|
||||||
newData[productIndex] = event.target.value;
|
event: React.ChangeEvent<any>
|
||||||
change({
|
) => {
|
||||||
target: {
|
const newData = data.lines;
|
||||||
name: "lines",
|
newData[productIndex] = event.target.value;
|
||||||
value: newData
|
change({
|
||||||
}
|
target: {
|
||||||
} as any);
|
name: "lines",
|
||||||
};
|
value: newData
|
||||||
return (
|
}
|
||||||
<>
|
} as any);
|
||||||
<DialogTitle>{i18n.t("Fulfill products")}</DialogTitle>
|
};
|
||||||
<Table className={classes.table}>
|
return (
|
||||||
<TableHead>
|
<>
|
||||||
<TableRow>
|
<DialogTitle>
|
||||||
<TableCell className={classes.colName}>
|
<FormattedMessage
|
||||||
<span className={classes.colNameLabel}>
|
defaultMessage="Fulfill products"
|
||||||
{i18n.t("Product name")}
|
description="dialog header"
|
||||||
</span>
|
/>
|
||||||
</TableCell>
|
</DialogTitle>
|
||||||
<TableCell className={classes.colSku}>
|
<Table className={classes.table}>
|
||||||
{i18n.t("SKU")}
|
<TableHead>
|
||||||
</TableCell>
|
<TableRow>
|
||||||
<TableCell className={classes.colQuantity}>
|
<TableCell className={classes.colName}>
|
||||||
{i18n.t("Quantity")}
|
<span className={classes.colNameLabel}>
|
||||||
</TableCell>
|
<FormattedMessage defaultMessage="Product name" />
|
||||||
</TableRow>
|
</span>
|
||||||
</TableHead>
|
</TableCell>
|
||||||
<TableBody>
|
<TableCell className={classes.colSku}>
|
||||||
{lines.map((product, productIndex) => {
|
<FormattedMessage
|
||||||
const remainingQuantity =
|
defaultMessage="SKU"
|
||||||
product.quantity - product.quantityFulfilled;
|
description="product's sku"
|
||||||
return (
|
/>
|
||||||
<TableRow key={product.id}>
|
</TableCell>
|
||||||
<TableCellAvatar
|
<TableCell className={classes.colQuantity}>
|
||||||
className={classes.colName}
|
<FormattedMessage
|
||||||
thumbnail={maybe(() => product.thumbnail.url)}
|
defaultMessage="Quantity"
|
||||||
>
|
description="quantity of fulfilled products"
|
||||||
{product.productName}
|
/>
|
||||||
</TableCellAvatar>
|
</TableCell>
|
||||||
<TableCell className={classes.colSku}>
|
</TableRow>
|
||||||
{product.productSku}
|
</TableHead>
|
||||||
</TableCell>
|
<TableBody>
|
||||||
<TableCell className={classes.colQuantity}>
|
{lines.map((product, productIndex) => {
|
||||||
<div className={classes.colQuantityContent}>
|
const remainingQuantity =
|
||||||
<TextField
|
product.quantity - product.quantityFulfilled;
|
||||||
type="number"
|
return (
|
||||||
inputProps={{
|
<TableRow key={product.id}>
|
||||||
max: remainingQuantity,
|
<TableCellAvatar
|
||||||
style: { textAlign: "right" }
|
className={classes.colName}
|
||||||
}}
|
thumbnail={maybe(() => product.thumbnail.url)}
|
||||||
className={classes.quantityInput}
|
>
|
||||||
value={data.lines[productIndex]}
|
{product.productName}
|
||||||
onChange={event =>
|
</TableCellAvatar>
|
||||||
handleQuantityChange(productIndex, event)
|
<TableCell className={classes.colSku}>
|
||||||
}
|
{product.productSku}
|
||||||
error={
|
</TableCell>
|
||||||
remainingQuantity < data.lines[productIndex]
|
<TableCell className={classes.colQuantity}>
|
||||||
}
|
<div className={classes.colQuantityContent}>
|
||||||
/>
|
<TextField
|
||||||
<div className={classes.remainingQuantity}>
|
type="number"
|
||||||
/ {remainingQuantity}
|
inputProps={{
|
||||||
|
max: remainingQuantity,
|
||||||
|
style: { textAlign: "right" }
|
||||||
|
}}
|
||||||
|
className={classes.quantityInput}
|
||||||
|
value={data.lines[productIndex]}
|
||||||
|
onChange={event =>
|
||||||
|
handleQuantityChange(productIndex, event)
|
||||||
|
}
|
||||||
|
error={
|
||||||
|
remainingQuantity < data.lines[productIndex]
|
||||||
|
}
|
||||||
|
/>
|
||||||
|
<div className={classes.remainingQuantity}>
|
||||||
|
/ {remainingQuantity}
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</TableCell>
|
||||||
</TableCell>
|
</TableRow>
|
||||||
</TableRow>
|
);
|
||||||
);
|
})}
|
||||||
})}
|
</TableBody>
|
||||||
</TableBody>
|
</Table>
|
||||||
</Table>
|
<DialogContent>
|
||||||
<DialogContent>
|
<FormSpacer />
|
||||||
<FormSpacer />
|
<TextField
|
||||||
<TextField
|
fullWidth
|
||||||
fullWidth
|
label={intl.formatMessage({
|
||||||
label={i18n.t("Tracking number")}
|
defaultMessage: "Tracking number",
|
||||||
name="trackingNumber"
|
description: "fulfillment group"
|
||||||
value={data.trackingNumber}
|
})}
|
||||||
onChange={change}
|
name="trackingNumber"
|
||||||
/>
|
value={data.trackingNumber}
|
||||||
</DialogContent>
|
onChange={change}
|
||||||
<DialogActions>
|
/>
|
||||||
<Button onClick={onClose}>
|
</DialogContent>
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
<DialogActions>
|
||||||
</Button>
|
<Button onClick={onClose}>
|
||||||
<ConfirmButton
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
transitionState={confirmButtonState}
|
</Button>
|
||||||
color="primary"
|
<ConfirmButton
|
||||||
variant="contained"
|
transitionState={confirmButtonState}
|
||||||
type="submit"
|
color="primary"
|
||||||
>
|
variant="contained"
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
type="submit"
|
||||||
</ConfirmButton>
|
>
|
||||||
</DialogActions>
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</>
|
</ConfirmButton>
|
||||||
);
|
</DialogActions>
|
||||||
}}
|
</>
|
||||||
</Form>
|
);
|
||||||
</Dialog>
|
}}
|
||||||
)
|
</Form>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
}
|
||||||
);
|
);
|
||||||
OrderFulfillmentDialog.displayName = "OrderFulfillmentDialog";
|
OrderFulfillmentDialog.displayName = "OrderFulfillmentDialog";
|
||||||
export default OrderFulfillmentDialog;
|
export default OrderFulfillmentDialog;
|
||||||
|
|
|
@ -5,12 +5,13 @@ import DialogContent from "@material-ui/core/DialogContent";
|
||||||
import DialogTitle from "@material-ui/core/DialogTitle";
|
import DialogTitle from "@material-ui/core/DialogTitle";
|
||||||
import TextField from "@material-ui/core/TextField";
|
import TextField from "@material-ui/core/TextField";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
export interface FormData {
|
export interface FormData {
|
||||||
trackingNumber: string;
|
trackingNumber: string;
|
||||||
|
@ -26,40 +27,49 @@ interface OrderFulfillmentTrackingDialogProps {
|
||||||
|
|
||||||
const OrderFulfillmentTrackingDialog: React.StatelessComponent<
|
const OrderFulfillmentTrackingDialog: React.StatelessComponent<
|
||||||
OrderFulfillmentTrackingDialogProps
|
OrderFulfillmentTrackingDialogProps
|
||||||
> = ({ confirmButtonState, open, trackingNumber, onConfirm, onClose }) => (
|
> = ({ confirmButtonState, open, trackingNumber, onConfirm, onClose }) => {
|
||||||
<Dialog onClose={onClose} open={open}>
|
const intl = useIntl();
|
||||||
<Form initial={{ trackingNumber }} onSubmit={onConfirm}>
|
|
||||||
{({ change, data, submit }) => (
|
return (
|
||||||
<>
|
<Dialog onClose={onClose} open={open}>
|
||||||
<DialogTitle>
|
<Form initial={{ trackingNumber }} onSubmit={onConfirm}>
|
||||||
{i18n.t("Add tracking code", { context: "title" })}
|
{({ change, data, submit }) => (
|
||||||
</DialogTitle>
|
<>
|
||||||
<DialogContent>
|
<DialogTitle>
|
||||||
<TextField
|
<FormattedMessage
|
||||||
label={i18n.t("Tracking number")}
|
defaultMessage="Add tracking code"
|
||||||
name="trackingNumber"
|
description="dialog header"
|
||||||
onChange={change}
|
/>
|
||||||
value={data.trackingNumber}
|
</DialogTitle>
|
||||||
fullWidth
|
<DialogContent>
|
||||||
/>
|
<TextField
|
||||||
</DialogContent>
|
label={intl.formatMessage({
|
||||||
<DialogActions>
|
defaultMessage: "Tracking number"
|
||||||
<Button onClick={onClose}>
|
})}
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
name="trackingNumber"
|
||||||
</Button>
|
onChange={change}
|
||||||
<ConfirmButton
|
value={data.trackingNumber}
|
||||||
transitionState={confirmButtonState}
|
fullWidth
|
||||||
color="primary"
|
/>
|
||||||
variant="contained"
|
</DialogContent>
|
||||||
onClick={submit}
|
<DialogActions>
|
||||||
>
|
<Button onClick={onClose}>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
</ConfirmButton>
|
</Button>
|
||||||
</DialogActions>
|
<ConfirmButton
|
||||||
</>
|
transitionState={confirmButtonState}
|
||||||
)}
|
color="primary"
|
||||||
</Form>
|
variant="contained"
|
||||||
</Dialog>
|
onClick={submit}
|
||||||
);
|
>
|
||||||
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
|
</ConfirmButton>
|
||||||
|
</DialogActions>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</Form>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderFulfillmentTrackingDialog.displayName = "OrderFulfillmentTrackingDialog";
|
OrderFulfillmentTrackingDialog.displayName = "OrderFulfillmentTrackingDialog";
|
||||||
export default OrderFulfillmentTrackingDialog;
|
export default OrderFulfillmentTrackingDialog;
|
||||||
|
|
|
@ -6,6 +6,7 @@ import {
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import Typography from "@material-ui/core/Typography";
|
import Typography from "@material-ui/core/Typography";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, IntlShape, useIntl } from "react-intl";
|
||||||
|
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import Hr from "@saleor/components/Hr";
|
import Hr from "@saleor/components/Hr";
|
||||||
|
@ -16,7 +17,6 @@ import {
|
||||||
TimelineEvent,
|
TimelineEvent,
|
||||||
TimelineNote
|
TimelineNote
|
||||||
} from "@saleor/components/Timeline";
|
} from "@saleor/components/Timeline";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import {
|
import {
|
||||||
OrderEventsEmailsEnum,
|
OrderEventsEmailsEnum,
|
||||||
OrderEventsEnum
|
OrderEventsEnum
|
||||||
|
@ -27,115 +27,152 @@ export interface FormData {
|
||||||
message: string;
|
message: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
const getEventMessage = (event: OrderDetails_order_events) => {
|
const getEventMessage = (event: OrderDetails_order_events, intl: IntlShape) => {
|
||||||
switch (event.type) {
|
switch (event.type) {
|
||||||
case OrderEventsEnum.CANCELED:
|
case OrderEventsEnum.CANCELED:
|
||||||
return i18n.t("Order was cancelled", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order was cancelled",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.DRAFT_ADDED_PRODUCTS:
|
case OrderEventsEnum.DRAFT_ADDED_PRODUCTS:
|
||||||
return i18n.t("Products were added to draft order", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Products were added to draft order",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.DRAFT_CREATED:
|
case OrderEventsEnum.DRAFT_CREATED:
|
||||||
return i18n.t("Draft order was created", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Draft order was created",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.DRAFT_REMOVED_PRODUCTS:
|
case OrderEventsEnum.DRAFT_REMOVED_PRODUCTS:
|
||||||
return i18n.t("Products were removed from draft order", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Products were removed from draft order",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.EMAIL_SENT:
|
case OrderEventsEnum.EMAIL_SENT:
|
||||||
switch (event.emailType) {
|
switch (event.emailType) {
|
||||||
case OrderEventsEmailsEnum.DIGITAL_LINKS:
|
case OrderEventsEmailsEnum.DIGITAL_LINKS:
|
||||||
return i18n.t("Links to the order's digital goods were sent", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Links to the order's digital goods were sent",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEmailsEnum.FULFILLMENT_CONFIRMATION:
|
case OrderEventsEmailsEnum.FULFILLMENT_CONFIRMATION:
|
||||||
return i18n.t("Fulfillment confirmation was sent to customer", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Fulfillment confirmation was sent to customer",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEmailsEnum.ORDER_CONFIRMATION:
|
case OrderEventsEmailsEnum.ORDER_CONFIRMATION:
|
||||||
return i18n.t("Order confirmation was sent to customer", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order confirmation was sent to customer",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEmailsEnum.PAYMENT_CONFIRMATION:
|
case OrderEventsEmailsEnum.PAYMENT_CONFIRMATION:
|
||||||
return i18n.t("Payment confirmation was sent to customer", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Payment confirmation was sent to customer",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEmailsEnum.SHIPPING_CONFIRMATION:
|
case OrderEventsEmailsEnum.SHIPPING_CONFIRMATION:
|
||||||
return i18n.t("Shipping details was sent to customer", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Shipping details was sent to customer",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEmailsEnum.TRACKING_UPDATED:
|
case OrderEventsEmailsEnum.TRACKING_UPDATED:
|
||||||
return i18n.t("Shipping tracking number was sent to customer", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Shipping tracking number was sent to customer",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
case OrderEventsEnum.FULFILLMENT_CANCELED:
|
case OrderEventsEnum.FULFILLMENT_CANCELED:
|
||||||
return i18n.t("Fulfillment was cancelled", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Fulfillment was cancelled",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.FULFILLMENT_FULFILLED_ITEMS:
|
case OrderEventsEnum.FULFILLMENT_FULFILLED_ITEMS:
|
||||||
return i18n.t("Fulfilled {{ quantity }} items", {
|
return intl.formatMessage(
|
||||||
context: "order history message",
|
{
|
||||||
quantity: event.quantity
|
defaultMessage: "Fulfilled {quantity} items",
|
||||||
});
|
description: "order history message"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
quantity: event.quantity
|
||||||
|
}
|
||||||
|
);
|
||||||
case OrderEventsEnum.FULFILLMENT_RESTOCKED_ITEMS:
|
case OrderEventsEnum.FULFILLMENT_RESTOCKED_ITEMS:
|
||||||
return i18n.t("Restocked {{ quantity }} items", {
|
return intl.formatMessage(
|
||||||
context: "order history message",
|
{
|
||||||
quantity: event.quantity
|
defaultMessage: "Restocked {quantity} items",
|
||||||
});
|
description: "order history message"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
quantity: event.quantity
|
||||||
|
}
|
||||||
|
);
|
||||||
case OrderEventsEnum.NOTE_ADDED:
|
case OrderEventsEnum.NOTE_ADDED:
|
||||||
return i18n.t("Note was added to the order", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Note was added to the order",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.ORDER_FULLY_PAID:
|
case OrderEventsEnum.ORDER_FULLY_PAID:
|
||||||
return i18n.t("Order was fully paid", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order was fully paid",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.ORDER_MARKED_AS_PAID:
|
case OrderEventsEnum.ORDER_MARKED_AS_PAID:
|
||||||
return i18n.t("Marked order as paid", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Marked order as paid",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.OTHER:
|
case OrderEventsEnum.OTHER:
|
||||||
return event.message;
|
return event.message;
|
||||||
case OrderEventsEnum.OVERSOLD_ITEMS:
|
case OrderEventsEnum.OVERSOLD_ITEMS:
|
||||||
return i18n.t("Oversold {{ quantity }} items", {
|
return intl.formatMessage(
|
||||||
context: "order history message",
|
{
|
||||||
quantity: event.quantity
|
defaultMessage: "Oversold {quantity} items",
|
||||||
});
|
description: "order history message"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
quantity: event.quantity
|
||||||
|
}
|
||||||
|
);
|
||||||
case OrderEventsEnum.PAYMENT_CAPTURED:
|
case OrderEventsEnum.PAYMENT_CAPTURED:
|
||||||
return i18n.t("Payment was captured", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Payment was captured",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.PAYMENT_FAILED:
|
case OrderEventsEnum.PAYMENT_FAILED:
|
||||||
return i18n.t("Payment failed", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Payment failed",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.PAYMENT_REFUNDED:
|
case OrderEventsEnum.PAYMENT_REFUNDED:
|
||||||
return i18n.t("Payment was refunded", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Payment was refunded",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.PAYMENT_VOIDED:
|
case OrderEventsEnum.PAYMENT_VOIDED:
|
||||||
return i18n.t("Payment was voided", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Payment was voided",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.PLACED:
|
case OrderEventsEnum.PLACED:
|
||||||
return i18n.t("Order was placed", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order was placed",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.PLACED_FROM_DRAFT:
|
case OrderEventsEnum.PLACED_FROM_DRAFT:
|
||||||
return i18n.t("Order was created from draft", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order was created from draft",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.TRACKING_UPDATED:
|
case OrderEventsEnum.TRACKING_UPDATED:
|
||||||
return i18n.t("Updated fulfillment group's tracking number", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Updated fulfillment group's tracking number",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
case OrderEventsEnum.UPDATED_ADDRESS:
|
case OrderEventsEnum.UPDATED_ADDRESS:
|
||||||
return i18n.t("Order address was updated", {
|
return intl.formatMessage({
|
||||||
context: "order history message"
|
defaultMessage: "Order address was updated",
|
||||||
|
description: "order history message"
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -158,51 +195,55 @@ interface OrderHistoryProps extends WithStyles<typeof styles> {
|
||||||
}
|
}
|
||||||
|
|
||||||
const OrderHistory = withStyles(styles, { name: "OrderHistory" })(
|
const OrderHistory = withStyles(styles, { name: "OrderHistory" })(
|
||||||
({ classes, history, onNoteAdd }: OrderHistoryProps) => (
|
({ classes, history, onNoteAdd }: OrderHistoryProps) => {
|
||||||
<div className={classes.root}>
|
const intl = useIntl();
|
||||||
<Typography className={classes.header} color="textSecondary">
|
|
||||||
{i18n.t("Order History")}
|
return (
|
||||||
</Typography>
|
<div className={classes.root}>
|
||||||
<Hr />
|
<Typography className={classes.header} color="textSecondary">
|
||||||
{history ? (
|
<FormattedMessage defaultMessage="Order History" />
|
||||||
<Timeline>
|
</Typography>
|
||||||
<Form initial={{ message: "" }} onSubmit={onNoteAdd} resetOnSubmit>
|
<Hr />
|
||||||
{({ change, data, submit }) => (
|
{history ? (
|
||||||
<TimelineAddNote
|
<Timeline>
|
||||||
message={data.message}
|
<Form initial={{ message: "" }} onSubmit={onNoteAdd} resetOnSubmit>
|
||||||
onChange={change}
|
{({ change, data, submit }) => (
|
||||||
onSubmit={submit}
|
<TimelineAddNote
|
||||||
/>
|
message={data.message}
|
||||||
)}
|
onChange={change}
|
||||||
</Form>
|
onSubmit={submit}
|
||||||
{history
|
/>
|
||||||
.slice()
|
)}
|
||||||
.reverse()
|
</Form>
|
||||||
.map(event => {
|
{history
|
||||||
if (event.type === OrderEventsEnum.NOTE_ADDED) {
|
.slice()
|
||||||
|
.reverse()
|
||||||
|
.map(event => {
|
||||||
|
if (event.type === OrderEventsEnum.NOTE_ADDED) {
|
||||||
|
return (
|
||||||
|
<TimelineNote
|
||||||
|
date={event.date}
|
||||||
|
user={event.user}
|
||||||
|
message={event.message}
|
||||||
|
key={event.id}
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
}
|
||||||
return (
|
return (
|
||||||
<TimelineNote
|
<TimelineEvent
|
||||||
date={event.date}
|
date={event.date}
|
||||||
user={event.user}
|
title={getEventMessage(event, intl)}
|
||||||
message={event.message}
|
|
||||||
key={event.id}
|
key={event.id}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
})}
|
||||||
return (
|
</Timeline>
|
||||||
<TimelineEvent
|
) : (
|
||||||
date={event.date}
|
<Skeleton />
|
||||||
title={getEventMessage(event)}
|
)}
|
||||||
key={event.id}
|
</div>
|
||||||
/>
|
);
|
||||||
);
|
}
|
||||||
})}
|
|
||||||
</Timeline>
|
|
||||||
) : (
|
|
||||||
<Skeleton />
|
|
||||||
)}
|
|
||||||
</div>
|
|
||||||
)
|
|
||||||
);
|
);
|
||||||
OrderHistory.displayName = "OrderHistory";
|
OrderHistory.displayName = "OrderHistory";
|
||||||
export default OrderHistory;
|
export default OrderHistory;
|
||||||
|
|
|
@ -10,6 +10,7 @@ import TableCell from "@material-ui/core/TableCell";
|
||||||
import TableFooter from "@material-ui/core/TableFooter";
|
import TableFooter from "@material-ui/core/TableFooter";
|
||||||
import TableRow from "@material-ui/core/TableRow";
|
import TableRow from "@material-ui/core/TableRow";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import Checkbox from "@saleor/components/Checkbox";
|
import Checkbox from "@saleor/components/Checkbox";
|
||||||
import { DateTime } from "@saleor/components/Date";
|
import { DateTime } from "@saleor/components/Date";
|
||||||
|
@ -18,7 +19,6 @@ import Skeleton from "@saleor/components/Skeleton";
|
||||||
import StatusLabel from "@saleor/components/StatusLabel";
|
import StatusLabel from "@saleor/components/StatusLabel";
|
||||||
import TableHead from "@saleor/components/TableHead";
|
import TableHead from "@saleor/components/TableHead";
|
||||||
import TablePagination from "@saleor/components/TablePagination";
|
import TablePagination from "@saleor/components/TablePagination";
|
||||||
import i18n from "@saleor/i18n";
|
|
||||||
import {
|
import {
|
||||||
maybe,
|
maybe,
|
||||||
renderCollection,
|
renderCollection,
|
||||||
|
@ -103,22 +103,34 @@ export const OrderList = withStyles(styles, { name: "OrderList" })(
|
||||||
toolbar={toolbar}
|
toolbar={toolbar}
|
||||||
>
|
>
|
||||||
<TableCell padding="dense" className={classes.colNumber}>
|
<TableCell padding="dense" className={classes.colNumber}>
|
||||||
{i18n.t("No. of Order", { context: "table header" })}
|
<FormattedMessage defaultMessage="No. of Order" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colDate}>
|
<TableCell padding="dense" className={classes.colDate}>
|
||||||
{i18n.t("Date", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Date"
|
||||||
|
description="date when order was placed"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colCustomer}>
|
<TableCell padding="dense" className={classes.colCustomer}>
|
||||||
{i18n.t("Customer", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Customer"
|
||||||
|
description="e-mail or full name"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colPayment}>
|
<TableCell padding="dense" className={classes.colPayment}>
|
||||||
{i18n.t("Payment", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Payment"
|
||||||
|
description="payment status"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell padding="dense" className={classes.colFulfillment}>
|
<TableCell padding="dense" className={classes.colFulfillment}>
|
||||||
{i18n.t("Fulfillment status", { context: "table header" })}
|
<FormattedMessage defaultMessage="Fulfillment status" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colTotal} padding="dense">
|
<TableCell className={classes.colTotal} padding="dense">
|
||||||
{i18n.t("Total", { context: "table header" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="total order price"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableHead>
|
</TableHead>
|
||||||
<TableFooter>
|
<TableFooter>
|
||||||
|
@ -220,7 +232,7 @@ export const OrderList = withStyles(styles, { name: "OrderList" })(
|
||||||
() => (
|
() => (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell colSpan={numberOfColumns}>
|
<TableCell colSpan={numberOfColumns}>
|
||||||
{i18n.t("No orders found")}
|
<FormattedMessage defaultMessage="No orders found" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
)
|
)
|
||||||
|
|
|
@ -1,11 +1,11 @@
|
||||||
import moment from "moment-timezone";
|
import moment from "moment-timezone";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { useIntl } from "react-intl";
|
||||||
|
|
||||||
import { DateContext } from "@saleor/components/Date/DateContext";
|
import { DateContext } from "@saleor/components/Date/DateContext";
|
||||||
import { FieldType, IFilter } from "@saleor/components/Filter";
|
import { FieldType, IFilter } from "@saleor/components/Filter";
|
||||||
import FilterBar from "@saleor/components/FilterBar";
|
import FilterBar from "@saleor/components/FilterBar";
|
||||||
import TimezoneContext from "@saleor/components/Timezone";
|
import TimezoneContext from "@saleor/components/Timezone";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { FilterProps } from "../../../types";
|
import { FilterProps } from "../../../types";
|
||||||
import { OrderStatusFilter } from "../../../types/globalTypes";
|
import { OrderStatusFilter } from "../../../types/globalTypes";
|
||||||
import { OrderListUrlFilters } from "../../urls";
|
import { OrderListUrlFilters } from "../../urls";
|
||||||
|
@ -26,6 +26,7 @@ export enum OrderFilterKeys {
|
||||||
const OrderListFilter: React.FC<OrderListFilterProps> = props => {
|
const OrderListFilter: React.FC<OrderListFilterProps> = props => {
|
||||||
const date = React.useContext(DateContext);
|
const date = React.useContext(DateContext);
|
||||||
const tz = React.useContext(TimezoneContext);
|
const tz = React.useContext(TimezoneContext);
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const filterMenu: IFilter = [
|
const filterMenu: IFilter = [
|
||||||
{
|
{
|
||||||
|
@ -40,7 +41,9 @@ const OrderListFilter: React.FC<OrderListFilterProps> = props => {
|
||||||
.toISOString()
|
.toISOString()
|
||||||
.split("T")[0] // Remove timezone
|
.split("T")[0] // Remove timezone
|
||||||
},
|
},
|
||||||
label: i18n.t("Last 7 Days"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Last 7 Days"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.dateLastWeek.toString()
|
value: OrderFilterKeys.dateLastWeek.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -53,7 +56,9 @@ const OrderListFilter: React.FC<OrderListFilterProps> = props => {
|
||||||
.toISOString()
|
.toISOString()
|
||||||
.split("T")[0] // Remove timezone
|
.split("T")[0] // Remove timezone
|
||||||
},
|
},
|
||||||
label: i18n.t("Last 30 Days"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Last 30 Days"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.dateLastMonth.toString()
|
value: OrderFilterKeys.dateLastMonth.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -66,58 +71,90 @@ const OrderListFilter: React.FC<OrderListFilterProps> = props => {
|
||||||
.toISOString()
|
.toISOString()
|
||||||
.split("T")[0] // Remove timezone
|
.split("T")[0] // Remove timezone
|
||||||
},
|
},
|
||||||
label: i18n.t("Last Year"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Last Year"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.dateLastYear.toString()
|
value: OrderFilterKeys.dateLastYear.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
children: [],
|
children: [],
|
||||||
data: {
|
data: {
|
||||||
additionalText: i18n.t("equals"),
|
additionalText: intl.formatMessage({
|
||||||
|
defaultMessage: "equals"
|
||||||
|
}),
|
||||||
fieldLabel: null,
|
fieldLabel: null,
|
||||||
type: FieldType.date
|
type: FieldType.date
|
||||||
},
|
},
|
||||||
label: i18n.t("Specific Date"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Specific Date"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.dateEqual.toString()
|
value: OrderFilterKeys.dateEqual.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
children: [],
|
children: [],
|
||||||
data: {
|
data: {
|
||||||
fieldLabel: i18n.t("Range"),
|
fieldLabel: intl.formatMessage({
|
||||||
|
defaultMessage: "Range"
|
||||||
|
}),
|
||||||
type: FieldType.rangeDate
|
type: FieldType.rangeDate
|
||||||
},
|
},
|
||||||
label: i18n.t("Range"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Range"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.dateRange.toString()
|
value: OrderFilterKeys.dateRange.toString()
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
data: {
|
data: {
|
||||||
fieldLabel: i18n.t("Date"),
|
fieldLabel: intl.formatMessage({
|
||||||
|
defaultMessage: "Date"
|
||||||
|
}),
|
||||||
type: FieldType.select
|
type: FieldType.select
|
||||||
},
|
},
|
||||||
label: i18n.t("Date"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Date"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.date.toString()
|
value: OrderFilterKeys.date.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
children: [],
|
children: [],
|
||||||
data: {
|
data: {
|
||||||
additionalText: i18n.t("is set as"),
|
additionalText: intl.formatMessage({
|
||||||
fieldLabel: i18n.t("Status"),
|
defaultMessage: "is set as",
|
||||||
|
description: "date is set as"
|
||||||
|
}),
|
||||||
|
fieldLabel: intl.formatMessage({
|
||||||
|
defaultMessage: "Status",
|
||||||
|
description: "order fulfillment status"
|
||||||
|
}),
|
||||||
options: [
|
options: [
|
||||||
{
|
{
|
||||||
label: i18n.t("Fulfilled"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Fulfilled",
|
||||||
|
description: "order fulfillment status"
|
||||||
|
}),
|
||||||
value: OrderStatusFilter.FULFILLED.toString()
|
value: OrderStatusFilter.FULFILLED.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: i18n.t("Partially Fulfilled"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Partially Fulfilled",
|
||||||
|
description: "order fulfillment status"
|
||||||
|
}),
|
||||||
value: OrderStatusFilter.PARTIALLY_FULFILLED.toString()
|
value: OrderStatusFilter.PARTIALLY_FULFILLED.toString()
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
label: i18n.t("Unfulfilled"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Unfulfilled",
|
||||||
|
description: "order fulfillment status"
|
||||||
|
}),
|
||||||
value: OrderStatusFilter.UNFULFILLED.toString()
|
value: OrderStatusFilter.UNFULFILLED.toString()
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
type: FieldType.select
|
type: FieldType.select
|
||||||
},
|
},
|
||||||
label: i18n.t("Fulfillment Status"),
|
label: intl.formatMessage({
|
||||||
|
defaultMessage: "Fulfillment Status",
|
||||||
|
description: "order"
|
||||||
|
}),
|
||||||
value: OrderFilterKeys.fulfillment.toString()
|
value: OrderFilterKeys.fulfillment.toString()
|
||||||
}
|
}
|
||||||
];
|
];
|
||||||
|
|
|
@ -2,10 +2,11 @@ import Button from "@material-ui/core/Button";
|
||||||
import Card from "@material-ui/core/Card";
|
import Card from "@material-ui/core/Card";
|
||||||
import AddIcon from "@material-ui/icons/Add";
|
import AddIcon from "@material-ui/icons/Add";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import Container from "@saleor/components/Container";
|
import Container from "@saleor/components/Container";
|
||||||
import PageHeader from "@saleor/components/PageHeader";
|
import PageHeader from "@saleor/components/PageHeader";
|
||||||
import i18n from "@saleor/i18n";
|
import { sectionNames } from "@saleor/intl";
|
||||||
import { FilterPageProps, ListActions, PageListProps } from "@saleor/types";
|
import { FilterPageProps, ListActions, PageListProps } from "@saleor/types";
|
||||||
import { OrderList_orders_edges_node } from "../../types/OrderList";
|
import { OrderList_orders_edges_node } from "../../types/OrderList";
|
||||||
import { OrderListUrlFilters } from "../../urls";
|
import { OrderListUrlFilters } from "../../urls";
|
||||||
|
@ -33,33 +34,48 @@ const OrderListPage: React.FC<OrderListPageProps> = ({
|
||||||
onTabChange,
|
onTabChange,
|
||||||
onFilterDelete,
|
onFilterDelete,
|
||||||
...listProps
|
...listProps
|
||||||
}) => (
|
}) => {
|
||||||
<Container>
|
const intl = useIntl();
|
||||||
<PageHeader title={i18n.t("Orders")}>
|
|
||||||
<Button color="primary" variant="contained" onClick={onAdd}>
|
return (
|
||||||
{i18n.t("Create order", { context: "button" })} <AddIcon />
|
<Container>
|
||||||
</Button>
|
<PageHeader title={intl.formatMessage(sectionNames.orders)}>
|
||||||
</PageHeader>
|
<Button color="primary" variant="contained" onClick={onAdd}>
|
||||||
<Card>
|
<FormattedMessage
|
||||||
<OrderListFilter
|
defaultMessage="Create order"
|
||||||
allTabLabel={i18n.t("All Orders")}
|
description="button"
|
||||||
currencySymbol={currencySymbol}
|
/>
|
||||||
currentTab={currentTab}
|
<AddIcon />
|
||||||
filterLabel={i18n.t("Select all orders where:")}
|
</Button>
|
||||||
filterTabs={filterTabs}
|
</PageHeader>
|
||||||
filtersList={filtersList}
|
<Card>
|
||||||
initialSearch={initialSearch}
|
<OrderListFilter
|
||||||
searchPlaceholder={i18n.t("Search Orders...")}
|
allTabLabel={intl.formatMessage({
|
||||||
onAll={onAll}
|
defaultMessage: "All Orders",
|
||||||
onSearchChange={onSearchChange}
|
description: "tab name"
|
||||||
onFilterAdd={onFilterAdd}
|
})}
|
||||||
onFilterSave={onFilterSave}
|
currencySymbol={currencySymbol}
|
||||||
onTabChange={onTabChange}
|
currentTab={currentTab}
|
||||||
onFilterDelete={onFilterDelete}
|
filterLabel={intl.formatMessage({
|
||||||
/>
|
defaultMessage: "Select all orders where:"
|
||||||
<OrderList {...listProps} />
|
})}
|
||||||
</Card>
|
filterTabs={filterTabs}
|
||||||
</Container>
|
filtersList={filtersList}
|
||||||
);
|
initialSearch={initialSearch}
|
||||||
|
searchPlaceholder={intl.formatMessage({
|
||||||
|
defaultMessage: "Search Orders..."
|
||||||
|
})}
|
||||||
|
onAll={onAll}
|
||||||
|
onSearchChange={onSearchChange}
|
||||||
|
onFilterAdd={onFilterAdd}
|
||||||
|
onFilterSave={onFilterSave}
|
||||||
|
onTabChange={onTabChange}
|
||||||
|
onFilterDelete={onFilterDelete}
|
||||||
|
/>
|
||||||
|
<OrderList {...listProps} />
|
||||||
|
</Card>
|
||||||
|
</Container>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderListPage.displayName = "OrderListPage";
|
OrderListPage.displayName = "OrderListPage";
|
||||||
export default OrderListPage;
|
export default OrderListPage;
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
import DialogContentText from "@material-ui/core/DialogContentText";
|
import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ActionDialog from "@saleor/components/ActionDialog";
|
import ActionDialog from "@saleor/components/ActionDialog";
|
||||||
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
|
|
||||||
export interface OrderMarkAsPaidDialogProps {
|
export interface OrderMarkAsPaidDialogProps {
|
||||||
confirmButtonState: ConfirmButtonTransitionState;
|
confirmButtonState: ConfirmButtonTransitionState;
|
||||||
|
@ -14,20 +14,25 @@ export interface OrderMarkAsPaidDialogProps {
|
||||||
|
|
||||||
const OrderMarkAsPaidDialog: React.StatelessComponent<
|
const OrderMarkAsPaidDialog: React.StatelessComponent<
|
||||||
OrderMarkAsPaidDialogProps
|
OrderMarkAsPaidDialogProps
|
||||||
> = ({ confirmButtonState, onClose, onConfirm, open }) => (
|
> = ({ confirmButtonState, onClose, onConfirm, open }) => {
|
||||||
<ActionDialog
|
const intl = useIntl();
|
||||||
confirmButtonState={confirmButtonState}
|
|
||||||
open={open}
|
return (
|
||||||
title={i18n.t("Mark order as paid")}
|
<ActionDialog
|
||||||
onClose={onClose}
|
confirmButtonState={confirmButtonState}
|
||||||
onConfirm={onConfirm}
|
open={open}
|
||||||
>
|
title={intl.formatMessage({
|
||||||
<DialogContentText>
|
defaultMessage: "Mark Order as Paid",
|
||||||
{i18n.t("Are you sure you want to mark this order as paid?", {
|
description: "dialog header"
|
||||||
context: "modal content"
|
|
||||||
})}
|
})}
|
||||||
</DialogContentText>
|
onClose={onClose}
|
||||||
</ActionDialog>
|
onConfirm={onConfirm}
|
||||||
);
|
>
|
||||||
|
<DialogContentText>
|
||||||
|
<FormattedMessage defaultMessage="Are you sure you want to mark this order as paid?" />
|
||||||
|
</DialogContentText>
|
||||||
|
</ActionDialog>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderMarkAsPaidDialog.displayName = "OrderMarkAsPaidDialog";
|
OrderMarkAsPaidDialog.displayName = "OrderMarkAsPaidDialog";
|
||||||
export default OrderMarkAsPaidDialog;
|
export default OrderMarkAsPaidDialog;
|
||||||
|
|
|
@ -9,13 +9,13 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
import { Hr } from "@saleor/components/Hr";
|
import { Hr } from "@saleor/components/Hr";
|
||||||
import Money, { subtractMoney } from "@saleor/components/Money";
|
import Money, { subtractMoney } from "@saleor/components/Money";
|
||||||
import Skeleton from "@saleor/components/Skeleton";
|
import Skeleton from "@saleor/components/Skeleton";
|
||||||
import StatusLabel from "@saleor/components/StatusLabel";
|
import StatusLabel from "@saleor/components/StatusLabel";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe, transformPaymentStatus } from "../../../misc";
|
import { maybe, transformPaymentStatus } from "../../../misc";
|
||||||
import { OrderAction, OrderStatus } from "../../../types/globalTypes";
|
import { OrderAction, OrderStatus } from "../../../types/globalTypes";
|
||||||
import { OrderDetails_order } from "../../types/OrderDetails";
|
import { OrderDetails_order } from "../../types/OrderDetails";
|
||||||
|
@ -52,6 +52,8 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
onRefund,
|
onRefund,
|
||||||
onVoid
|
onVoid
|
||||||
}: OrderPaymentProps) => {
|
}: OrderPaymentProps) => {
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const canCapture = maybe(() => order.actions, []).includes(
|
const canCapture = maybe(() => order.actions, []).includes(
|
||||||
OrderAction.CAPTURE
|
OrderAction.CAPTURE
|
||||||
);
|
);
|
||||||
|
@ -78,16 +80,25 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
<table className={classes.root}>
|
<table className={classes.root}>
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr>
|
<tr>
|
||||||
<td>{i18n.t("Subtotal")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Subtotal"
|
||||||
|
description="order subtotal price"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td>
|
<td>
|
||||||
{maybe(() => order.lines) === undefined ? (
|
{maybe(() => order.lines) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : (
|
) : (
|
||||||
i18n.t("{{ quantity }} items", {
|
<FormattedMessage
|
||||||
quantity: order.lines
|
defaultMessage="{quantity} items"
|
||||||
.map(line => line.quantity)
|
description="ordered products"
|
||||||
.reduce((curr, prev) => prev + curr, 0)
|
values={{
|
||||||
})
|
quantity: order.lines
|
||||||
|
.map(line => line.quantity)
|
||||||
|
.reduce((curr, prev) => prev + curr, 0)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
)}
|
)}
|
||||||
</td>
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
|
@ -99,14 +110,23 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>{i18n.t("Taxes")}</td>
|
<td>
|
||||||
|
<FormattedMessage defaultMessage="Taxes" />
|
||||||
|
</td>
|
||||||
<td>
|
<td>
|
||||||
{maybe(() => order.total.tax) === undefined ? (
|
{maybe(() => order.total.tax) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : order.total.tax.amount > 0 ? (
|
) : order.total.tax.amount > 0 ? (
|
||||||
i18n.t("VAT included")
|
intl.formatMessage({
|
||||||
|
defaultMessage: "VAT included",
|
||||||
|
description: "vat included in order price"
|
||||||
|
})
|
||||||
) : (
|
) : (
|
||||||
i18n.t("does not apply")
|
intl.formatMessage({
|
||||||
|
defaultMessage: "does not apply",
|
||||||
|
description: "vat not included in order price",
|
||||||
|
id: "orderPaymentVATDoesNotApply"
|
||||||
|
})
|
||||||
)}
|
)}
|
||||||
</td>
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
|
@ -118,13 +138,22 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>{i18n.t("Shipping")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Shipping"
|
||||||
|
description="order shipping method name"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td>
|
<td>
|
||||||
{maybe(() => order.shippingMethodName) === undefined &&
|
{maybe(() => order.shippingMethodName) === undefined &&
|
||||||
maybe(() => order.shippingPrice) === undefined ? (
|
maybe(() => order.shippingPrice) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
) : order.shippingMethodName === null ? (
|
) : order.shippingMethodName === null ? (
|
||||||
i18n.t("does not apply")
|
intl.formatMessage({
|
||||||
|
defaultMessage: "does not apply",
|
||||||
|
description: "order does not require shipping",
|
||||||
|
id: "orderPaymentShippingDoesNotApply"
|
||||||
|
})
|
||||||
) : (
|
) : (
|
||||||
order.shippingMethodName
|
order.shippingMethodName
|
||||||
)}
|
)}
|
||||||
|
@ -138,7 +167,12 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr className={classes.totalRow}>
|
<tr className={classes.totalRow}>
|
||||||
<td>{i18n.t("Total")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Total"
|
||||||
|
description="order total price"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td />
|
<td />
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
{maybe(() => order.total.gross) === undefined ? (
|
{maybe(() => order.total.gross) === undefined ? (
|
||||||
|
@ -156,7 +190,12 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
<table className={classes.root}>
|
<table className={classes.root}>
|
||||||
<tbody>
|
<tbody>
|
||||||
<tr>
|
<tr>
|
||||||
<td>{i18n.t("Preauthorized amount")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Preauthorized amount"
|
||||||
|
description="order payment"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
{maybe(() => order.totalAuthorized.amount) === undefined ? (
|
{maybe(() => order.totalAuthorized.amount) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
|
@ -166,7 +205,12 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr>
|
<tr>
|
||||||
<td>{i18n.t("Captured amount")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Captured amount"
|
||||||
|
description="order payment"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
{maybe(() => order.totalCaptured.amount) === undefined ? (
|
{maybe(() => order.totalCaptured.amount) === undefined ? (
|
||||||
<Skeleton />
|
<Skeleton />
|
||||||
|
@ -176,7 +220,12 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
<tr className={classes.totalRow}>
|
<tr className={classes.totalRow}>
|
||||||
<td>{i18n.t("Outstanding Balance")}</td>
|
<td>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Outstanding Balance"
|
||||||
|
description="order payment"
|
||||||
|
/>
|
||||||
|
</td>
|
||||||
<td className={classes.textRight}>
|
<td className={classes.textRight}>
|
||||||
{maybe(
|
{maybe(
|
||||||
() => order.total.gross.amount && order.totalCaptured.amount
|
() => order.total.gross.amount && order.totalCaptured.amount
|
||||||
|
@ -202,22 +251,34 @@ const OrderPayment = withStyles(styles, { name: "OrderPayment" })(
|
||||||
<CardActions>
|
<CardActions>
|
||||||
{canCapture && (
|
{canCapture && (
|
||||||
<Button color="primary" variant="text" onClick={onCapture}>
|
<Button color="primary" variant="text" onClick={onCapture}>
|
||||||
{i18n.t("Capture", { context: "button" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Capture"
|
||||||
|
description="capture payment, button"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
{canRefund && (
|
{canRefund && (
|
||||||
<Button color="primary" variant="text" onClick={onRefund}>
|
<Button color="primary" variant="text" onClick={onRefund}>
|
||||||
{i18n.t("Refund", { context: "button" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Refund"
|
||||||
|
description="button"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
{canVoid && (
|
{canVoid && (
|
||||||
<Button color="primary" variant="text" onClick={onVoid}>
|
<Button color="primary" variant="text" onClick={onVoid}>
|
||||||
{i18n.t("Void", { context: "button" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Void"
|
||||||
|
description="void payment, button"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
{canMarkAsPaid && (
|
{canMarkAsPaid && (
|
||||||
<Button color="primary" variant="text" onClick={onMarkAsPaid}>
|
<Button color="primary" variant="text" onClick={onMarkAsPaid}>
|
||||||
{i18n.t("Mark as paid", { context: "button" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Mark as paid"
|
||||||
|
description="order, button"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
)}
|
)}
|
||||||
</CardActions>
|
</CardActions>
|
||||||
|
|
|
@ -5,12 +5,13 @@ import DialogContent from "@material-ui/core/DialogContent";
|
||||||
import DialogTitle from "@material-ui/core/DialogTitle";
|
import DialogTitle from "@material-ui/core/DialogTitle";
|
||||||
import TextField from "@material-ui/core/TextField";
|
import TextField from "@material-ui/core/TextField";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
export interface FormData {
|
export interface FormData {
|
||||||
amount: number;
|
amount: number;
|
||||||
|
@ -32,58 +33,71 @@ const OrderPaymentDialog: React.StatelessComponent<OrderPaymentDialogProps> = ({
|
||||||
variant,
|
variant,
|
||||||
onClose,
|
onClose,
|
||||||
onSubmit
|
onSubmit
|
||||||
}) => (
|
}) => {
|
||||||
<Dialog onClose={onClose} open={open}>
|
const intl = useIntl();
|
||||||
<Form
|
|
||||||
initial={{
|
|
||||||
amount: initial
|
|
||||||
}}
|
|
||||||
onSubmit={data => {
|
|
||||||
onSubmit(data);
|
|
||||||
onClose();
|
|
||||||
}}
|
|
||||||
>
|
|
||||||
{({ data, change, submit }) => (
|
|
||||||
<>
|
|
||||||
<DialogTitle>
|
|
||||||
{variant === "capture"
|
|
||||||
? i18n.t("Capture payment", { context: "title" })
|
|
||||||
: i18n.t("Refund payment", { context: "title" })}
|
|
||||||
</DialogTitle>
|
|
||||||
|
|
||||||
<DialogContent>
|
return (
|
||||||
<TextField
|
<Dialog onClose={onClose} open={open}>
|
||||||
fullWidth
|
<Form
|
||||||
label={i18n.t("Amount")}
|
initial={{
|
||||||
name="amount"
|
amount: initial
|
||||||
onChange={change}
|
}}
|
||||||
inputProps={{
|
onSubmit={data => {
|
||||||
step: "0.01"
|
onSubmit(data);
|
||||||
}}
|
onClose();
|
||||||
type="number"
|
}}
|
||||||
value={data.amount}
|
>
|
||||||
/>
|
{({ data, change, submit }) => (
|
||||||
</DialogContent>
|
<>
|
||||||
<DialogActions>
|
<DialogTitle>
|
||||||
<Button onClick={onClose}>
|
{variant === "capture"
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
? intl.formatMessage({
|
||||||
</Button>
|
defaultMessage: "Capture Payment",
|
||||||
<ConfirmButton
|
description: "dialog header"
|
||||||
transitionState={confirmButtonState}
|
})
|
||||||
color="primary"
|
: intl.formatMessage({
|
||||||
variant="contained"
|
defaultMessage: "Refund Payment",
|
||||||
onClick={() => {
|
description: "dialog header"
|
||||||
onClose();
|
})}
|
||||||
submit();
|
</DialogTitle>
|
||||||
}}
|
|
||||||
>
|
<DialogContent>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<TextField
|
||||||
</ConfirmButton>
|
fullWidth
|
||||||
</DialogActions>
|
label={intl.formatMessage({
|
||||||
</>
|
defaultMessage: "Amount",
|
||||||
)}
|
description: "amount of refunded money"
|
||||||
</Form>
|
})}
|
||||||
</Dialog>
|
name="amount"
|
||||||
);
|
onChange={change}
|
||||||
|
inputProps={{
|
||||||
|
step: "0.01"
|
||||||
|
}}
|
||||||
|
type="number"
|
||||||
|
value={data.amount}
|
||||||
|
/>
|
||||||
|
</DialogContent>
|
||||||
|
<DialogActions>
|
||||||
|
<Button onClick={onClose}>
|
||||||
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
|
</Button>
|
||||||
|
<ConfirmButton
|
||||||
|
transitionState={confirmButtonState}
|
||||||
|
color="primary"
|
||||||
|
variant="contained"
|
||||||
|
onClick={() => {
|
||||||
|
onClose();
|
||||||
|
submit();
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
|
</ConfirmButton>
|
||||||
|
</DialogActions>
|
||||||
|
</>
|
||||||
|
)}
|
||||||
|
</Form>
|
||||||
|
</Dialog>
|
||||||
|
);
|
||||||
|
};
|
||||||
OrderPaymentDialog.displayName = "OrderPaymentDialog";
|
OrderPaymentDialog.displayName = "OrderPaymentDialog";
|
||||||
export default OrderPaymentDialog;
|
export default OrderPaymentDialog;
|
||||||
|
|
|
@ -5,11 +5,12 @@ import DialogContent from "@material-ui/core/DialogContent";
|
||||||
import DialogContentText from "@material-ui/core/DialogContentText";
|
import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import DialogTitle from "@material-ui/core/DialogTitle";
|
import DialogTitle from "@material-ui/core/DialogTitle";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
} from "@saleor/components/ConfirmButton";
|
} from "@saleor/components/ConfirmButton";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
|
|
||||||
interface OrderPaymentVoidDialogProps {
|
interface OrderPaymentVoidDialogProps {
|
||||||
confirmButtonState: ConfirmButtonTransitionState;
|
confirmButtonState: ConfirmButtonTransitionState;
|
||||||
|
@ -22,21 +23,28 @@ const OrderPaymentVoidDialog: React.StatelessComponent<
|
||||||
OrderPaymentVoidDialogProps
|
OrderPaymentVoidDialogProps
|
||||||
> = ({ confirmButtonState, open, onConfirm, onClose }) => (
|
> = ({ confirmButtonState, open, onConfirm, onClose }) => (
|
||||||
<Dialog onClose={onClose} open={open}>
|
<Dialog onClose={onClose} open={open}>
|
||||||
<DialogTitle>{i18n.t("Void payment", { context: "title" })}</DialogTitle>
|
<DialogTitle>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Void Payment"
|
||||||
|
description="dialog header"
|
||||||
|
/>
|
||||||
|
</DialogTitle>
|
||||||
<DialogContent>
|
<DialogContent>
|
||||||
<DialogContentText>
|
<DialogContentText>
|
||||||
{i18n.t("Are you sure you want to void this payment?")}
|
<FormattedMessage defaultMessage="Are you sure you want to void this payment?" />
|
||||||
</DialogContentText>
|
</DialogContentText>
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions>
|
<DialogActions>
|
||||||
<Button onClick={onClose}>{i18n.t("Back", { context: "button" })}</Button>
|
<Button onClick={onClose}>
|
||||||
|
<FormattedMessage {...buttonMessages.back} />
|
||||||
|
</Button>
|
||||||
<ConfirmButton
|
<ConfirmButton
|
||||||
transitionState={confirmButtonState}
|
transitionState={confirmButtonState}
|
||||||
color="primary"
|
color="primary"
|
||||||
variant="contained"
|
variant="contained"
|
||||||
onClick={onConfirm}
|
onClick={onConfirm}
|
||||||
>
|
>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</ConfirmButton>
|
</ConfirmButton>
|
||||||
</DialogActions>
|
</DialogActions>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
|
|
|
@ -17,6 +17,7 @@ import TableRow from "@material-ui/core/TableRow";
|
||||||
import TextField from "@material-ui/core/TextField";
|
import TextField from "@material-ui/core/TextField";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
import InfiniteScroll from "react-infinite-scroller";
|
import InfiniteScroll from "react-infinite-scroller";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import Checkbox from "@saleor/components/Checkbox";
|
import Checkbox from "@saleor/components/Checkbox";
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
|
@ -25,7 +26,7 @@ import ConfirmButton, {
|
||||||
import Money from "@saleor/components/Money";
|
import Money from "@saleor/components/Money";
|
||||||
import TableCellAvatar from "@saleor/components/TableCellAvatar";
|
import TableCellAvatar from "@saleor/components/TableCellAvatar";
|
||||||
import useSearchQuery from "@saleor/hooks/useSearchQuery";
|
import useSearchQuery from "@saleor/hooks/useSearchQuery";
|
||||||
import i18n from "@saleor/i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
import { maybe, renderCollection } from "@saleor/misc";
|
import { maybe, renderCollection } from "@saleor/misc";
|
||||||
import { FetchMoreProps } from "@saleor/types";
|
import { FetchMoreProps } from "@saleor/types";
|
||||||
import {
|
import {
|
||||||
|
@ -161,6 +162,7 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
onClose,
|
onClose,
|
||||||
onSubmit
|
onSubmit
|
||||||
}: OrderProductAddDialogProps & WithStyles<typeof styles>) => {
|
}: OrderProductAddDialogProps & WithStyles<typeof styles>) => {
|
||||||
|
const intl = useIntl();
|
||||||
const [query, onQueryChange] = useSearchQuery(onFetch);
|
const [query, onQueryChange] = useSearchQuery(onFetch);
|
||||||
const [variants, setVariants] = React.useState<
|
const [variants, setVariants] = React.useState<
|
||||||
SearchOrderVariant_products_edges_node_variants[]
|
SearchOrderVariant_products_edges_node_variants[]
|
||||||
|
@ -187,21 +189,24 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
fullWidth
|
fullWidth
|
||||||
maxWidth="sm"
|
maxWidth="sm"
|
||||||
>
|
>
|
||||||
<DialogTitle>{i18n.t("Add product")}</DialogTitle>
|
<DialogTitle>
|
||||||
|
<FormattedMessage
|
||||||
|
defaultMessage="Add Product"
|
||||||
|
description="dialog header"
|
||||||
|
/>
|
||||||
|
</DialogTitle>
|
||||||
<DialogContent className={classes.overflow}>
|
<DialogContent className={classes.overflow}>
|
||||||
<TextField
|
<TextField
|
||||||
name="query"
|
name="query"
|
||||||
value={query}
|
value={query}
|
||||||
onChange={onQueryChange}
|
onChange={onQueryChange}
|
||||||
label={i18n.t("Search Products", {
|
label={intl.formatMessage({
|
||||||
context: "product search input label"
|
defaultMessage: "Search Products"
|
||||||
|
})}
|
||||||
|
placeholder={intl.formatMessage({
|
||||||
|
defaultMessage:
|
||||||
|
"Search by product name, attribute, product type etc..."
|
||||||
})}
|
})}
|
||||||
placeholder={i18n.t(
|
|
||||||
"Search by product name, attribute, product type etc...",
|
|
||||||
{
|
|
||||||
context: "product search input placeholder"
|
|
||||||
}
|
|
||||||
)}
|
|
||||||
fullWidth
|
fullWidth
|
||||||
InputProps={{
|
InputProps={{
|
||||||
autoComplete: "off",
|
autoComplete: "off",
|
||||||
|
@ -285,9 +290,13 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
<TableCell>
|
<TableCell>
|
||||||
<div>{variant.name}</div>
|
<div>{variant.name}</div>
|
||||||
<div className={classes.grayText}>
|
<div className={classes.grayText}>
|
||||||
{i18n.t("SKU {{ sku }}", {
|
<FormattedMessage
|
||||||
sku: variant.sku
|
defaultMessage="SKU {sku}"
|
||||||
})}
|
description="variant sku"
|
||||||
|
values={{
|
||||||
|
sku: variant.sku
|
||||||
|
}}
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.textRight}>
|
<TableCell className={classes.textRight}>
|
||||||
|
@ -301,7 +310,7 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
() => (
|
() => (
|
||||||
<TableRow>
|
<TableRow>
|
||||||
<TableCell colSpan={4}>
|
<TableCell colSpan={4}>
|
||||||
{i18n.t("No products matching given query")}
|
<FormattedMessage defaultMessage="No products matching given query" />
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
)
|
)
|
||||||
|
@ -312,7 +321,7 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions>
|
<DialogActions>
|
||||||
<Button onClick={onClose}>
|
<Button onClick={onClose}>
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
</Button>
|
</Button>
|
||||||
<ConfirmButton
|
<ConfirmButton
|
||||||
transitionState={confirmButtonState}
|
transitionState={confirmButtonState}
|
||||||
|
@ -321,7 +330,7 @@ const OrderProductAddDialog = withStyles(styles, {
|
||||||
type="submit"
|
type="submit"
|
||||||
onClick={handleSubmit}
|
onClick={handleSubmit}
|
||||||
>
|
>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</ConfirmButton>
|
</ConfirmButton>
|
||||||
</DialogActions>
|
</DialogActions>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
|
|
|
@ -10,6 +10,7 @@ import {
|
||||||
WithStyles
|
WithStyles
|
||||||
} from "@material-ui/core/styles";
|
} from "@material-ui/core/styles";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage } from "react-intl";
|
||||||
|
|
||||||
import ConfirmButton, {
|
import ConfirmButton, {
|
||||||
ConfirmButtonTransitionState
|
ConfirmButtonTransitionState
|
||||||
|
@ -17,7 +18,7 @@ import ConfirmButton, {
|
||||||
import Form from "@saleor/components/Form";
|
import Form from "@saleor/components/Form";
|
||||||
import Money from "@saleor/components/Money";
|
import Money from "@saleor/components/Money";
|
||||||
import { SingleSelectField } from "@saleor/components/SingleSelectField";
|
import { SingleSelectField } from "@saleor/components/SingleSelectField";
|
||||||
import i18n from "../../../i18n";
|
import { buttonMessages } from "@saleor/intl";
|
||||||
import { OrderDetails_order_availableShippingMethods } from "../../types/OrderDetails";
|
import { OrderDetails_order_availableShippingMethods } from "../../types/OrderDetails";
|
||||||
|
|
||||||
export interface FormData {
|
export interface FormData {
|
||||||
|
@ -85,7 +86,10 @@ const OrderShippingMethodEditDialog = withStyles(styles, {
|
||||||
return (
|
return (
|
||||||
<Dialog onClose={onClose} open={open} classes={{ paper: classes.dialog }}>
|
<Dialog onClose={onClose} open={open} classes={{ paper: classes.dialog }}>
|
||||||
<DialogTitle>
|
<DialogTitle>
|
||||||
{i18n.t("Edit shipping method", { context: "title" })}
|
<FormattedMessage
|
||||||
|
defaultMessage="Edit Shipping Method"
|
||||||
|
description="dialog header"
|
||||||
|
/>
|
||||||
</DialogTitle>
|
</DialogTitle>
|
||||||
<Form initial={initialForm} onSubmit={onSubmit}>
|
<Form initial={initialForm} onSubmit={onSubmit}>
|
||||||
{({ change, data }) => (
|
{({ change, data }) => (
|
||||||
|
@ -100,7 +104,7 @@ const OrderShippingMethodEditDialog = withStyles(styles, {
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
<DialogActions>
|
<DialogActions>
|
||||||
<Button onClick={onClose}>
|
<Button onClick={onClose}>
|
||||||
{i18n.t("Cancel", { context: "button" })}
|
<FormattedMessage {...buttonMessages.cancel} />
|
||||||
</Button>
|
</Button>
|
||||||
<ConfirmButton
|
<ConfirmButton
|
||||||
transitionState={confirmButtonState}
|
transitionState={confirmButtonState}
|
||||||
|
@ -108,7 +112,7 @@ const OrderShippingMethodEditDialog = withStyles(styles, {
|
||||||
variant="contained"
|
variant="contained"
|
||||||
type="submit"
|
type="submit"
|
||||||
>
|
>
|
||||||
{i18n.t("Confirm", { context: "button" })}
|
<FormattedMessage {...buttonMessages.confirm} />
|
||||||
</ConfirmButton>
|
</ConfirmButton>
|
||||||
</DialogActions>
|
</DialogActions>
|
||||||
</>
|
</>
|
||||||
|
|
|
@ -8,6 +8,7 @@ import TableCell from "@material-ui/core/TableCell";
|
||||||
import TableHead from "@material-ui/core/TableHead";
|
import TableHead from "@material-ui/core/TableHead";
|
||||||
import TableRow from "@material-ui/core/TableRow";
|
import TableRow from "@material-ui/core/TableRow";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import CardTitle from "@saleor/components/CardTitle";
|
import CardTitle from "@saleor/components/CardTitle";
|
||||||
import Money from "@saleor/components/Money";
|
import Money from "@saleor/components/Money";
|
||||||
|
@ -16,7 +17,6 @@ import StatusLabel from "@saleor/components/StatusLabel";
|
||||||
import TableCellAvatar, {
|
import TableCellAvatar, {
|
||||||
AVATAR_MARGIN
|
AVATAR_MARGIN
|
||||||
} from "@saleor/components/TableCellAvatar";
|
} from "@saleor/components/TableCellAvatar";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
import { OrderDetails_order_lines } from "../../types/OrderDetails";
|
||||||
|
|
||||||
|
@ -58,90 +58,116 @@ interface OrderUnfulfilledItemsProps extends WithStyles<typeof styles> {
|
||||||
|
|
||||||
const OrderUnfulfilledItems = withStyles(styles, {
|
const OrderUnfulfilledItems = withStyles(styles, {
|
||||||
name: "OrderUnfulfilledItems"
|
name: "OrderUnfulfilledItems"
|
||||||
})(({ canFulfill, classes, lines, onFulfill }: OrderUnfulfilledItemsProps) => (
|
})(({ canFulfill, classes, lines, onFulfill }: OrderUnfulfilledItemsProps) => {
|
||||||
<Card>
|
const intl = useIntl();
|
||||||
<CardTitle
|
|
||||||
title={
|
return (
|
||||||
<StatusLabel
|
<Card>
|
||||||
label={i18n.t("Unfulfilled ({{ quantity }})", {
|
<CardTitle
|
||||||
quantity: lines
|
title={
|
||||||
.map(line => line.quantity - line.quantityFulfilled)
|
<StatusLabel
|
||||||
.reduce((prev, curr) => prev + curr, 0)
|
label={intl.formatMessage(
|
||||||
})}
|
{
|
||||||
status="error"
|
defaultMessage: "Unfulfilled ({quantity})",
|
||||||
/>
|
description: "section header"
|
||||||
}
|
},
|
||||||
/>
|
{
|
||||||
<Table className={classes.table}>
|
quantity: lines
|
||||||
<TableHead>
|
.map(line => line.quantity - line.quantityFulfilled)
|
||||||
<TableRow>
|
.reduce((prev, curr) => prev + curr, 0)
|
||||||
<TableCell className={classes.colName}>
|
}
|
||||||
<span className={classes.colNameLabel}>{i18n.t("Product")}</span>
|
)}
|
||||||
</TableCell>
|
status="error"
|
||||||
<TableCell className={classes.colQuantity}>
|
/>
|
||||||
{i18n.t("Quantity")}
|
}
|
||||||
</TableCell>
|
/>
|
||||||
<TableCell className={classes.colPrice}>{i18n.t("Price")}</TableCell>
|
<Table className={classes.table}>
|
||||||
<TableCell className={classes.colTotal}>{i18n.t("Total")}</TableCell>
|
<TableHead>
|
||||||
</TableRow>
|
<TableRow>
|
||||||
</TableHead>
|
<TableCell className={classes.colName}>
|
||||||
<TableBody>
|
<span className={classes.colNameLabel}>
|
||||||
{lines.map(line => (
|
<FormattedMessage
|
||||||
<TableRow
|
defaultMessage="Product"
|
||||||
className={!!line ? classes.clickableRow : undefined}
|
description="product name"
|
||||||
hover={!!line}
|
/>
|
||||||
key={maybe(() => line.id)}
|
</span>
|
||||||
>
|
</TableCell>
|
||||||
<TableCellAvatar
|
|
||||||
className={classes.colName}
|
|
||||||
thumbnail={maybe(() => line.thumbnail.url)}
|
|
||||||
>
|
|
||||||
{maybe(() => line.productName) || <Skeleton />}
|
|
||||||
</TableCellAvatar>
|
|
||||||
<TableCell className={classes.colQuantity}>
|
<TableCell className={classes.colQuantity}>
|
||||||
{maybe(() => line.quantity - line.quantityFulfilled) || (
|
<FormattedMessage
|
||||||
<Skeleton />
|
defaultMessage="Quantity"
|
||||||
)}
|
description="ordered products"
|
||||||
|
/>
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colPrice}>
|
<TableCell className={classes.colPrice}>
|
||||||
{maybe(() => line.unitPrice.gross) ? (
|
<FormattedMessage
|
||||||
<Money money={line.unitPrice.gross} />
|
defaultMessage="Price"
|
||||||
) : (
|
description="product unit price"
|
||||||
<Skeleton />
|
/>
|
||||||
)}
|
|
||||||
</TableCell>
|
</TableCell>
|
||||||
<TableCell className={classes.colTotal}>
|
<TableCell className={classes.colTotal}>
|
||||||
{maybe(
|
<FormattedMessage
|
||||||
() =>
|
defaultMessage="Total"
|
||||||
(line.quantity - line.quantityFulfilled) *
|
description="order line total price"
|
||||||
line.unitPrice.gross.amount
|
/>
|
||||||
) ? (
|
|
||||||
<Money
|
|
||||||
money={{
|
|
||||||
amount:
|
|
||||||
(line.quantity - line.quantityFulfilled) *
|
|
||||||
line.unitPrice.gross.amount,
|
|
||||||
currency: line.unitPrice.gross.currency
|
|
||||||
}}
|
|
||||||
/>
|
|
||||||
) : (
|
|
||||||
<Skeleton />
|
|
||||||
)}
|
|
||||||
</TableCell>
|
</TableCell>
|
||||||
</TableRow>
|
</TableRow>
|
||||||
))}
|
</TableHead>
|
||||||
</TableBody>
|
<TableBody>
|
||||||
</Table>
|
{lines.map(line => (
|
||||||
{canFulfill && (
|
<TableRow
|
||||||
<CardActions>
|
className={!!line ? classes.clickableRow : undefined}
|
||||||
<Button variant="text" color="primary" onClick={onFulfill}>
|
hover={!!line}
|
||||||
{i18n.t("Fulfill", {
|
key={maybe(() => line.id)}
|
||||||
context: "button"
|
>
|
||||||
})}
|
<TableCellAvatar
|
||||||
</Button>
|
className={classes.colName}
|
||||||
</CardActions>
|
thumbnail={maybe(() => line.thumbnail.url)}
|
||||||
)}
|
>
|
||||||
</Card>
|
{maybe(() => line.productName) || <Skeleton />}
|
||||||
));
|
</TableCellAvatar>
|
||||||
|
<TableCell className={classes.colQuantity}>
|
||||||
|
{maybe(() => line.quantity - line.quantityFulfilled) || (
|
||||||
|
<Skeleton />
|
||||||
|
)}
|
||||||
|
</TableCell>
|
||||||
|
<TableCell className={classes.colPrice}>
|
||||||
|
{maybe(() => line.unitPrice.gross) ? (
|
||||||
|
<Money money={line.unitPrice.gross} />
|
||||||
|
) : (
|
||||||
|
<Skeleton />
|
||||||
|
)}
|
||||||
|
</TableCell>
|
||||||
|
<TableCell className={classes.colTotal}>
|
||||||
|
{maybe(
|
||||||
|
() =>
|
||||||
|
(line.quantity - line.quantityFulfilled) *
|
||||||
|
line.unitPrice.gross.amount
|
||||||
|
) ? (
|
||||||
|
<Money
|
||||||
|
money={{
|
||||||
|
amount:
|
||||||
|
(line.quantity - line.quantityFulfilled) *
|
||||||
|
line.unitPrice.gross.amount,
|
||||||
|
currency: line.unitPrice.gross.currency
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
) : (
|
||||||
|
<Skeleton />
|
||||||
|
)}
|
||||||
|
</TableCell>
|
||||||
|
</TableRow>
|
||||||
|
))}
|
||||||
|
</TableBody>
|
||||||
|
</Table>
|
||||||
|
{canFulfill && (
|
||||||
|
<CardActions>
|
||||||
|
<Button variant="text" color="primary" onClick={onFulfill}>
|
||||||
|
<FormattedMessage defaultMessage="Fulfill" description="button" />
|
||||||
|
</Button>
|
||||||
|
</CardActions>
|
||||||
|
)}
|
||||||
|
</Card>
|
||||||
|
);
|
||||||
|
});
|
||||||
OrderUnfulfilledItems.displayName = "OrderUnfulfilledItems";
|
OrderUnfulfilledItems.displayName = "OrderUnfulfilledItems";
|
||||||
export default OrderUnfulfilledItems;
|
export default OrderUnfulfilledItems;
|
||||||
|
|
|
@ -1,9 +1,10 @@
|
||||||
import { parse as parseQs } from "qs";
|
import { parse as parseQs } from "qs";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { useIntl } from "react-intl";
|
||||||
import { Route, RouteComponentProps, Switch } from "react-router-dom";
|
import { Route, RouteComponentProps, Switch } from "react-router-dom";
|
||||||
|
|
||||||
|
import { sectionNames } from "@saleor/intl";
|
||||||
import { WindowTitle } from "../components/WindowTitle";
|
import { WindowTitle } from "../components/WindowTitle";
|
||||||
import i18n from "../i18n";
|
|
||||||
import {
|
import {
|
||||||
orderDraftListPath,
|
orderDraftListPath,
|
||||||
OrderDraftListUrlQueryParams,
|
OrderDraftListUrlQueryParams,
|
||||||
|
@ -46,15 +47,19 @@ const OrderDetails: React.StatelessComponent<RouteComponentProps<any>> = ({
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|
||||||
const Component = () => (
|
const Component = () => {
|
||||||
<>
|
const intl = useIntl();
|
||||||
<WindowTitle title={i18n.t("Orders")} />
|
|
||||||
<Switch>
|
return (
|
||||||
<Route exact path={orderDraftListPath} component={OrderDraftList} />
|
<>
|
||||||
<Route exact path={orderListPath} component={OrderList} />
|
<WindowTitle title={intl.formatMessage(sectionNames.orders)} />
|
||||||
<Route path={orderPath(":id")} component={OrderDetails} />
|
<Switch>
|
||||||
</Switch>
|
<Route exact path={orderDraftListPath} component={OrderDraftList} />
|
||||||
</>
|
<Route exact path={orderListPath} component={OrderList} />
|
||||||
);
|
<Route path={orderPath(":id")} component={OrderDetails} />
|
||||||
|
</Switch>
|
||||||
|
</>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
export default Component;
|
export default Component;
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { useIntl } from "react-intl";
|
||||||
|
|
||||||
import useNavigator from "@saleor/hooks/useNavigator";
|
import useNavigator from "@saleor/hooks/useNavigator";
|
||||||
import useNotifier from "@saleor/hooks/useNotifier";
|
import useNotifier from "@saleor/hooks/useNotifier";
|
||||||
import i18n from "../../../i18n";
|
|
||||||
import { maybe } from "../../../misc";
|
import { maybe } from "../../../misc";
|
||||||
import { OrderAddNote } from "../../types/OrderAddNote";
|
import { OrderAddNote } from "../../types/OrderAddNote";
|
||||||
import { OrderCancel } from "../../types/OrderCancel";
|
import { OrderCancel } from "../../types/OrderCancel";
|
||||||
|
@ -52,55 +52,65 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
> = ({ children }) => {
|
> = ({ children }) => {
|
||||||
const navigate = useNavigator();
|
const navigate = useNavigator();
|
||||||
const pushMessage = useNotifier();
|
const pushMessage = useNotifier();
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const handlePaymentCapture = (data: OrderCapture) => {
|
const handlePaymentCapture = (data: OrderCapture) => {
|
||||||
if (!maybe(() => data.orderCapture.errors.length)) {
|
if (!maybe(() => data.orderCapture.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Payment successfully captured", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Payment successfully captured"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Payment not captured: {{ errorMessage }}", {
|
text: intl.formatMessage(
|
||||||
context: "notification",
|
{
|
||||||
errorMessage: data.orderCapture.errors.filter(
|
defaultMessage: "Payment not captured: {errorMessage}"
|
||||||
error => error.field === "payment"
|
},
|
||||||
)[0].message
|
{
|
||||||
})
|
errorMessage: data.orderCapture.errors.find(
|
||||||
|
error => error.field === "payment"
|
||||||
|
).message
|
||||||
|
}
|
||||||
|
)
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
const handlePaymentRefund = (data: OrderRefund) => {
|
const handlePaymentRefund = (data: OrderRefund) => {
|
||||||
if (!maybe(() => data.orderRefund.errors.length)) {
|
if (!maybe(() => data.orderRefund.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Payment successfully refunded", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Payment successfully refunded"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Payment not refunded: {{ errorMessage }}", {
|
text: intl.formatMessage(
|
||||||
context: "notification",
|
{
|
||||||
errorMessage: data.orderRefund.errors.filter(
|
defaultMessage: "Payment not refunded: {errorMessage}",
|
||||||
error => error.field === "payment"
|
description: "notification"
|
||||||
)[0].message
|
},
|
||||||
})
|
{
|
||||||
|
errorMessage: data.orderRefund.errors.find(
|
||||||
|
error => error.field === "payment"
|
||||||
|
).message
|
||||||
|
}
|
||||||
|
)
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
const handleOrderFulfillmentCreate = (data: OrderCreateFulfillment) => {
|
const handleOrderFulfillmentCreate = (data: OrderCreateFulfillment) => {
|
||||||
if (!maybe(() => data.orderFulfillmentCreate.errors.length)) {
|
if (!maybe(() => data.orderFulfillmentCreate.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Items successfully fulfilled", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Items successfully fulfilled"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderFulfillmentCreate.order.id), true);
|
navigate(orderUrl(data.orderFulfillmentCreate.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not fulfill items", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not fulfill items"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -108,53 +118,53 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleOrderMarkAsPaid = (data: OrderMarkAsPaid) => {
|
const handleOrderMarkAsPaid = (data: OrderMarkAsPaid) => {
|
||||||
if (!maybe(() => data.orderMarkAsPaid.errors.length)) {
|
if (!maybe(() => data.orderMarkAsPaid.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order marked as paid", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order marked as paid"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderMarkAsPaid.order.id), true);
|
navigate(orderUrl(data.orderMarkAsPaid.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not mark order as paid", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not mark order as paid"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
const handleOrderCancel = (data: OrderCancel) => {
|
const handleOrderCancel = (data: OrderCancel) => {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order successfully cancelled", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order successfully cancelled"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderCancel.order.id), true);
|
navigate(orderUrl(data.orderCancel.order.id), true);
|
||||||
};
|
};
|
||||||
const handleDraftCancel = () => {
|
const handleDraftCancel = () => {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order successfully cancelled", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order successfully cancelled"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderListUrl(), true);
|
navigate(orderListUrl(), true);
|
||||||
};
|
};
|
||||||
const handleOrderVoid = () => {
|
const handleOrderVoid = () => {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order payment successfully voided", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order payment successfully voided"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
const handleNoteAdd = (data: OrderAddNote) => {
|
const handleNoteAdd = (data: OrderAddNote) => {
|
||||||
if (!maybe(() => data.orderAddNote.errors.length)) {
|
if (!maybe(() => data.orderAddNote.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Note successfully added", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Note successfully added"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not add note", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not add note"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -162,8 +172,8 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleUpdate = (data: OrderUpdate) => {
|
const handleUpdate = (data: OrderUpdate) => {
|
||||||
if (!maybe(() => data.orderUpdate.errors.length)) {
|
if (!maybe(() => data.orderUpdate.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order successfully updated", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order successfully updated"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderUpdate.order.id), true);
|
navigate(orderUrl(data.orderUpdate.order.id), true);
|
||||||
|
@ -172,8 +182,8 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleDraftUpdate = (data: OrderDraftUpdate) => {
|
const handleDraftUpdate = (data: OrderDraftUpdate) => {
|
||||||
if (!maybe(() => data.draftOrderUpdate.errors.length)) {
|
if (!maybe(() => data.draftOrderUpdate.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order successfully updated", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order successfully updated"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.draftOrderUpdate.order.id), true);
|
navigate(orderUrl(data.draftOrderUpdate.order.id), true);
|
||||||
|
@ -182,14 +192,14 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleShippingMethodUpdate = (data: OrderShippingMethodUpdate) => {
|
const handleShippingMethodUpdate = (data: OrderShippingMethodUpdate) => {
|
||||||
if (!maybe(() => data.orderUpdateShipping.errors.length)) {
|
if (!maybe(() => data.orderUpdateShipping.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Shipping method successfully updated", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Shipping method successfully updated"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not update shipping method", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not update shipping method"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -198,14 +208,14 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleOrderLineDelete = (data: OrderLineDelete) => {
|
const handleOrderLineDelete = (data: OrderLineDelete) => {
|
||||||
if (!maybe(() => data.draftOrderLineDelete.errors.length)) {
|
if (!maybe(() => data.draftOrderLineDelete.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order line deleted", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order line deleted"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not delete order line", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not delete order line"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -213,15 +223,15 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleOrderLinesAdd = (data: OrderLinesAdd) => {
|
const handleOrderLinesAdd = (data: OrderLinesAdd) => {
|
||||||
if (!maybe(() => data.draftOrderLinesCreate.errors.length)) {
|
if (!maybe(() => data.draftOrderLinesCreate.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order line added", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order line added"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.draftOrderLinesCreate.order.id), true);
|
navigate(orderUrl(data.draftOrderLinesCreate.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not create order line", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not create order line"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -229,14 +239,14 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleOrderLineUpdate = (data: OrderLineUpdate) => {
|
const handleOrderLineUpdate = (data: OrderLineUpdate) => {
|
||||||
if (!maybe(() => data.draftOrderLineUpdate.errors.length)) {
|
if (!maybe(() => data.draftOrderLineUpdate.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Order line updated", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Order line updated"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not update order line", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not update order line"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -244,15 +254,15 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleOrderFulfillmentCancel = (data: OrderFulfillmentCancel) => {
|
const handleOrderFulfillmentCancel = (data: OrderFulfillmentCancel) => {
|
||||||
if (!maybe(() => data.orderFulfillmentCancel.errors.length)) {
|
if (!maybe(() => data.orderFulfillmentCancel.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Fulfillment successfully cancelled", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Fulfillment successfully cancelled"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderFulfillmentCancel.order.id), true);
|
navigate(orderUrl(data.orderFulfillmentCancel.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not cancel fulfillment", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not cancel fulfillment"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -262,15 +272,15 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
) => {
|
) => {
|
||||||
if (!maybe(() => data.orderFulfillmentUpdateTracking.errors.length)) {
|
if (!maybe(() => data.orderFulfillmentUpdateTracking.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Fulfillment successfully updated", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Fulfillment successfully updated"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.orderFulfillmentUpdateTracking.order.id), true);
|
navigate(orderUrl(data.orderFulfillmentUpdateTracking.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not update fulfillment", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not update fulfillment"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -278,15 +288,15 @@ export const OrderDetailsMessages: React.StatelessComponent<
|
||||||
const handleDraftFinalize = (data: OrderDraftFinalize) => {
|
const handleDraftFinalize = (data: OrderDraftFinalize) => {
|
||||||
if (!maybe(() => data.draftOrderComplete.errors.length)) {
|
if (!maybe(() => data.draftOrderComplete.errors.length)) {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Draft order successfully finalized", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Draft order successfully finalized"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.draftOrderComplete.order.id), true);
|
navigate(orderUrl(data.draftOrderComplete.order.id), true);
|
||||||
} else {
|
} else {
|
||||||
pushMessage({
|
pushMessage({
|
||||||
text: i18n.t("Could not finalize draft", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Could not finalize draft"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
|
@ -2,6 +2,7 @@ import DialogContentText from "@material-ui/core/DialogContentText";
|
||||||
import IconButton from "@material-ui/core/IconButton";
|
import IconButton from "@material-ui/core/IconButton";
|
||||||
import DeleteIcon from "@material-ui/icons/Delete";
|
import DeleteIcon from "@material-ui/icons/Delete";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import ActionDialog from "@saleor/components/ActionDialog";
|
import ActionDialog from "@saleor/components/ActionDialog";
|
||||||
import useBulkActions from "@saleor/hooks/useBulkActions";
|
import useBulkActions from "@saleor/hooks/useBulkActions";
|
||||||
|
@ -11,7 +12,6 @@ import useNotifier from "@saleor/hooks/useNotifier";
|
||||||
import usePaginator, {
|
import usePaginator, {
|
||||||
createPaginationState
|
createPaginationState
|
||||||
} from "@saleor/hooks/usePaginator";
|
} from "@saleor/hooks/usePaginator";
|
||||||
import i18n from "@saleor/i18n";
|
|
||||||
import { getMutationState, maybe } from "@saleor/misc";
|
import { getMutationState, maybe } from "@saleor/misc";
|
||||||
import { ListViews } from "@saleor/types";
|
import { ListViews } from "@saleor/types";
|
||||||
import OrderDraftListPage from "../components/OrderDraftListPage";
|
import OrderDraftListPage from "../components/OrderDraftListPage";
|
||||||
|
@ -44,6 +44,7 @@ export const OrderDraftList: React.StatelessComponent<OrderDraftListProps> = ({
|
||||||
const { updateListSettings, settings } = useListSettings(
|
const { updateListSettings, settings } = useListSettings(
|
||||||
ListViews.DRAFT_LIST
|
ListViews.DRAFT_LIST
|
||||||
);
|
);
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const closeModal = () =>
|
const closeModal = () =>
|
||||||
navigate(
|
navigate(
|
||||||
|
@ -56,7 +57,9 @@ export const OrderDraftList: React.StatelessComponent<OrderDraftListProps> = ({
|
||||||
|
|
||||||
const handleCreateOrderCreateSuccess = (data: OrderDraftCreate) => {
|
const handleCreateOrderCreateSuccess = (data: OrderDraftCreate) => {
|
||||||
notify({
|
notify({
|
||||||
text: i18n.t("Order draft succesfully created")
|
text: intl.formatMessage({
|
||||||
|
defaultMessage: "Order draft succesfully created"
|
||||||
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.draftOrderCreate.order.id));
|
navigate(orderUrl(data.draftOrderCreate.order.id));
|
||||||
};
|
};
|
||||||
|
@ -77,7 +80,9 @@ export const OrderDraftList: React.StatelessComponent<OrderDraftListProps> = ({
|
||||||
const handleOrderDraftBulkCancel = (data: OrderDraftBulkCancel) => {
|
const handleOrderDraftBulkCancel = (data: OrderDraftBulkCancel) => {
|
||||||
if (data.draftOrderBulkDelete.errors.length === 0) {
|
if (data.draftOrderBulkDelete.errors.length === 0) {
|
||||||
notify({
|
notify({
|
||||||
text: i18n.t("Removed draft orders")
|
text: intl.formatMessage({
|
||||||
|
defaultMessage: "Removed draft orders"
|
||||||
|
})
|
||||||
});
|
});
|
||||||
refetch();
|
refetch();
|
||||||
reset();
|
reset();
|
||||||
|
@ -145,22 +150,29 @@ export const OrderDraftList: React.StatelessComponent<OrderDraftListProps> = ({
|
||||||
onClose={closeModal}
|
onClose={closeModal}
|
||||||
onConfirm={onOrderDraftBulkDelete}
|
onConfirm={onOrderDraftBulkDelete}
|
||||||
open={params.action === "remove"}
|
open={params.action === "remove"}
|
||||||
title={i18n.t("Remove Order Drafts")}
|
title={intl.formatMessage({
|
||||||
|
defaultMessage: "Delete Order Drafts",
|
||||||
|
description: "dialog header"
|
||||||
|
})}
|
||||||
variant="delete"
|
variant="delete"
|
||||||
>
|
>
|
||||||
<DialogContentText
|
<DialogContentText>
|
||||||
dangerouslySetInnerHTML={{
|
<FormattedMessage
|
||||||
__html: i18n.t(
|
defaultMessage="Are you sure you want to delete {counter, plural,
|
||||||
"Are you sure you want to remove <strong>{{ number }}</strong> order drafts?",
|
one {this order draft}
|
||||||
{
|
other {{displayQuantity} orderDrafts}
|
||||||
number: maybe(
|
}?"
|
||||||
() => params.ids.length.toString(),
|
description="dialog content"
|
||||||
"..."
|
values={{
|
||||||
)
|
counter: maybe(() => params.ids.length),
|
||||||
}
|
displayQuantity: (
|
||||||
)
|
<strong>
|
||||||
}}
|
{maybe(() => params.ids.length)}
|
||||||
/>
|
</strong>
|
||||||
|
)
|
||||||
|
}}
|
||||||
|
/>
|
||||||
|
</DialogContentText>
|
||||||
</ActionDialog>
|
</ActionDialog>
|
||||||
</>
|
</>
|
||||||
);
|
);
|
||||||
|
|
|
@ -1,5 +1,6 @@
|
||||||
import Button from "@material-ui/core/Button";
|
import Button from "@material-ui/core/Button";
|
||||||
import React from "react";
|
import React from "react";
|
||||||
|
import { FormattedMessage, useIntl } from "react-intl";
|
||||||
|
|
||||||
import DeleteFilterTabDialog from "@saleor/components/DeleteFilterTabDialog";
|
import DeleteFilterTabDialog from "@saleor/components/DeleteFilterTabDialog";
|
||||||
import SaveFilterTabDialog, {
|
import SaveFilterTabDialog, {
|
||||||
|
@ -14,7 +15,6 @@ import usePaginator, {
|
||||||
createPaginationState
|
createPaginationState
|
||||||
} from "@saleor/hooks/usePaginator";
|
} from "@saleor/hooks/usePaginator";
|
||||||
import useShop from "@saleor/hooks/useShop";
|
import useShop from "@saleor/hooks/useShop";
|
||||||
import i18n from "@saleor/i18n";
|
|
||||||
import { getMutationState, maybe } from "@saleor/misc";
|
import { getMutationState, maybe } from "@saleor/misc";
|
||||||
import { ListViews } from "@saleor/types";
|
import { ListViews } from "@saleor/types";
|
||||||
import OrderBulkCancelDialog from "../../components/OrderBulkCancelDialog";
|
import OrderBulkCancelDialog from "../../components/OrderBulkCancelDialog";
|
||||||
|
@ -62,6 +62,7 @@ export const OrderList: React.StatelessComponent<OrderListProps> = ({
|
||||||
const { updateListSettings, settings } = useListSettings(
|
const { updateListSettings, settings } = useListSettings(
|
||||||
ListViews.ORDER_LIST
|
ListViews.ORDER_LIST
|
||||||
);
|
);
|
||||||
|
const intl = useIntl();
|
||||||
|
|
||||||
const tabs = getFilterTabs();
|
const tabs = getFilterTabs();
|
||||||
|
|
||||||
|
@ -133,7 +134,9 @@ export const OrderList: React.StatelessComponent<OrderListProps> = ({
|
||||||
|
|
||||||
const handleCreateOrderCreateSuccess = (data: OrderDraftCreate) => {
|
const handleCreateOrderCreateSuccess = (data: OrderDraftCreate) => {
|
||||||
notify({
|
notify({
|
||||||
text: i18n.t("Order draft succesfully created")
|
text: intl.formatMessage({
|
||||||
|
defaultMessage: "Order draft succesfully created"
|
||||||
|
})
|
||||||
});
|
});
|
||||||
navigate(orderUrl(data.draftOrderCreate.order.id));
|
navigate(orderUrl(data.draftOrderCreate.order.id));
|
||||||
};
|
};
|
||||||
|
@ -160,8 +163,8 @@ export const OrderList: React.StatelessComponent<OrderListProps> = ({
|
||||||
const handleOrderBulkCancel = (data: OrderBulkCancel) => {
|
const handleOrderBulkCancel = (data: OrderBulkCancel) => {
|
||||||
if (data.orderBulkCancel.errors.length === 0) {
|
if (data.orderBulkCancel.errors.length === 0) {
|
||||||
notify({
|
notify({
|
||||||
text: i18n.t("Orders cancelled", {
|
text: intl.formatMessage({
|
||||||
context: "notification"
|
defaultMessage: "Orders cancelled"
|
||||||
})
|
})
|
||||||
});
|
});
|
||||||
reset();
|
reset();
|
||||||
|
@ -218,9 +221,10 @@ export const OrderList: React.StatelessComponent<OrderListProps> = ({
|
||||||
color="primary"
|
color="primary"
|
||||||
onClick={() => openModal("cancel", listElements)}
|
onClick={() => openModal("cancel", listElements)}
|
||||||
>
|
>
|
||||||
{i18n.t("Cancel", {
|
<FormattedMessage
|
||||||
context: "cancel orders"
|
defaultMessage="Cancel"
|
||||||
})}
|
description="cancel orders, button"
|
||||||
|
/>
|
||||||
</Button>
|
</Button>
|
||||||
}
|
}
|
||||||
onSearchChange={email => changeFilterField({ email })}
|
onSearchChange={email => changeFilterField({ email })}
|
||||||
|
|
Loading…
Reference in a new issue