merge with master

This commit is contained in:
Karolina Rakoczy 2021-03-01 13:07:05 +01:00
commit dfdf43fed5
119 changed files with 1359 additions and 1404 deletions

View file

@ -70,6 +70,7 @@ jobs:
npm run test npm run test
cypress-run: cypress-run:
if: github.event.pull_request.head.repo.full_name == 'mirumee/saleor-dashboard'
runs-on: ubuntu-16.04 runs-on: ubuntu-16.04
steps: steps:
- name: Checkout - name: Checkout

View file

@ -21,6 +21,7 @@ All notable, unreleased changes to this project will be documented in this file.
- Add OAuth2 login with OpenID support - #963 by @orzechdev - Add OAuth2 login with OpenID support - #963 by @orzechdev
- Fix no channels crash - #984 by @dominik-zeglen - Fix no channels crash - #984 by @dominik-zeglen
- Update webhooks - #982 by @piotrgrundas - Update webhooks - #982 by @piotrgrundas
- Fix trigger form change when collections are being added to list of product collections - #987 by @gax97
# 2.11.1 # 2.11.1

View file

@ -8,8 +8,8 @@ ARG APP_MOUNT_URI
ARG API_URI ARG API_URI
ARG STATIC_URL ARG STATIC_URL
ENV API_URI ${API_URI:-http://localhost:8000/graphql/} ENV API_URI ${API_URI:-http://localhost:8000/graphql/}
ENV APP_MOUNT_URI ${APP_MOUNT_URI:-/dashboard/} ENV APP_MOUNT_URI ${APP_MOUNT_URI:-/}
ENV STATIC_URL ${STATIC_URL:-/dashboard/} ENV STATIC_URL ${STATIC_URL:-/}
EXPOSE 9000 EXPOSE 9000
CMD npm start -- --host 0.0.0.0 CMD npm start -- --host 0.0.0.0

View file

@ -12,7 +12,7 @@ class ProductDetails {
availableForPurchase availableForPurchase
} }
}`; }`;
return cy.sendFrontShopRequestWithQuery(query); return cy.sendRequestWithQuery(query, "token");
} }
} }
export default ProductDetails; export default ProductDetails;

View file

@ -14,7 +14,7 @@ class Search {
} }
}`; }`;
return cy.sendFrontShopRequestWithQuery(query); return cy.sendRequestWithQuery(query, "token");
} }
} }
export default Search; export default Search;

View file

@ -5,7 +5,7 @@ import { productDetailsUrl } from "../../../url/urlList";
import ChannelsUtils from "../../../utils/channelsUtils"; import ChannelsUtils from "../../../utils/channelsUtils";
import ProductsUtils from "../../../utils/productsUtils"; import ProductsUtils from "../../../utils/productsUtils";
import ShippingUtils from "../../../utils/shippingUtils"; import ShippingUtils from "../../../utils/shippingUtils";
import StoreFrontProductUtils from "../../../utils/storeFront/storeFrontProductUtils"; import { isProductAvailableForPurchase } from "../../../utils/storeFront/storeFrontProductUtils";
// <reference types="cypress" /> // <reference types="cypress" />
describe("Products available in listings", () => { describe("Products available in listings", () => {
@ -13,7 +13,6 @@ describe("Products available in listings", () => {
const channelsUtils = new ChannelsUtils(); const channelsUtils = new ChannelsUtils();
const productsUtils = new ProductsUtils(); const productsUtils = new ProductsUtils();
const productSteps = new ProductSteps(); const productSteps = new ProductSteps();
const frontShopProductUtils = new StoreFrontProductUtils();
const startsWith = "Cy-"; const startsWith = "Cy-";
const name = `${startsWith}${faker.random.number()}`; const name = `${startsWith}${faker.random.number()}`;
let productType; let productType;
@ -74,14 +73,14 @@ describe("Products available in listings", () => {
productSteps.updateProductIsAvailableForPurchase(productUrl, true); productSteps.updateProductIsAvailableForPurchase(productUrl, true);
}) })
.then(() => { .then(() => {
frontShopProductUtils.isProductAvailableForPurchase( isProductAvailableForPurchase(
productsUtils.getCreatedProduct().id, productsUtils.getCreatedProduct().id,
defaultChannel.slug, defaultChannel.slug,
productName productName
); );
}) })
.then(isProductVisible => { .then(isVisibleResp => {
expect(isProductVisible).to.be.eq(true); expect(isVisibleResp).to.be.eq(true);
}); });
}); });
it("should update product to not available for purchase", () => { it("should update product to not available for purchase", () => {
@ -102,7 +101,7 @@ describe("Products available in listings", () => {
productSteps.updateProductIsAvailableForPurchase(productUrl, false); productSteps.updateProductIsAvailableForPurchase(productUrl, false);
}) })
.then(() => { .then(() => {
frontShopProductUtils.isProductAvailableForPurchase( isProductAvailableForPurchase(
productsUtils.getCreatedProduct().id, productsUtils.getCreatedProduct().id,
defaultChannel.slug, defaultChannel.slug,
productName productName

View file

@ -4,14 +4,13 @@ import ProductSteps from "../../../steps/productSteps";
import { productDetailsUrl } from "../../../url/urlList"; import { productDetailsUrl } from "../../../url/urlList";
import ChannelsUtils from "../../../utils/channelsUtils"; import ChannelsUtils from "../../../utils/channelsUtils";
import ProductsUtils from "../../../utils/productsUtils"; import ProductsUtils from "../../../utils/productsUtils";
import StoreFrontProductUtils from "../../../utils/storeFront/storeFrontProductUtils"; import { isProductVisible } from "../../../utils/storeFront/storeFrontProductUtils";
// <reference types="cypress" /> // <reference types="cypress" />
describe("Published products", () => { describe("Published products", () => {
const channelsUtils = new ChannelsUtils(); const channelsUtils = new ChannelsUtils();
const productsUtils = new ProductsUtils(); const productsUtils = new ProductsUtils();
const productSteps = new ProductSteps(); const productSteps = new ProductSteps();
const frontShopProductUtils = new StoreFrontProductUtils();
const startsWith = "Cy-"; const startsWith = "Cy-";
const name = `${startsWith}${faker.random.number()}`; const name = `${startsWith}${faker.random.number()}`;
@ -53,11 +52,7 @@ describe("Published products", () => {
const product = productsUtils.getCreatedProduct(); const product = productsUtils.getCreatedProduct();
const productUrl = productDetailsUrl(product.id); const productUrl = productDetailsUrl(product.id);
productSteps.updateProductPublish(productUrl, true); productSteps.updateProductPublish(productUrl, true);
frontShopProductUtils.isProductVisible( isProductVisible(product.id, defaultChannel.slug, productName);
product.id,
defaultChannel.slug,
productName
);
}) })
.then(isVisible => { .then(isVisible => {
expect(isVisible).to.be.eq(true); expect(isVisible).to.be.eq(true);
@ -84,22 +79,14 @@ describe("Published products", () => {
product = productsUtils.getCreatedProduct(); product = productsUtils.getCreatedProduct();
const productUrl = productDetailsUrl(product.id); const productUrl = productDetailsUrl(product.id);
productSteps.updateProductPublish(productUrl, false); productSteps.updateProductPublish(productUrl, false);
frontShopProductUtils.isProductVisible( isProductVisible(product.id, defaultChannel.slug, productName);
product.id,
defaultChannel.slug,
productName
);
}) })
.then(isVisible => { .then(isVisible => {
expect(isVisible).to.be.eq(false); expect(isVisible).to.be.eq(false);
cy.loginInShop(); cy.loginInShop();
}) })
.then(() => { .then(() => {
frontShopProductUtils.isProductVisible( isProductVisible(product.id, defaultChannel.slug, productName);
product.id,
defaultChannel.slug,
productName
);
}) })
.then(isVisible => { .then(isVisible => {
expect(isVisible).to.be.eq(true); expect(isVisible).to.be.eq(true);

View file

@ -4,14 +4,13 @@ import ProductSteps from "../../../steps/productSteps";
import { productDetailsUrl } from "../../../url/urlList"; import { productDetailsUrl } from "../../../url/urlList";
import ChannelsUtils from "../../../utils/channelsUtils"; import ChannelsUtils from "../../../utils/channelsUtils";
import ProductsUtils from "../../../utils/productsUtils"; import ProductsUtils from "../../../utils/productsUtils";
import StoreFrontProductUtils from "../../../utils/storeFront/storeFrontProductUtils"; import { isProductVisibleInSearchResult } from "../../../utils/storeFront/storeFrontProductUtils";
// <reference types="cypress" /> // <reference types="cypress" />
describe("Products displayed in listings", () => { describe("Products displayed in listings", () => {
const channelsUtils = new ChannelsUtils(); const channelsUtils = new ChannelsUtils();
const productsUtils = new ProductsUtils(); const productsUtils = new ProductsUtils();
const productSteps = new ProductSteps(); const productSteps = new ProductSteps();
const frontShopProductUtils = new StoreFrontProductUtils();
const startsWith = "Cy-"; const startsWith = "Cy-";
const name = `${startsWith}${faker.random.number()}`; const name = `${startsWith}${faker.random.number()}`;
@ -53,10 +52,7 @@ describe("Products displayed in listings", () => {
const product = productsUtils.getCreatedProduct(); const product = productsUtils.getCreatedProduct();
const productUrl = productDetailsUrl(product.id); const productUrl = productDetailsUrl(product.id);
productSteps.updateProductVisibleInListings(productUrl); productSteps.updateProductVisibleInListings(productUrl);
frontShopProductUtils.isProductVisibleInSearchResult( isProductVisibleInSearchResult(productName, defaultChannel.slug);
productName,
defaultChannel.slug
);
}) })
.then(isProductVisible => { .then(isProductVisible => {
expect(isProductVisible).to.be.eq(true); expect(isProductVisible).to.be.eq(true);
@ -82,18 +78,15 @@ describe("Products displayed in listings", () => {
const product = productsUtils.getCreatedProduct(); const product = productsUtils.getCreatedProduct();
const productUrl = productDetailsUrl(product.id); const productUrl = productDetailsUrl(product.id);
productSteps.updateProductVisibleInListings(productUrl); productSteps.updateProductVisibleInListings(productUrl);
frontShopProductUtils isProductVisibleInSearchResult(productName, defaultChannel.slug).then(
.isProductVisibleInSearchResult(productName, defaultChannel.slug) isProductVisible => {
.then(isProductVisible => {
expect(isProductVisible).to.be.eq(false); expect(isProductVisible).to.be.eq(false);
}); }
);
cy.loginInShop(); cy.loginInShop();
}) })
.then(() => { .then(() => {
frontShopProductUtils.isProductVisibleInSearchResult( isProductVisibleInSearchResult(productName, defaultChannel.slug);
productName,
defaultChannel.slug
);
}) })
.then(isProductVisible => { .then(isProductVisible => {
expect(isProductVisible).to.be.eq(true); expect(isProductVisible).to.be.eq(true);

View file

@ -39,9 +39,6 @@ Cypress.Commands.add("addAliasToGraphRequest", operationName => {
}); });
}); });
Cypress.Commands.add("sendFrontShopRequestWithQuery", query =>
cy.sendRequestWithQuery(query, "token")
);
Cypress.Commands.add("sendRequestWithQuery", (query, authorization = "auth") => Cypress.Commands.add("sendRequestWithQuery", (query, authorization = "auth") =>
cy.request({ cy.request({
body: { body: {

View file

@ -1,34 +1,32 @@
import ProductDetails from "../../apiRequests/storeFront/ProductDetails"; import ProductDetails from "../../apiRequests/storeFront/ProductDetails";
import Search from "../../apiRequests/storeFront/Search"; import Search from "../../apiRequests/storeFront/Search";
class StoreFrontProductUtils { export const isProductVisible = (productId, channelSlug, name) => {
isProductVisible(productId, channelSlug, name) { const productDetails = new ProductDetails();
const productDetails = new ProductDetails(); return productDetails
return productDetails .getProductDetails(productId, channelSlug)
.getProductDetails(productId, channelSlug) .then(productDetailsResp => {
.then(productDetailsResp => { const product = productDetailsResp.body.data.product;
const product = productDetailsResp.body.data.product; return product !== null && product.name === name;
return product !== null && product.name === name; });
}); };
}
isProductAvailableForPurchase(productId, channelSlug) { export const isProductAvailableForPurchase = (productId, channelSlug) => {
const productDetails = new ProductDetails(); const productDetails = new ProductDetails();
return productDetails return productDetails
.getProductDetails(productId, channelSlug) .getProductDetails(productId, channelSlug)
.then( .then(
productDetailsResp => productDetailsResp =>
productDetailsResp.body.data.product.isAvailableForPurchase productDetailsResp.body.data.product.isAvailableForPurchase
); );
} };
isProductVisibleInSearchResult(productName, channelSlug) { export const isProductVisibleInSearchResult = (productName, channelSlug) => {
const search = new Search(); const search = new Search();
return search return search
.searchInShop(productName, channelSlug) .searchInShop(productName, channelSlug)
.then( .then(
resp => resp =>
resp.body.data.products.totalCount !== 0 && resp.body.data.products.totalCount !== 0 &&
resp.body.data.products.edges[0].node.name === productName resp.body.data.products.edges[0].node.name === productName
); );
} };
}
export default StoreFrontProductUtils;

View file

@ -5603,13 +5603,6 @@
"context": "label", "context": "label",
"string": "Shipping rate name" "string": "Shipping rate name"
}, },
"src_dot_shipping_dot_components_dot_ShippingRateZipCodeRangeRemoveDialog_dot_3640694505": {
"string": "Are you sure you want to remove this postal code rule?"
},
"src_dot_shipping_dot_components_dot_ShippingRateZipCodeRangeRemoveDialog_dot_76039652": {
"context": "header",
"string": "Remove postal codes from Shipping Rate"
},
"src_dot_shipping_dot_components_dot_ShippingWeightUnitForm_dot_2863708228": { "src_dot_shipping_dot_components_dot_ShippingWeightUnitForm_dot_2863708228": {
"string": "This unit will be used as default shipping weight" "string": "This unit will be used as default shipping weight"
}, },
@ -5693,6 +5686,54 @@
"context": "label", "context": "label",
"string": "Shipping zone name" "string": "Shipping zone name"
}, },
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodeRangeDialog_dot_3070993206": {
"context": "range input label",
"string": "Postal codes (end)"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodeRangeDialog_dot_3099331554": {
"context": "add postal code range, button",
"string": "Add"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodeRangeDialog_dot_3419096551": {
"context": "range input label",
"string": "Postal codes (start)"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodeRangeDialog_dot_3668595137": {
"string": "Please provide range of postal codes you want to add to the include/exclude list."
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodeRangeDialog_dot_3849853790": {
"context": "dialog header",
"string": "Add postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_1301350004": {
"string": "This shipping rate has no postal codes assigned"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_1680649143": {
"context": "action",
"string": "Include postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_1779803917": {
"string": "Added postal codes will be excluded from using this delivery methods. If none are added all postal codes will be able to use that shipping rate"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_1909179974": {
"context": "button",
"string": "Add postal code range"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_2274108851": {
"context": "number of postal code ranges",
"string": "{number} postal code ranges"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_2965119249": {
"string": "Only added postal codes will be able to use this shipping rate"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_3782353530": {
"context": "postal codes, header",
"string": "Postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZonePostalCodes_dot_399764149": {
"context": "action",
"string": "Exclude postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZoneRatesCreatePage_dot_1161979494": { "src_dot_shipping_dot_components_dot_ShippingZoneRatesCreatePage_dot_1161979494": {
"context": "page title", "context": "page title",
"string": "Price Rate Create" "string": "Price Rate Create"
@ -5753,54 +5794,6 @@
"context": "input placeholder", "context": "input placeholder",
"string": "Select Warehouse" "string": "Select Warehouse"
}, },
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodeRangeDialog_dot_3070993206": {
"context": "range input label",
"string": "Postal codes (end)"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodeRangeDialog_dot_3099331554": {
"context": "add postal code range, button",
"string": "Add"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodeRangeDialog_dot_3419096551": {
"context": "range input label",
"string": "Postal codes (start)"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodeRangeDialog_dot_3668595137": {
"string": "Please provide range of postal codes you want to add to the include/exclude list."
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodeRangeDialog_dot_3849853790": {
"context": "dialog header",
"string": "Add postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_1301350004": {
"string": "This shipping rate has no postal codes assigned"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_1680649143": {
"context": "action",
"string": "Include postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_1779803917": {
"string": "Added postal codes will be excluded from using this delivery methods. If none are added all postal codes will be able to use that shipping rate"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_1909179974": {
"context": "button",
"string": "Add postal code range"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_2274108851": {
"context": "number of postal code ranges",
"string": "{number} postal code ranges"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_2965119249": {
"string": "Only added postal codes will be able to use this shipping rate"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_3782353530": {
"context": "postal codes, header",
"string": "Postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZoneZipCodes_dot_399764149": {
"context": "action",
"string": "Exclude postal codes"
},
"src_dot_shipping_dot_components_dot_ShippingZonesListPage_dot_1325966144": { "src_dot_shipping_dot_components_dot_ShippingZonesListPage_dot_1325966144": {
"context": "header", "context": "header",
"string": "Shipping" "string": "Shipping"
@ -5860,10 +5853,6 @@
"src_dot_shipping_dot_views_dot_PriceRatesUpdate_dot_3823295269": { "src_dot_shipping_dot_views_dot_PriceRatesUpdate_dot_3823295269": {
"string": "Manage Channel Availability" "string": "Manage Channel Availability"
}, },
"src_dot_shipping_dot_views_dot_PriceRatesUpdate_dot_4243341946": {
"context": "postal code range add error text",
"string": "Cannot add specified postal codes range."
},
"src_dot_shipping_dot_views_dot_PriceRatesUpdate_dot_870815507": { "src_dot_shipping_dot_views_dot_PriceRatesUpdate_dot_870815507": {
"context": "unassign products from shipping method, button", "context": "unassign products from shipping method, button",
"string": "Unassign" "string": "Unassign"
@ -5886,10 +5875,6 @@
"src_dot_shipping_dot_views_dot_WeightRatesUpdate_dot_3014453080": { "src_dot_shipping_dot_views_dot_WeightRatesUpdate_dot_3014453080": {
"string": "Manage Channels Availability" "string": "Manage Channels Availability"
}, },
"src_dot_shipping_dot_views_dot_WeightRatesUpdate_dot_4243341946": {
"context": "postal code range add error text",
"string": "Cannot add specified postal codes range."
},
"src_dot_shipping_dot_views_dot_WeightRatesUpdate_dot_870815507": { "src_dot_shipping_dot_views_dot_WeightRatesUpdate_dot_870815507": {
"context": "unassign products from shipping method, button", "context": "unassign products from shipping method, button",
"string": "Unassign" "string": "Unassign"

View file

@ -671,7 +671,7 @@ type Category implements Node & ObjectWithMetadata {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
slug: String! slug: String!
parent: Category parent: Category
level: Int! level: Int!
@ -746,7 +746,7 @@ type CategoryTranslatableContent implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
translation(languageCode: LanguageCodeEnum!): CategoryTranslation translation(languageCode: LanguageCodeEnum!): CategoryTranslation
category: Category category: Category
@ -763,7 +763,7 @@ type CategoryTranslation implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
language: LanguageDisplay! language: LanguageDisplay!
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
} }
@ -1050,7 +1050,7 @@ type Collection implements Node & ObjectWithMetadata {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
slug: String! slug: String!
privateMetadata: [MetadataItem]! privateMetadata: [MetadataItem]!
metadata: [MetadataItem]! metadata: [MetadataItem]!
@ -1205,7 +1205,7 @@ type CollectionTranslatableContent implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
translation(languageCode: LanguageCodeEnum!): CollectionTranslation translation(languageCode: LanguageCodeEnum!): CollectionTranslation
collection: Collection collection: Collection
@ -1222,7 +1222,7 @@ type CollectionTranslation implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
name: String! name: String!
description: JSONString! description: JSONString
language: LanguageDisplay! language: LanguageDisplay!
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
} }
@ -2607,8 +2607,6 @@ type Mutation {
shopAddressUpdate(input: AddressInput): ShopAddressUpdate shopAddressUpdate(input: AddressInput): ShopAddressUpdate
orderSettingsUpdate(input: OrderSettingsUpdateInput!): OrderSettingsUpdate orderSettingsUpdate(input: OrderSettingsUpdateInput!): OrderSettingsUpdate
shippingMethodChannelListingUpdate(id: ID!, input: ShippingMethodChannelListingInput!): ShippingMethodChannelListingUpdate shippingMethodChannelListingUpdate(id: ID!, input: ShippingMethodChannelListingInput!): ShippingMethodChannelListingUpdate
shippingMethodZipCodeRulesCreate(input: ShippingZipCodeRulesCreateInput!, shippingMethodId: ID!): ShippingZipCodeRulesCreate
shippingMethodZipCodeRulesDelete(id: ID!): ShippingZipCodeRulesDelete
shippingPriceCreate(input: ShippingPriceInput!): ShippingPriceCreate shippingPriceCreate(input: ShippingPriceInput!): ShippingPriceCreate
shippingPriceDelete(id: ID!): ShippingPriceDelete shippingPriceDelete(id: ID!): ShippingPriceDelete
shippingPriceBulkDelete(ids: [ID]!): ShippingPriceBulkDelete shippingPriceBulkDelete(ids: [ID]!): ShippingPriceBulkDelete
@ -3307,7 +3305,7 @@ type Page implements Node & ObjectWithMetadata {
seoDescription: String seoDescription: String
id: ID! id: ID!
title: String! title: String!
content: JSONString! content: JSONString
publicationDate: Date publicationDate: Date
isPublished: Boolean! isPublished: Boolean!
slug: String! slug: String!
@ -3441,7 +3439,7 @@ type PageTranslatableContent implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
title: String! title: String!
content: JSONString! content: JSONString
contentJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `content` field instead.") contentJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `content` field instead.")
translation(languageCode: LanguageCodeEnum!): PageTranslation translation(languageCode: LanguageCodeEnum!): PageTranslation
page: Page page: Page
@ -3458,7 +3456,7 @@ type PageTranslation implements Node {
seoDescription: String seoDescription: String
id: ID! id: ID!
title: String! title: String!
content: JSONString! content: JSONString
language: LanguageDisplay! language: LanguageDisplay!
contentJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `content` field instead.") contentJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `content` field instead.")
} }
@ -3824,6 +3822,11 @@ input PluginUpdateInput {
scalar PositiveDecimal scalar PositiveDecimal
enum PostalCodeRuleInclusionTypeEnum {
INCLUDE
EXCLUDE
}
input PriceRangeInput { input PriceRangeInput {
gte: Float gte: Float
lte: Float lte: Float
@ -3834,7 +3837,7 @@ type Product implements Node & ObjectWithMetadata {
seoTitle: String seoTitle: String
seoDescription: String seoDescription: String
name: String! name: String!
description: JSONString! description: JSONString
productType: ProductType! productType: ProductType!
slug: String! slug: String!
category: Category category: Category
@ -4140,7 +4143,7 @@ type ProductTranslatableContent implements Node {
seoTitle: String seoTitle: String
seoDescription: String seoDescription: String
name: String! name: String!
description: JSONString! description: JSONString
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
translation(languageCode: LanguageCodeEnum!): ProductTranslation translation(languageCode: LanguageCodeEnum!): ProductTranslation
product: Product product: Product
@ -4157,7 +4160,7 @@ type ProductTranslation implements Node {
seoTitle: String seoTitle: String
seoDescription: String seoDescription: String
name: String! name: String!
description: JSONString! description: JSONString
language: LanguageDisplay! language: LanguageDisplay!
descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.") descriptionJson: JSONString @deprecated(reason: "Will be removed in Saleor 4.0. Use the `description` field instead.")
} }
@ -4746,7 +4749,7 @@ type ShippingMethod implements Node & ObjectWithMetadata {
price: Money price: Money
maximumOrderPrice: Money maximumOrderPrice: Money
minimumOrderPrice: Money minimumOrderPrice: Money
zipCodeRules: [ShippingMethodZipCodeRule] postalCodeRules: [ShippingMethodPostalCodeRule]
excludedProducts(before: String, after: String, first: Int, last: Int): ProductCountableConnection excludedProducts(before: String, after: String, first: Int, last: Int): ProductCountableConnection
} }
@ -4776,6 +4779,13 @@ type ShippingMethodChannelListingUpdate {
shippingErrors: [ShippingError!]! shippingErrors: [ShippingError!]!
} }
type ShippingMethodPostalCodeRule implements Node {
start: String
end: String
inclusionType: PostalCodeRuleInclusionTypeEnum
id: ID!
}
type ShippingMethodTranslatableContent implements Node { type ShippingMethodTranslatableContent implements Node {
id: ID! id: ID!
name: String! name: String!
@ -4794,10 +4804,9 @@ enum ShippingMethodTypeEnum {
WEIGHT WEIGHT
} }
type ShippingMethodZipCodeRule implements Node { input ShippingPostalCodeRulesCreateInputRange {
start: String start: String!
end: String end: String
id: ID!
} }
type ShippingPriceBulkDelete { type ShippingPriceBulkDelete {
@ -4838,6 +4847,9 @@ input ShippingPriceInput {
minimumDeliveryDays: Int minimumDeliveryDays: Int
type: ShippingMethodTypeEnum type: ShippingMethodTypeEnum
shippingZone: ID shippingZone: ID
addPostalCodeRules: [ShippingPostalCodeRulesCreateInputRange!]
deletePostalCodeRules: [ID!]
inclusionType: PostalCodeRuleInclusionTypeEnum
} }
type ShippingPriceRemoveProductFromExclude { type ShippingPriceRemoveProductFromExclude {
@ -4859,29 +4871,6 @@ type ShippingPriceUpdate {
shippingErrors: [ShippingError!]! shippingErrors: [ShippingError!]!
} }
type ShippingZipCodeRulesCreate {
errors: [Error!]! @deprecated(reason: "Use typed errors with error codes. This field will be removed after 2020-07-31.")
zipCodeRules: [ShippingMethodZipCodeRule]
shippingMethod: ShippingMethod
shippingErrors: [ShippingError!]!
}
input ShippingZipCodeRulesCreateInput {
zipCodeRules: [ShippingZipCodeRulesCreateInputRange]!
}
input ShippingZipCodeRulesCreateInputRange {
start: String!
end: String
}
type ShippingZipCodeRulesDelete {
errors: [Error!]! @deprecated(reason: "Use typed errors with error codes. This field will be removed after 2020-07-31.")
shippingMethod: ShippingMethod
shippingErrors: [ShippingError!]!
shippingMethodZipCodeRule: ShippingMethodZipCodeRule
}
type ShippingZone implements Node & ObjectWithMetadata { type ShippingZone implements Node & ObjectWithMetadata {
id: ID! id: ID!
name: String! name: String!

View file

@ -39,7 +39,7 @@ export interface CategoryCreate_categoryCreate_category {
backgroundImage: CategoryCreate_categoryCreate_category_backgroundImage | null; backgroundImage: CategoryCreate_categoryCreate_category_backgroundImage | null;
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
parent: CategoryCreate_categoryCreate_category_parent | null; parent: CategoryCreate_categoryCreate_category_parent | null;

View file

@ -165,7 +165,7 @@ export interface CategoryDetails_category {
backgroundImage: CategoryDetails_category_backgroundImage | null; backgroundImage: CategoryDetails_category_backgroundImage | null;
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
parent: CategoryDetails_category_parent | null; parent: CategoryDetails_category_parent | null;

View file

@ -39,7 +39,7 @@ export interface CategoryUpdate_categoryUpdate_category {
backgroundImage: CategoryUpdate_categoryUpdate_category_backgroundImage | null; backgroundImage: CategoryUpdate_categoryUpdate_category_backgroundImage | null;
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
parent: CategoryUpdate_categoryUpdate_category_parent | null; parent: CategoryUpdate_categoryUpdate_category_parent | null;

View file

@ -1,6 +1,7 @@
import { WindowTitle } from "@saleor/components/WindowTitle"; import { WindowTitle } from "@saleor/components/WindowTitle";
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 { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler"; import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler";
import { import {
useMetadataUpdate, useMetadataUpdate,
@ -48,7 +49,7 @@ export const CategoryCreateView: React.FC<CategoryCreateViewProps> = ({
const result = await createCategory({ const result = await createCategory({
variables: { variables: {
input: { input: {
description: JSON.stringify(formData.description), description: getParsedDataForJsonStringField(formData.description),
name: formData.name, name: formData.name,
seo: { seo: {
description: formData.seoDescription, description: formData.seoDescription,

View file

@ -13,6 +13,7 @@ import usePaginator, {
createPaginationState createPaginationState
} from "@saleor/hooks/usePaginator"; } from "@saleor/hooks/usePaginator";
import { commonMessages } from "@saleor/intl"; import { commonMessages } from "@saleor/intl";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler"; import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler";
import { mapNodeToChoice } from "@saleor/utils/maps"; import { mapNodeToChoice } from "@saleor/utils/maps";
@ -188,7 +189,7 @@ export const CategoryDetails: React.FC<CategoryDetailsProps> = ({
id, id,
input: { input: {
backgroundImageAlt: formData.backgroundImageAlt, backgroundImageAlt: formData.backgroundImageAlt,
description: JSON.stringify(formData.description), description: getParsedDataForJsonStringField(formData.description),
name: formData.name, name: formData.name,
seo: { seo: {
description: formData.seoDescription, description: formData.seoDescription,

View file

@ -10,8 +10,8 @@ import ChannelDeleteDialog, {
const props: ChannelDeleteDialogProps = { const props: ChannelDeleteDialogProps = {
channelsChoices: mapNodeToChoice(channelsList), channelsChoices: mapNodeToChoice(channelsList),
hasOrders: true,
confirmButtonState: "default", confirmButtonState: "default",
hasOrders: true,
onBack: () => undefined, onBack: () => undefined,
onClose: () => undefined, onClose: () => undefined,
onConfirm: () => undefined, onConfirm: () => undefined,

View file

@ -13,16 +13,20 @@ import { defineMessages, useIntl } from "react-intl";
import { useStyles } from "../styles"; import { useStyles } from "../styles";
const messages = defineMessages({ const messages = defineMessages({
needToBeMoved: { deleteChannel: {
defaultMessage: defaultMessage: "Delete Channel",
"All order information from this channel need to be moved to a different channel. Please select channel orders need to be moved to:.", description: "dialog header"
description: "delete channel"
}, },
deletingAllProductData: { deletingAllProductData: {
defaultMessage: defaultMessage:
"Deleting channel will delete all product data regarding this channel. Are you sure you want to delete this channel?", "Deleting channel will delete all product data regarding this channel. Are you sure you want to delete this channel?",
description: "delete channel" description: "delete channel"
}, },
needToBeMoved: {
defaultMessage:
"All order information from this channel need to be moved to a different channel. Please select channel orders need to be moved to:.",
description: "delete channel"
},
noAvailableChannel: { noAvailableChannel: {
defaultMessage: defaultMessage:
"There is no available channel to move order information to. Please create a channel with same currency so that information can be moved to it.", "There is no available channel to move order information to. Please create a channel with same currency so that information can be moved to it.",
@ -31,10 +35,6 @@ const messages = defineMessages({
selectChannel: { selectChannel: {
defaultMessage: "Select Channel", defaultMessage: "Select Channel",
description: "dialog header" description: "dialog header"
},
deleteChannel: {
defaultMessage: "Delete Channel",
description: "dialog header"
} }
}); });

View file

@ -72,8 +72,8 @@ export const channelsList: Channels_channels[] = [
{ {
__typename: "Channel", __typename: "Channel",
currencyCode: "euro", currencyCode: "euro",
id: "Q2hhbm5lbDo5w0z",
hasOrders: false, hasOrders: false,
id: "Q2hhbm5lbDo5w0z",
isActive: true, isActive: true,
name: "Channel USD", name: "Channel USD",
slug: "channel-usd1" slug: "channel-usd1"

View file

@ -102,7 +102,7 @@ export interface CollectionDetails_collection {
privateMetadata: (CollectionDetails_collection_privateMetadata | null)[]; privateMetadata: (CollectionDetails_collection_privateMetadata | null)[];
backgroundImage: CollectionDetails_collection_backgroundImage | null; backgroundImage: CollectionDetails_collection_backgroundImage | null;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
products: CollectionDetails_collection_products | null; products: CollectionDetails_collection_products | null;

View file

@ -48,7 +48,7 @@ export interface CollectionUpdate_collectionUpdate_collection {
privateMetadata: (CollectionUpdate_collectionUpdate_collection_privateMetadata | null)[]; privateMetadata: (CollectionUpdate_collectionUpdate_collection_privateMetadata | null)[];
backgroundImage: CollectionUpdate_collectionUpdate_collection_backgroundImage | null; backgroundImage: CollectionUpdate_collectionUpdate_collection_backgroundImage | null;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

View file

@ -48,7 +48,7 @@ export interface CreateCollection_collectionCreate_collection {
privateMetadata: (CreateCollection_collectionCreate_collection_privateMetadata | null)[]; privateMetadata: (CreateCollection_collectionCreate_collection_privateMetadata | null)[];
backgroundImage: CreateCollection_collectionCreate_collection_backgroundImage | null; backgroundImage: CreateCollection_collectionCreate_collection_backgroundImage | null;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

View file

@ -7,6 +7,7 @@ import useChannels from "@saleor/hooks/useChannels";
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 { commonMessages } from "@saleor/intl"; import { commonMessages } from "@saleor/intl";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler"; import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler";
import { import {
@ -102,7 +103,7 @@ export const CollectionCreate: React.FC<CollectionCreateProps> = ({
input: { input: {
backgroundImage: formData.backgroundImage.value, backgroundImage: formData.backgroundImage.value,
backgroundImageAlt: formData.backgroundImageAlt, backgroundImageAlt: formData.backgroundImageAlt,
description: JSON.stringify(formData.description), description: getParsedDataForJsonStringField(formData.description),
name: formData.name, name: formData.name,
seo: { seo: {
description: formData.seoDescription, description: formData.seoDescription,

View file

@ -21,6 +21,7 @@ import usePaginator, {
} from "@saleor/hooks/usePaginator"; } from "@saleor/hooks/usePaginator";
import { commonMessages } from "@saleor/intl"; import { commonMessages } from "@saleor/intl";
import useProductSearch from "@saleor/searches/useProductSearch"; import useProductSearch from "@saleor/searches/useProductSearch";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler"; import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler";
import { import {
@ -198,7 +199,7 @@ export const CollectionDetails: React.FC<CollectionDetailsProps> = ({
const handleUpdate = async (formData: CollectionUpdateData) => { const handleUpdate = async (formData: CollectionUpdateData) => {
const input: CollectionInput = { const input: CollectionInput = {
backgroundImageAlt: formData.backgroundImageAlt, backgroundImageAlt: formData.backgroundImageAlt,
description: JSON.stringify(formData.description), description: getParsedDataForJsonStringField(formData.description),
name: formData.name, name: formData.name,
seo: { seo: {
description: formData.seoDescription, description: formData.seoDescription,

View file

@ -26,26 +26,26 @@ const messages = defineMessages({
defaultAddress: { defaultAddress: {
defaultMessage: "Default Address" defaultMessage: "Default Address"
}, },
defaultShippingAddress: {
defaultMessage: "Default Shipping Address"
},
defaultBillingAddress: { defaultBillingAddress: {
defaultMessage: "Default Billing Address" defaultMessage: "Default Billing Address"
}, },
setDefaultShipping: { defaultShippingAddress: {
defaultMessage: "Set as default shipping address", defaultMessage: "Default Shipping Address"
description: "button"
}, },
setDefaultBilling: { deleteAddress: {
defaultMessage: "Set as default billing address", defaultMessage: "Delete Address",
description: "button" description: "button"
}, },
editAddress: { editAddress: {
defaultMessage: "Edit Address", defaultMessage: "Edit Address",
description: "button" description: "button"
}, },
deleteAddress: { setDefaultBilling: {
defaultMessage: "Delete Address", defaultMessage: "Set as default billing address",
description: "button"
},
setDefaultShipping: {
defaultMessage: "Set as default shipping address",
description: "button" description: "button"
} }
}); });

View file

@ -23,6 +23,14 @@ export interface CustomerAddressListPageProps {
} }
const messages = defineMessages({ const messages = defineMessages({
addAddress: {
defaultMessage: "Add address",
description: "button"
},
doesntHaveAddresses: {
defaultMessage:
"This customer doesnt have any adresses added to his address book. You can add address using the button below."
},
fullNameAddress: { fullNameAddress: {
defaultMessage: "{fullName}'s Address Book", defaultMessage: "{fullName}'s Address Book",
description: "customer's address book, header" description: "customer's address book, header"
@ -31,16 +39,8 @@ const messages = defineMessages({
defaultMessage: "{fullName} Details", defaultMessage: "{fullName} Details",
description: "customer details, header" description: "customer details, header"
}, },
addAddress: {
defaultMessage: "Add address",
description: "button"
},
noAddressToShow: { noAddressToShow: {
defaultMessage: "There is no address to show for this customer" defaultMessage: "There is no address to show for this customer"
},
doesntHaveAddresses: {
defaultMessage:
"This customer doesnt have any adresses added to his address book. You can add address using the button below."
} }
}); });

View file

@ -64,8 +64,8 @@ const CustomerDetailsPage: React.FC<CustomerDetailsPageProps> = ({
firstName: customer?.firstName || "", firstName: customer?.firstName || "",
isActive: customer?.isActive || false, isActive: customer?.isActive || false,
lastName: customer?.lastName || "", lastName: customer?.lastName || "",
note: customer?.note || "",
metadata: customer?.metadata.map(mapMetadataItemToInput), metadata: customer?.metadata.map(mapMetadataItemToInput),
note: customer?.note || "",
privateMetadata: customer?.privateMetadata.map(mapMetadataItemToInput) privateMetadata: customer?.privateMetadata.map(mapMetadataItemToInput)
}; };

View file

@ -946,8 +946,6 @@ export const customerList: ListCustomers_customers_edges_node[] = [
]; ];
export const customer: CustomerDetails_user & CustomerAddresses_user = { export const customer: CustomerDetails_user & CustomerAddresses_user = {
__typename: "User", __typename: "User",
metadata: [],
privateMetadata: [],
addresses: [ addresses: [
{ {
__typename: "Address", __typename: "Address",
@ -1046,6 +1044,7 @@ export const customer: CustomerDetails_user & CustomerAddresses_user = {
} }
] ]
}, },
metadata: [],
note: null, note: null,
orders: { orders: {
__typename: "OrderCountableConnection", __typename: "OrderCountableConnection",
@ -1069,5 +1068,6 @@ export const customer: CustomerDetails_user & CustomerAddresses_user = {
} }
} }
] ]
} },
privateMetadata: []
}; };

View file

@ -17,11 +17,12 @@ export const shippingZoneFragment = gql`
} }
`; `;
export const shippingMethodWithZipCodesFragment = gql` export const shippingMethodWithPostalCodesFragment = gql`
fragment ShippingMethodWithZipCodesFragment on ShippingMethod { fragment ShippingMethodWithPostalCodesFragment on ShippingMethod {
id id
zipCodeRules { postalCodeRules {
id id
inclusionType
start start
end end
} }
@ -30,9 +31,9 @@ export const shippingMethodWithZipCodesFragment = gql`
export const shippingMethodFragment = gql` export const shippingMethodFragment = gql`
${metadataFragment} ${metadataFragment}
${fragmentMoney} ${fragmentMoney}
${shippingMethodWithZipCodesFragment} ${shippingMethodWithPostalCodesFragment}
fragment ShippingMethodFragment on ShippingMethod { fragment ShippingMethodFragment on ShippingMethod {
...ShippingMethodWithZipCodesFragment ...ShippingMethodWithPostalCodesFragment
...MetadataFragment ...MetadataFragment
minimumOrderWeight { minimumOrderWeight {
unit unit

View file

@ -37,7 +37,7 @@ export interface CategoryDetailsFragment {
backgroundImage: CategoryDetailsFragment_backgroundImage | null; backgroundImage: CategoryDetailsFragment_backgroundImage | null;
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
parent: CategoryDetailsFragment_parent | null; parent: CategoryDetailsFragment_parent | null;

View file

@ -14,7 +14,7 @@ export interface CategoryTranslationFragment_translation_language {
export interface CategoryTranslationFragment_translation { export interface CategoryTranslationFragment_translation {
__typename: "CategoryTranslation"; __typename: "CategoryTranslation";
id: string; id: string;
description: any; description: any | null;
language: CategoryTranslationFragment_translation_language; language: CategoryTranslationFragment_translation_language;
name: string; name: string;
seoDescription: string | null; seoDescription: string | null;
@ -25,7 +25,7 @@ export interface CategoryTranslationFragment_category {
__typename: "Category"; __typename: "Category";
id: string; id: string;
name: string; name: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

View file

@ -46,7 +46,7 @@ export interface CollectionDetailsFragment {
privateMetadata: (CollectionDetailsFragment_privateMetadata | null)[]; privateMetadata: (CollectionDetailsFragment_privateMetadata | null)[];
backgroundImage: CollectionDetailsFragment_backgroundImage | null; backgroundImage: CollectionDetailsFragment_backgroundImage | null;
slug: string; slug: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

View file

@ -10,7 +10,7 @@ export interface CollectionTranslationFragment_collection {
__typename: "Collection"; __typename: "Collection";
id: string; id: string;
name: string; name: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }
@ -23,7 +23,7 @@ export interface CollectionTranslationFragment_translation_language {
export interface CollectionTranslationFragment_translation { export interface CollectionTranslationFragment_translation {
__typename: "CollectionTranslation"; __typename: "CollectionTranslation";
id: string; id: string;
description: any; description: any | null;
language: CollectionTranslationFragment_translation_language; language: CollectionTranslationFragment_translation_language;
name: string; name: string;
seoDescription: string | null; seoDescription: string | null;

View file

@ -109,7 +109,7 @@ export interface PageDetailsFragment {
pageType: PageDetailsFragment_pageType; pageType: PageDetailsFragment_pageType;
metadata: (PageDetailsFragment_metadata | null)[]; metadata: (PageDetailsFragment_metadata | null)[];
privateMetadata: (PageDetailsFragment_privateMetadata | null)[]; privateMetadata: (PageDetailsFragment_privateMetadata | null)[];
content: any; content: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
publicationDate: any | null; publicationDate: any | null;

View file

@ -17,7 +17,7 @@ export interface PageTranslatableFragment_translation_language {
export interface PageTranslatableFragment_translation { export interface PageTranslatableFragment_translation {
__typename: "PageTranslation"; __typename: "PageTranslation";
id: string; id: string;
content: any; content: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
title: string; title: string;
@ -27,7 +27,7 @@ export interface PageTranslatableFragment_translation {
export interface PageTranslatableFragment { export interface PageTranslatableFragment {
__typename: "PageTranslatableContent"; __typename: "PageTranslatableContent";
id: string; id: string;
content: any; content: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
title: string; title: string;

View file

@ -11,7 +11,7 @@ import { LanguageCodeEnum } from "./../../types/globalTypes";
export interface PageTranslationFragment_page { export interface PageTranslationFragment_page {
__typename: "Page"; __typename: "Page";
id: string; id: string;
content: any; content: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
title: string; title: string;
@ -26,7 +26,7 @@ export interface PageTranslationFragment_translation_language {
export interface PageTranslationFragment_translation { export interface PageTranslationFragment_translation {
__typename: "PageTranslation"; __typename: "PageTranslation";
id: string; id: string;
content: any; content: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
title: string; title: string;

View file

@ -253,7 +253,7 @@ export interface Product {
privateMetadata: (Product_privateMetadata | null)[]; privateMetadata: (Product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -12,7 +12,7 @@ export interface ProductTranslationFragment_product {
__typename: "Product"; __typename: "Product";
id: string; id: string;
name: string; name: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }
@ -26,7 +26,7 @@ export interface ProductTranslationFragment_translation_language {
export interface ProductTranslationFragment_translation { export interface ProductTranslationFragment_translation {
__typename: "ProductTranslation"; __typename: "ProductTranslation";
id: string; id: string;
description: any; description: any | null;
language: ProductTranslationFragment_translation_language; language: ProductTranslationFragment_translation_language;
name: string; name: string;
seoDescription: string | null; seoDescription: string | null;

View file

@ -2,15 +2,16 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL fragment: ShippingMethodFragment // GraphQL fragment: ShippingMethodFragment
// ==================================================== // ====================================================
export interface ShippingMethodFragment_zipCodeRules { export interface ShippingMethodFragment_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -76,7 +77,7 @@ export interface ShippingMethodFragment_channelListings {
export interface ShippingMethodFragment { export interface ShippingMethodFragment {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingMethodFragment_zipCodeRules | null)[] | null; postalCodeRules: (ShippingMethodFragment_postalCodeRules | null)[] | null;
metadata: (ShippingMethodFragment_metadata | null)[]; metadata: (ShippingMethodFragment_metadata | null)[];
privateMetadata: (ShippingMethodFragment_privateMetadata | null)[]; privateMetadata: (ShippingMethodFragment_privateMetadata | null)[];
minimumOrderWeight: ShippingMethodFragment_minimumOrderWeight | null; minimumOrderWeight: ShippingMethodFragment_minimumOrderWeight | null;

View file

@ -2,15 +2,16 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL fragment: ShippingMethodWithExcludedProductsFragment // GraphQL fragment: ShippingMethodWithExcludedProductsFragment
// ==================================================== // ====================================================
export interface ShippingMethodWithExcludedProductsFragment_zipCodeRules { export interface ShippingMethodWithExcludedProductsFragment_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -107,7 +108,7 @@ export interface ShippingMethodWithExcludedProductsFragment_excludedProducts {
export interface ShippingMethodWithExcludedProductsFragment { export interface ShippingMethodWithExcludedProductsFragment {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingMethodWithExcludedProductsFragment_zipCodeRules | null)[] | null; postalCodeRules: (ShippingMethodWithExcludedProductsFragment_postalCodeRules | null)[] | null;
metadata: (ShippingMethodWithExcludedProductsFragment_metadata | null)[]; metadata: (ShippingMethodWithExcludedProductsFragment_metadata | null)[];
privateMetadata: (ShippingMethodWithExcludedProductsFragment_privateMetadata | null)[]; privateMetadata: (ShippingMethodWithExcludedProductsFragment_privateMetadata | null)[];
minimumOrderWeight: ShippingMethodWithExcludedProductsFragment_minimumOrderWeight | null; minimumOrderWeight: ShippingMethodWithExcludedProductsFragment_minimumOrderWeight | null;

View file

@ -0,0 +1,23 @@
/* tslint:disable */
/* eslint-disable */
// This file was automatically generated and should not be edited.
import { PostalCodeRuleInclusionTypeEnum } from "./../../types/globalTypes";
// ====================================================
// GraphQL fragment: ShippingMethodWithPostalCodesFragment
// ====================================================
export interface ShippingMethodWithPostalCodesFragment_postalCodeRules {
__typename: "ShippingMethodPostalCodeRule";
id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null;
end: string | null;
}
export interface ShippingMethodWithPostalCodesFragment {
__typename: "ShippingMethod";
id: string;
postalCodeRules: (ShippingMethodWithPostalCodesFragment_postalCodeRules | null)[] | null;
}

View file

@ -2,13 +2,16 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { PostalCodeRuleInclusionTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL fragment: ShippingMethodWithZipCodesFragment // GraphQL fragment: ShippingMethodWithZipCodesFragment
// ==================================================== // ====================================================
export interface ShippingMethodWithZipCodesFragment_zipCodeRules { export interface ShippingMethodWithZipCodesFragment_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -16,5 +19,5 @@ export interface ShippingMethodWithZipCodesFragment_zipCodeRules {
export interface ShippingMethodWithZipCodesFragment { export interface ShippingMethodWithZipCodesFragment {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingMethodWithZipCodesFragment_zipCodeRules | null)[] | null; postalCodeRules: (ShippingMethodWithZipCodesFragment_postalCodeRules | null)[] | null;
} }

View file

@ -2,7 +2,7 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL fragment: ShippingZoneDetailsFragment // GraphQL fragment: ShippingZoneDetailsFragment
@ -26,9 +26,10 @@ export interface ShippingZoneDetailsFragment_countries {
country: string; country: string;
} }
export interface ShippingZoneDetailsFragment_shippingMethods_zipCodeRules { export interface ShippingZoneDetailsFragment_shippingMethods_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -94,7 +95,7 @@ export interface ShippingZoneDetailsFragment_shippingMethods_channelListings {
export interface ShippingZoneDetailsFragment_shippingMethods { export interface ShippingZoneDetailsFragment_shippingMethods {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingZoneDetailsFragment_shippingMethods_zipCodeRules | null)[] | null; postalCodeRules: (ShippingZoneDetailsFragment_shippingMethods_postalCodeRules | null)[] | null;
metadata: (ShippingZoneDetailsFragment_shippingMethods_metadata | null)[]; metadata: (ShippingZoneDetailsFragment_shippingMethods_metadata | null)[];
privateMetadata: (ShippingZoneDetailsFragment_shippingMethods_privateMetadata | null)[]; privateMetadata: (ShippingZoneDetailsFragment_shippingMethods_privateMetadata | null)[];
minimumOrderWeight: ShippingZoneDetailsFragment_shippingMethods_minimumOrderWeight | null; minimumOrderWeight: ShippingZoneDetailsFragment_shippingMethods_minimumOrderWeight | null;

View file

@ -167,8 +167,8 @@ const Routes: React.FC = () => {
dispatchAppState({ dispatchAppState({
payload: { payload: {
errorId, error: "unhandled",
error: "unhandled" errorId
}, },
type: "displayError" type: "displayError"
}); });

View file

@ -122,7 +122,7 @@ function usePageForm(
title: page?.title || "" title: page?.title || ""
}); });
const [content, changeContent] = useRichText({ const [content, changeContent] = useRichText({
initial: pageExists ? page?.content : null, initial: page?.content,
triggerChange triggerChange
}); });

View file

@ -117,7 +117,7 @@ export interface PageCreate_pageCreate_page {
pageType: PageCreate_pageCreate_page_pageType; pageType: PageCreate_pageCreate_page_pageType;
metadata: (PageCreate_pageCreate_page_metadata | null)[]; metadata: (PageCreate_pageCreate_page_metadata | null)[];
privateMetadata: (PageCreate_pageCreate_page_privateMetadata | null)[]; privateMetadata: (PageCreate_pageCreate_page_privateMetadata | null)[];
content: any; content: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
publicationDate: any | null; publicationDate: any | null;

View file

@ -109,7 +109,7 @@ export interface PageDetails_page {
pageType: PageDetails_page_pageType; pageType: PageDetails_page_pageType;
metadata: (PageDetails_page_metadata | null)[]; metadata: (PageDetails_page_metadata | null)[];
privateMetadata: (PageDetails_page_privateMetadata | null)[]; privateMetadata: (PageDetails_page_privateMetadata | null)[];
content: any; content: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
publicationDate: any | null; publicationDate: any | null;

View file

@ -116,7 +116,7 @@ export interface PageUpdate_pageUpdate_page {
pageType: PageUpdate_pageUpdate_page_pageType; pageType: PageUpdate_pageUpdate_page_pageType;
metadata: (PageUpdate_pageUpdate_page_metadata | null)[]; metadata: (PageUpdate_pageUpdate_page_metadata | null)[];
privateMetadata: (PageUpdate_pageUpdate_page_privateMetadata | null)[]; privateMetadata: (PageUpdate_pageUpdate_page_privateMetadata | null)[];
content: any; content: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
publicationDate: any | null; publicationDate: any | null;

View file

@ -12,6 +12,7 @@ import useNotifier from "@saleor/hooks/useNotifier";
import usePageSearch from "@saleor/searches/usePageSearch"; import usePageSearch from "@saleor/searches/usePageSearch";
import usePageTypeSearch from "@saleor/searches/usePageTypeSearch"; import usePageTypeSearch from "@saleor/searches/usePageTypeSearch";
import useProductSearch from "@saleor/searches/useProductSearch"; import useProductSearch from "@saleor/searches/useProductSearch";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler"; import createMetadataCreateHandler from "@saleor/utils/handlers/metadataCreateHandler";
import { import {
useMetadataUpdate, useMetadataUpdate,
@ -128,7 +129,7 @@ export const PageCreate: React.FC<PageCreateProps> = ({ params }) => {
attributes: formData.attributes, attributes: formData.attributes,
updatedFileAttributes updatedFileAttributes
}), }),
content: JSON.stringify(formData.content), content: getParsedDataForJsonStringField(formData.content),
isPublished: formData.isPublished, isPublished: formData.isPublished,
pageType: formData.pageType, pageType: formData.pageType,
publicationDate: formData.publicationDate, publicationDate: formData.publicationDate,

View file

@ -23,6 +23,7 @@ import useNotifier from "@saleor/hooks/useNotifier";
import { commonMessages } from "@saleor/intl"; import { commonMessages } from "@saleor/intl";
import usePageSearch from "@saleor/searches/usePageSearch"; import usePageSearch from "@saleor/searches/usePageSearch";
import useProductSearch from "@saleor/searches/useProductSearch"; import useProductSearch from "@saleor/searches/useProductSearch";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler"; import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler";
import { import {
useMetadataUpdate, useMetadataUpdate,
@ -53,7 +54,7 @@ const createPageInput = (
attributes: data.attributes, attributes: data.attributes,
updatedFileAttributes updatedFileAttributes
}), }),
content: JSON.stringify(data.content), content: getParsedDataForJsonStringField(data.content),
isPublished: data.isPublished, isPublished: data.isPublished,
publicationDate: data.publicationDate, publicationDate: data.publicationDate,
seo: { seo: {

View file

@ -220,7 +220,7 @@ function useProductUpdateForm(
triggerChange(); triggerChange();
}; };
const handleCollectionSelect = createMultiAutocompleteSelectHandler( const handleCollectionSelect = createMultiAutocompleteSelectHandler(
form.toggleValue, event => form.toggleValue(event, triggerChange),
opts.setSelectedCollections, opts.setSelectedCollections,
opts.selectedCollections, opts.selectedCollections,
opts.collections opts.collections

View file

@ -253,7 +253,7 @@ export interface ProductChannelListingUpdate_productChannelListingUpdate_product
privateMetadata: (ProductChannelListingUpdate_productChannelListingUpdate_product_privateMetadata | null)[]; privateMetadata: (ProductChannelListingUpdate_productChannelListingUpdate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -260,7 +260,7 @@ export interface ProductCreate_productCreate_product {
privateMetadata: (ProductCreate_productCreate_product_privateMetadata | null)[]; privateMetadata: (ProductCreate_productCreate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -253,7 +253,7 @@ export interface ProductDetails_product {
privateMetadata: (ProductDetails_product_privateMetadata | null)[]; privateMetadata: (ProductDetails_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -259,7 +259,7 @@ export interface ProductImageCreate_productImageCreate_product {
privateMetadata: (ProductImageCreate_productImageCreate_product_privateMetadata | null)[]; privateMetadata: (ProductImageCreate_productImageCreate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -259,7 +259,7 @@ export interface ProductImageUpdate_productImageUpdate_product {
privateMetadata: (ProductImageUpdate_productImageUpdate_product_privateMetadata | null)[]; privateMetadata: (ProductImageUpdate_productImageUpdate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -260,7 +260,7 @@ export interface ProductUpdate_productUpdate_product {
privateMetadata: (ProductUpdate_productUpdate_product_privateMetadata | null)[]; privateMetadata: (ProductUpdate_productUpdate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -259,7 +259,7 @@ export interface ProductVariantReorder_productVariantReorder_product {
privateMetadata: (ProductVariantReorder_productVariantReorder_product_privateMetadata | null)[]; privateMetadata: (ProductVariantReorder_productVariantReorder_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -259,7 +259,7 @@ export interface ProductVariantSetDefault_productVariantSetDefault_product {
privateMetadata: (ProductVariantSetDefault_productVariantSetDefault_product_privateMetadata | null)[]; privateMetadata: (ProductVariantSetDefault_productVariantSetDefault_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -260,7 +260,7 @@ export interface SimpleProductUpdate_productUpdate_product {
privateMetadata: (SimpleProductUpdate_productUpdate_product_privateMetadata | null)[]; privateMetadata: (SimpleProductUpdate_productUpdate_product_privateMetadata | null)[];
name: string; name: string;
slug: string; slug: string;
description: any; description: any | null;
seoTitle: string | null; seoTitle: string | null;
seoDescription: string | null; seoDescription: string | null;
rating: number | null; rating: number | null;

View file

@ -37,6 +37,7 @@ import {
} from "@saleor/products/types/VariantCreate"; } from "@saleor/products/types/VariantCreate";
import { getAvailabilityVariables } from "@saleor/products/utils/handlers"; import { getAvailabilityVariables } from "@saleor/products/utils/handlers";
import { SearchProductTypes_search_edges_node } from "@saleor/searches/types/SearchProductTypes"; import { SearchProductTypes_search_edges_node } from "@saleor/searches/types/SearchProductTypes";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import { MutationFetchResult } from "react-apollo"; import { MutationFetchResult } from "react-apollo";
const getChannelsVariables = (productId: string, channels: ChannelData[]) => ({ const getChannelsVariables = (productId: string, channels: ChannelData[]) => ({
@ -108,7 +109,7 @@ export function createHandler(
category: formData.category, category: formData.category,
chargeTaxes: formData.chargeTaxes, chargeTaxes: formData.chargeTaxes,
collections: formData.collections, collections: formData.collections,
description: JSON.stringify(formData.description), description: getParsedDataForJsonStringField(formData.description),
name: formData.name, name: formData.name,
productType: formData.productType?.id, productType: formData.productType?.id,
rating: formData.rating, rating: formData.rating,

View file

@ -56,6 +56,7 @@ import {
} from "@saleor/products/types/VariantCreate"; } from "@saleor/products/types/VariantCreate";
import { mapFormsetStockToStockInput } from "@saleor/products/utils/data"; import { mapFormsetStockToStockInput } from "@saleor/products/utils/data";
import { getAvailabilityVariables } from "@saleor/products/utils/handlers"; import { getAvailabilityVariables } from "@saleor/products/utils/handlers";
import { getParsedDataForJsonStringField } from "@saleor/translations/utils";
import { ReorderEvent } from "@saleor/types"; import { ReorderEvent } from "@saleor/types";
import { move } from "@saleor/utils/lists"; import { move } from "@saleor/utils/lists";
import { diff } from "fast-array-diff"; import { diff } from "fast-array-diff";
@ -185,7 +186,7 @@ export function createUpdateHandler(
category: data.category, category: data.category,
chargeTaxes: data.chargeTaxes, chargeTaxes: data.chargeTaxes,
collections: data.collections, collections: data.collections,
description: JSON.stringify(data.description), description: getParsedDataForJsonStringField(data.description),
name: data.name, name: data.name,
rating: data.rating, rating: data.rating,
seo: { seo: {

View file

@ -1,42 +0,0 @@
import DialogContentText from "@material-ui/core/DialogContentText";
import ActionDialog from "@saleor/components/ActionDialog";
import { ConfirmButtonTransitionState } from "@saleor/components/ConfirmButton";
import { DialogProps } from "@saleor/types";
import React from "react";
import { FormattedMessage, useIntl } from "react-intl";
export interface ShippingRateZipCodeRangeRemoveDialogProps extends DialogProps {
confirmButtonState: ConfirmButtonTransitionState;
onConfirm: () => void;
}
const ShippingRateZipCodeRangeRemoveDialog: React.FC<ShippingRateZipCodeRangeRemoveDialogProps> = ({
confirmButtonState,
open,
onClose,
onConfirm
}) => {
const intl = useIntl();
return (
<ActionDialog
confirmButtonState={confirmButtonState}
open={open}
onClose={onClose}
onConfirm={onConfirm}
title={intl.formatMessage({
defaultMessage: "Remove postal codes from Shipping Rate",
description: "header"
})}
variant="delete"
>
<DialogContentText>
<FormattedMessage defaultMessage="Are you sure you want to remove this postal code rule?" />
</DialogContentText>
</ActionDialog>
);
};
ShippingRateZipCodeRangeRemoveDialog.displayName =
"ShippingRateZipCodeRangeRemoveDialog";
export default ShippingRateZipCodeRangeRemoveDialog;

View file

@ -1,2 +0,0 @@
export * from "./ShippingRateZipCodeRangeRemoveDialog";
export { default } from "./ShippingRateZipCodeRangeRemoveDialog";

View file

@ -2,12 +2,12 @@ import Decorator from "@saleor/storybook/Decorator";
import { storiesOf } from "@storybook/react"; import { storiesOf } from "@storybook/react";
import React from "react"; import React from "react";
import ShippingZoneZipCodeRangeDialog from "./ShippingZoneZipCodeRangeDialog"; import ShippingZonePostalCodeRangeDialog from "./ShippingZonePostalCodeRangeDialog";
storiesOf("Shipping / Add postal code range", module) storiesOf("Shipping / Add postal code range", module)
.addDecorator(Decorator) .addDecorator(Decorator)
.add("default", () => ( .add("default", () => (
<ShippingZoneZipCodeRangeDialog <ShippingZonePostalCodeRangeDialog
confirmButtonState="default" confirmButtonState="default"
open={true} open={true}
onClose={() => undefined} onClose={() => undefined}

View file

@ -16,7 +16,7 @@ import { DialogProps, MinMax } from "@saleor/types";
import React from "react"; import React from "react";
import { FormattedMessage, useIntl } from "react-intl"; import { FormattedMessage, useIntl } from "react-intl";
export interface ShippingZoneZipCodeRangeDialogProps extends DialogProps { export interface ShippingZonePostalCodeRangeDialogProps extends DialogProps {
confirmButtonState: ConfirmButtonTransitionState; confirmButtonState: ConfirmButtonTransitionState;
onSubmit: (range: MinMax) => void; onSubmit: (range: MinMax) => void;
} }
@ -28,11 +28,11 @@ const useStyles = makeStyles(
} }
}), }),
{ {
name: "ShippingZoneZipCodeRangeDialog" name: "ShippingZonePostalCodeRangeDialog"
} }
); );
const ShippingZoneZipCodeRangeDialog: React.FC<ShippingZoneZipCodeRangeDialogProps> = ({ const ShippingZonePostalCodeRangeDialog: React.FC<ShippingZonePostalCodeRangeDialogProps> = ({
confirmButtonState, confirmButtonState,
open, open,
onClose, onClose,
@ -105,5 +105,6 @@ const ShippingZoneZipCodeRangeDialog: React.FC<ShippingZoneZipCodeRangeDialogPro
); );
}; };
ShippingZoneZipCodeRangeDialog.displayName = "ShippingZoneZipCodeRangeDialog"; ShippingZonePostalCodeRangeDialog.displayName =
export default ShippingZoneZipCodeRangeDialog; "ShippingZonePostalCodeRangeDialog";
export default ShippingZonePostalCodeRangeDialog;

View file

@ -0,0 +1,2 @@
export * from "./ShippingZonePostalCodeRangeDialog";
export { default } from "./ShippingZonePostalCodeRangeDialog";

View file

@ -13,27 +13,24 @@ import CardTitle from "@saleor/components/CardTitle";
import RadioGroupField from "@saleor/components/RadioGroupField"; import RadioGroupField from "@saleor/components/RadioGroupField";
import ResponsiveTable from "@saleor/components/ResponsiveTable"; import ResponsiveTable from "@saleor/components/ResponsiveTable";
import Skeleton from "@saleor/components/Skeleton"; import Skeleton from "@saleor/components/Skeleton";
import { ShippingMethodFragment_zipCodeRules } from "@saleor/fragments/types/ShippingMethodFragment"; import { ShippingMethodFragment_postalCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
import { FormChange } from "@saleor/hooks/useForm";
import ArrowDropdown from "@saleor/icons/ArrowDropdown"; import ArrowDropdown from "@saleor/icons/ArrowDropdown";
import { renderCollection } from "@saleor/misc"; import { renderCollection } from "@saleor/misc";
import { PostalCodeRuleInclusionTypeEnum } from "@saleor/types/globalTypes";
import classNames from "classnames"; import classNames from "classnames";
import React from "react"; import React from "react";
import { FormattedMessage, useIntl } from "react-intl"; import { FormattedMessage, useIntl } from "react-intl";
export enum ZipCodeInclusion { export interface ShippingZonePostalCodesProps {
Include,
Exclude
}
export interface ShippingZoneZipCodesProps {
data: Record<"includeZipCodes", ZipCodeInclusion>;
disabled: boolean; disabled: boolean;
initialExpanded?: boolean; initialExpanded?: boolean;
zipCodes: ShippingMethodFragment_zipCodeRules[] | undefined; initialInclusionType?: PostalCodeRuleInclusionTypeEnum;
onZipCodeInclusionChange: FormChange; postalCodes: ShippingMethodFragment_postalCodeRules[] | undefined;
onZipCodeDelete: (id: string) => void; onPostalCodeInclusionChange: (
onZipCodeRangeAdd: () => void; inclusion: PostalCodeRuleInclusionTypeEnum
) => void;
onPostalCodeDelete: (code: ShippingMethodFragment_postalCodeRules) => void;
onPostalCodeRangeAdd: () => void;
} }
const useStyles = makeStyles( const useStyles = makeStyles(
@ -60,23 +57,45 @@ const useStyles = makeStyles(
} }
}), }),
{ {
name: "ShippingZoneZipCodes" name: "ShippingZonePostalCodes"
} }
); );
const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({ const ShippingZonePostalCodes: React.FC<ShippingZonePostalCodesProps> = ({
data,
disabled, disabled,
initialExpanded, initialExpanded = true,
zipCodes, initialInclusionType = PostalCodeRuleInclusionTypeEnum.EXCLUDE,
onZipCodeDelete, postalCodes,
onZipCodeInclusionChange, onPostalCodeDelete,
onZipCodeRangeAdd onPostalCodeInclusionChange,
onPostalCodeRangeAdd
}) => { }) => {
const [expanded, setExpanded] = React.useState(initialExpanded); const [expanded, setExpanded] = React.useState(initialExpanded);
const [inclusionType, setInclusionType] = React.useState(null);
const intl = useIntl(); const intl = useIntl();
const classes = useStyles({}); const classes = useStyles({});
const onInclusionRadioChange = (event: React.ChangeEvent<any>) => {
const value = event.target.value;
setInclusionType(value);
onPostalCodeInclusionChange(value);
};
const getPostalCodeRangeLabel = (
postalCodeRange: ShippingMethodFragment_postalCodeRules
) => {
if (!postalCodeRange?.start) {
return <Skeleton />;
}
if (postalCodeRange?.end) {
return `${postalCodeRange.start} - ${postalCodeRange.end}`;
}
return postalCodeRange.start;
};
const getInlcusionType = () =>
inclusionType === null ? initialInclusionType : inclusionType;
return ( return (
<Card> <Card>
<CardTitle <CardTitle
@ -87,8 +106,8 @@ const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({
toolbar={ toolbar={
<Button <Button
color="primary" color="primary"
onClick={onZipCodeRangeAdd} onClick={onPostalCodeRangeAdd}
data-test="add-zip-code-range" data-test="add-postal-code-range"
> >
<FormattedMessage <FormattedMessage
defaultMessage="Add postal code range" defaultMessage="Add postal code range"
@ -115,13 +134,12 @@ const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({
</Typography> </Typography>
</div> </div>
), ),
value: ZipCodeInclusion.Exclude value: PostalCodeRuleInclusionTypeEnum.EXCLUDE
}, },
{ {
disabled: true,
label: ( label: (
<div className={classes.option}> <div className={classes.option}>
<Typography color="textSecondary" variant="body1"> <Typography variant="body1">
<FormattedMessage <FormattedMessage
defaultMessage="Include postal codes" defaultMessage="Include postal codes"
description="action" description="action"
@ -132,12 +150,12 @@ const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({
</Typography> </Typography>
</div> </div>
), ),
value: ZipCodeInclusion.Include value: PostalCodeRuleInclusionTypeEnum.INCLUDE
} }
]} ]}
name="includeZipCodes" name="includePostalCodes"
value={data.includeZipCodes} value={getInlcusionType()}
onChange={onZipCodeInclusionChange} onChange={onInclusionRadioChange}
/> />
</CardContent> </CardContent>
<ResponsiveTable> <ResponsiveTable>
@ -145,61 +163,50 @@ const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({
<col /> <col />
<col className={classes.colAction} /> <col className={classes.colAction} />
</colgroup> </colgroup>
{zipCodes === undefined || <TableHead>
(zipCodes.length > 0 && ( <TableRow>
<TableHead> <TableCell>
<TableRow> {postalCodes === undefined ? (
<TableCell> <Skeleton className={classes.skeleton} />
{zipCodes === undefined ? ( ) : (
<Skeleton className={classes.skeleton} /> <Typography variant="caption">
) : ( <FormattedMessage
<Typography variant="caption"> defaultMessage="{number} postal code ranges"
<FormattedMessage description="number of postal code ranges"
defaultMessage="{number} postal code ranges" values={{
description="number of postal code ranges" number: postalCodes.length
values={{ }}
number: zipCodes.length />
}} </Typography>
/> )}
</Typography> </TableCell>
)} <TableCell>
</TableCell> <IconButton onClick={() => setExpanded(!expanded)}>
<TableCell> <ArrowDropdown
<IconButton onClick={() => setExpanded(!expanded)}> className={classNames(classes.arrow, {
<ArrowDropdown [classes.arrowRotate]: expanded
className={classNames(classes.arrow, { })}
[classes.arrowRotate]: expanded />
})} </IconButton>
/> </TableCell>
</IconButton> </TableRow>
</TableCell> </TableHead>
</TableRow>
</TableHead>
))}
{expanded && ( {expanded && (
<TableBody> <TableBody>
{renderCollection( {renderCollection(
zipCodes, postalCodes,
zipCodeRange => ( postalCodeRange => (
<TableRow key={zipCodeRange?.id}> <TableRow key={postalCodeRange?.id}>
<TableCell> <TableCell>
{zipCodeRange?.start ? ( {getPostalCodeRangeLabel(postalCodeRange)}
zipCodeRange?.end ? (
`${zipCodeRange.start} - ${zipCodeRange.end}`
) : (
zipCodeRange.start
)
) : (
<Skeleton />
)}
</TableCell> </TableCell>
<TableCell> <TableCell>
<IconButton <IconButton
disabled={disabled} disabled={disabled}
color="primary" color="primary"
onClick={() => onZipCodeDelete(zipCodeRange.id)} onClick={() => onPostalCodeDelete(postalCodeRange)}
data-test="delete-zip-code" data-test="delete-postal-code"
data-test-id={zipCodeRange?.id} data-test-id={postalCodeRange?.id}
> >
<DeleteIcon /> <DeleteIcon />
</IconButton> </IconButton>
@ -223,8 +230,5 @@ const ShippingZoneZipCodes: React.FC<ShippingZoneZipCodesProps> = ({
); );
}; };
ShippingZoneZipCodes.displayName = "ShippingZoneZipCodes"; ShippingZonePostalCodes.displayName = "ShippingZonePostalCodes";
ShippingZoneZipCodes.defaultProps = { export default ShippingZonePostalCodes;
initialExpanded: true
};
export default ShippingZoneZipCodes;

View file

@ -0,0 +1,2 @@
export * from "./ShippingZonePostalCodes";
export { default } from "./ShippingZonePostalCodes";

View file

@ -1,5 +1,8 @@
import Decorator from "@saleor/storybook//Decorator"; import Decorator from "@saleor/storybook//Decorator";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import { storiesOf } from "@storybook/react"; import { storiesOf } from "@storybook/react";
import React from "react"; import React from "react";
@ -45,27 +48,30 @@ const props: ShippingZoneRatesCreatePageProps = {
onBack: () => undefined, onBack: () => undefined,
onChannelsChange: () => undefined, onChannelsChange: () => undefined,
onDelete: () => undefined, onDelete: () => undefined,
onPostalCodeAssign: () => undefined,
onPostalCodeInclusionChange: () => undefined,
onPostalCodeUnassign: () => undefined,
onSubmit: () => undefined, onSubmit: () => undefined,
onZipCodeAssign: () => undefined,
onZipCodeUnassign: () => undefined,
openChannelsModal: () => undefined, openChannelsModal: () => undefined,
saveButtonBarState: "default", postalCodes: [
shippingChannels: defaultChannels,
variant: ShippingMethodTypeEnum.PRICE,
zipCodes: [
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-200", end: "51-200",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-220" start: "51-220"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "31-101", end: "31-101",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "44-205" start: "44-205"
} }
] ],
saveButtonBarState: "default",
shippingChannels: defaultChannels,
variant: ShippingMethodTypeEnum.PRICE
}; };
storiesOf("Shipping / ShippingZoneRatesCreatePage page", module) storiesOf("Shipping / ShippingZoneRatesCreatePage page", module)

View file

@ -10,24 +10,24 @@ import PageHeader from "@saleor/components/PageHeader";
import SaveButtonBar from "@saleor/components/SaveButtonBar"; import SaveButtonBar from "@saleor/components/SaveButtonBar";
import { ShippingChannelsErrorFragment } from "@saleor/fragments/types/ShippingChannelsErrorFragment"; import { ShippingChannelsErrorFragment } from "@saleor/fragments/types/ShippingChannelsErrorFragment";
import { ShippingErrorFragment } from "@saleor/fragments/types/ShippingErrorFragment"; import { ShippingErrorFragment } from "@saleor/fragments/types/ShippingErrorFragment";
import { ShippingMethodFragment_zipCodeRules } from "@saleor/fragments/types/ShippingMethodFragment"; import { ShippingMethodFragment_postalCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
import { validatePrice } from "@saleor/products/utils/validation"; import { validatePrice } from "@saleor/products/utils/validation";
import OrderValue from "@saleor/shipping/components/OrderValue"; import OrderValue from "@saleor/shipping/components/OrderValue";
import OrderWeight from "@saleor/shipping/components/OrderWeight"; import OrderWeight from "@saleor/shipping/components/OrderWeight";
import PricingCard from "@saleor/shipping/components/PricingCard"; import PricingCard from "@saleor/shipping/components/PricingCard";
import ShippingRateInfo from "@saleor/shipping/components/ShippingRateInfo"; import ShippingRateInfo from "@saleor/shipping/components/ShippingRateInfo";
import { createChannelsChangeHandler } from "@saleor/shipping/handlers"; import { createChannelsChangeHandler } from "@saleor/shipping/handlers";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import React from "react"; import React from "react";
import { FormattedMessage, useIntl } from "react-intl"; import { FormattedMessage, useIntl } from "react-intl";
import ShippingZoneZipCodes, { import ShippingZonePostalCodes from "../ShippingZonePostalCodes";
ZipCodeInclusion
} from "../ShippingZoneZipCodes";
export interface FormData { export interface FormData {
channelListings: ChannelShippingData[]; channelListings: ChannelShippingData[];
includeZipCodes: ZipCodeInclusion;
name: string; name: string;
noLimits: boolean; noLimits: boolean;
minValue: string; minValue: string;
@ -42,15 +42,18 @@ export interface ShippingZoneRatesCreatePageProps {
shippingChannels: ChannelShippingData[]; shippingChannels: ChannelShippingData[];
disabled: boolean; disabled: boolean;
hasChannelChanged?: boolean; hasChannelChanged?: boolean;
zipCodes?: ShippingMethodFragment_zipCodeRules[]; postalCodes?: ShippingMethodFragment_postalCodeRules[];
channelErrors: ShippingChannelsErrorFragment[]; channelErrors: ShippingChannelsErrorFragment[];
errors: ShippingErrorFragment[]; errors: ShippingErrorFragment[];
saveButtonBarState: ConfirmButtonTransitionState; saveButtonBarState: ConfirmButtonTransitionState;
onBack: () => void; onBack: () => void;
onDelete?: () => void; onDelete?: () => void;
onSubmit: (data: FormData) => void; onSubmit: (data: FormData) => void;
onZipCodeAssign: () => void; onPostalCodeInclusionChange: (
onZipCodeUnassign: (id: string) => void; inclusion: PostalCodeRuleInclusionTypeEnum
) => void;
onPostalCodeAssign: () => void;
onPostalCodeUnassign: (code: any) => void;
onChannelsChange: (data: ChannelShippingData[]) => void; onChannelsChange: (data: ChannelShippingData[]) => void;
openChannelsModal: () => void; openChannelsModal: () => void;
variant: ShippingMethodTypeEnum; variant: ShippingMethodTypeEnum;
@ -66,19 +69,19 @@ export const ShippingZoneRatesCreatePage: React.FC<ShippingZoneRatesCreatePagePr
onBack, onBack,
onDelete, onDelete,
onSubmit, onSubmit,
onPostalCodeInclusionChange,
onChannelsChange, onChannelsChange,
onZipCodeAssign, onPostalCodeAssign,
onZipCodeUnassign, onPostalCodeUnassign,
openChannelsModal, openChannelsModal,
saveButtonBarState, saveButtonBarState,
variant, variant,
zipCodes postalCodes
}) => { }) => {
const intl = useIntl(); const intl = useIntl();
const isPriceVariant = variant === ShippingMethodTypeEnum.PRICE; const isPriceVariant = variant === ShippingMethodTypeEnum.PRICE;
const initialForm: FormData = { const initialForm: FormData = {
channelListings: shippingChannels, channelListings: shippingChannels,
includeZipCodes: ZipCodeInclusion.Include,
maxDays: "", maxDays: "",
maxValue: "", maxValue: "",
minDays: "", minDays: "",
@ -88,6 +91,12 @@ export const ShippingZoneRatesCreatePage: React.FC<ShippingZoneRatesCreatePagePr
type: null type: null
}; };
const postalCodeInclusionChange = (
inclusion: PostalCodeRuleInclusionTypeEnum
) => {
onPostalCodeInclusionChange(inclusion);
};
return ( return (
<Form initial={initialForm} onSubmit={onSubmit}> <Form initial={initialForm} onSubmit={onSubmit}>
{({ change, data, hasChanged, submit, triggerChange }) => { {({ change, data, hasChanged, submit, triggerChange }) => {
@ -154,13 +163,12 @@ export const ShippingZoneRatesCreatePage: React.FC<ShippingZoneRatesCreatePagePr
errors={channelErrors} errors={channelErrors}
/> />
<CardSpacer /> <CardSpacer />
<ShippingZoneZipCodes <ShippingZonePostalCodes
data={data}
disabled={disabled} disabled={disabled}
onZipCodeDelete={onZipCodeUnassign} onPostalCodeDelete={onPostalCodeUnassign}
onZipCodeInclusionChange={() => undefined} onPostalCodeInclusionChange={postalCodeInclusionChange}
onZipCodeRangeAdd={onZipCodeAssign} onPostalCodeRangeAdd={onPostalCodeAssign}
zipCodes={zipCodes} postalCodes={postalCodes}
/> />
</div> </div>
<div> <div>

View file

@ -48,12 +48,13 @@ const props: ShippingZoneRatesPageProps = {
onChannelsChange: () => undefined, onChannelsChange: () => undefined,
onDelete: () => undefined, onDelete: () => undefined,
onNextPage: () => undefined, onNextPage: () => undefined,
onPostalCodeAssign: () => undefined,
onPostalCodeInclusionChange: () => undefined,
onPostalCodeUnassign: () => undefined,
onPreviousPage: () => undefined, onPreviousPage: () => undefined,
onProductAssign: () => undefined, onProductAssign: () => undefined,
onProductUnassign: () => undefined, onProductUnassign: () => undefined,
onSubmit: () => undefined, onSubmit: () => undefined,
onZipCodeAssign: () => undefined,
onZipCodeUnassign: () => undefined,
openChannelsModal: () => undefined, openChannelsModal: () => undefined,
rate: shippingZone.shippingMethods[0], rate: shippingZone.shippingMethods[0],
saveButtonBarState: "default", saveButtonBarState: "default",

View file

@ -12,6 +12,7 @@ import PageHeader from "@saleor/components/PageHeader";
import SaveButtonBar from "@saleor/components/SaveButtonBar"; import SaveButtonBar from "@saleor/components/SaveButtonBar";
import { ShippingChannelsErrorFragment } from "@saleor/fragments/types/ShippingChannelsErrorFragment"; import { ShippingChannelsErrorFragment } from "@saleor/fragments/types/ShippingChannelsErrorFragment";
import { ShippingErrorFragment } from "@saleor/fragments/types/ShippingErrorFragment"; import { ShippingErrorFragment } from "@saleor/fragments/types/ShippingErrorFragment";
import { ShippingMethodFragment_postalCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
import { validatePrice } from "@saleor/products/utils/validation"; import { validatePrice } from "@saleor/products/utils/validation";
import OrderValue from "@saleor/shipping/components/OrderValue"; import OrderValue from "@saleor/shipping/components/OrderValue";
import OrderWeight from "@saleor/shipping/components/OrderWeight"; import OrderWeight from "@saleor/shipping/components/OrderWeight";
@ -21,19 +22,19 @@ import ShippingRateInfo from "@saleor/shipping/components/ShippingRateInfo";
import { createChannelsChangeHandler } from "@saleor/shipping/handlers"; import { createChannelsChangeHandler } from "@saleor/shipping/handlers";
import { ShippingZone_shippingZone_shippingMethods } from "@saleor/shipping/types/ShippingZone"; import { ShippingZone_shippingZone_shippingMethods } from "@saleor/shipping/types/ShippingZone";
import { ListActions, ListProps } from "@saleor/types"; import { ListActions, ListProps } from "@saleor/types";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import { mapMetadataItemToInput } from "@saleor/utils/maps"; import { mapMetadataItemToInput } from "@saleor/utils/maps";
import useMetadataChangeTrigger from "@saleor/utils/metadata/useMetadataChangeTrigger"; import useMetadataChangeTrigger from "@saleor/utils/metadata/useMetadataChangeTrigger";
import React from "react"; import React from "react";
import { FormattedMessage } from "react-intl"; import { FormattedMessage } from "react-intl";
import ShippingZoneZipCodes, { import ShippingZonePostalCodes from "../ShippingZonePostalCodes";
ZipCodeInclusion
} from "../ShippingZoneZipCodes";
export interface FormData extends MetadataFormData { export interface FormData extends MetadataFormData {
channelListings: ChannelShippingData[]; channelListings: ChannelShippingData[];
includeZipCodes: ZipCodeInclusion;
name: string; name: string;
noLimits: boolean; noLimits: boolean;
minValue: string; minValue: string;
@ -50,6 +51,7 @@ export interface ShippingZoneRatesPageProps
shippingChannels: ChannelShippingData[]; shippingChannels: ChannelShippingData[];
disabled: boolean; disabled: boolean;
hasChannelChanged?: boolean; hasChannelChanged?: boolean;
havePostalCodesChanged?: boolean;
rate: ShippingZone_shippingZone_shippingMethods; rate: ShippingZone_shippingZone_shippingMethods;
channelErrors: ShippingChannelsErrorFragment[]; channelErrors: ShippingChannelsErrorFragment[];
errors: ShippingErrorFragment[]; errors: ShippingErrorFragment[];
@ -57,8 +59,11 @@ export interface ShippingZoneRatesPageProps
onBack: () => void; onBack: () => void;
onDelete?: () => void; onDelete?: () => void;
onSubmit: (data: FormData) => void; onSubmit: (data: FormData) => void;
onZipCodeAssign: () => void; onPostalCodeInclusionChange: (
onZipCodeUnassign: (id: string) => void; inclusion: PostalCodeRuleInclusionTypeEnum
) => void;
onPostalCodeAssign: () => void;
onPostalCodeUnassign: (code: ShippingMethodFragment_postalCodeRules) => void;
onChannelsChange: (data: ChannelShippingData[]) => void; onChannelsChange: (data: ChannelShippingData[]) => void;
openChannelsModal: () => void; openChannelsModal: () => void;
onProductAssign: () => void; onProductAssign: () => void;
@ -73,12 +78,14 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
disabled, disabled,
errors, errors,
hasChannelChanged, hasChannelChanged,
havePostalCodesChanged,
onBack, onBack,
onDelete, onDelete,
onSubmit, onSubmit,
onPostalCodeInclusionChange,
onChannelsChange, onChannelsChange,
onZipCodeAssign, onPostalCodeAssign,
onZipCodeUnassign, onPostalCodeUnassign,
onProductAssign, onProductAssign,
onProductUnassign, onProductUnassign,
openChannelsModal, openChannelsModal,
@ -90,7 +97,6 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
const isPriceVariant = variant === ShippingMethodTypeEnum.PRICE; const isPriceVariant = variant === ShippingMethodTypeEnum.PRICE;
const initialForm: FormData = { const initialForm: FormData = {
channelListings: shippingChannels, channelListings: shippingChannels,
includeZipCodes: ZipCodeInclusion.Exclude,
maxDays: rate?.maximumDeliveryDays?.toString() || "", maxDays: rate?.maximumDeliveryDays?.toString() || "",
maxValue: rate?.maximumOrderWeight?.value.toString() || "", maxValue: rate?.maximumOrderWeight?.value.toString() || "",
metadata: rate?.metadata.map(mapMetadataItemToInput), metadata: rate?.metadata.map(mapMetadataItemToInput),
@ -102,6 +108,14 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
type: rate?.type || null type: rate?.type || null
}; };
const postalCodesInclusionType = rate?.postalCodeRules[0]?.inclusionType;
const postalCodeInclusionChange = (
inclusion: PostalCodeRuleInclusionTypeEnum
) => {
onPostalCodeInclusionChange(inclusion);
};
const { const {
makeChangeHandler: makeMetadataChangeHandler makeChangeHandler: makeMetadataChangeHandler
} = useMetadataChangeTrigger(); } = useMetadataChangeTrigger();
@ -119,6 +133,8 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
); );
const changeMetadata = makeMetadataChangeHandler(change); const changeMetadata = makeMetadataChangeHandler(change);
const formIsUnchanged =
!hasChanged && !hasChannelChanged && !havePostalCodesChanged;
return ( return (
<Container> <Container>
@ -162,13 +178,13 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
errors={channelErrors} errors={channelErrors}
/> />
<CardSpacer /> <CardSpacer />
<ShippingZoneZipCodes <ShippingZonePostalCodes
data={data}
disabled={disabled} disabled={disabled}
onZipCodeDelete={onZipCodeUnassign} onPostalCodeDelete={onPostalCodeUnassign}
onZipCodeInclusionChange={() => undefined} onPostalCodeInclusionChange={postalCodeInclusionChange}
onZipCodeRangeAdd={onZipCodeAssign} onPostalCodeRangeAdd={onPostalCodeAssign}
zipCodes={rate?.zipCodeRules} postalCodes={rate?.postalCodeRules}
initialInclusionType={postalCodesInclusionType}
/> />
<CardSpacer /> <CardSpacer />
<ShippingMethodProducts <ShippingMethodProducts
@ -196,9 +212,7 @@ export const ShippingZoneRatesPage: React.FC<ShippingZoneRatesPageProps> = ({
</div> </div>
</Grid> </Grid>
<SaveButtonBar <SaveButtonBar
disabled={ disabled={disabled || formDisabled || formIsUnchanged}
disabled || formDisabled || (!hasChanged && !hasChannelChanged)
}
onCancel={onBack} onCancel={onBack}
onDelete={onDelete} onDelete={onDelete}
onSave={submit} onSave={submit}

View file

@ -1,2 +0,0 @@
export * from "./ShippingZoneZipCodeRangeDialog";
export { default } from "./ShippingZoneZipCodeRangeDialog";

View file

@ -1,2 +0,0 @@
export * from "./ShippingZoneZipCodes";
export { default } from "./ShippingZoneZipCodes";

View file

@ -2,7 +2,11 @@ import { ShippingZoneFragment } from "@saleor/fragments/types/ShippingZoneFragme
import { SearchProducts_search_edges_node } from "@saleor/searches/types/SearchProducts"; import { SearchProducts_search_edges_node } from "@saleor/searches/types/SearchProducts";
import { ShippingZone_shippingZone } from "@saleor/shipping/types/ShippingZone"; import { ShippingZone_shippingZone } from "@saleor/shipping/types/ShippingZone";
import { ShippingMethodTypeEnum, WeightUnitsEnum } from "../types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum,
WeightUnitsEnum
} from "../types/globalTypes";
export const shippingZones: ShippingZoneFragment[] = [ export const shippingZones: ShippingZoneFragment[] = [
{ {
@ -1632,28 +1636,31 @@ export const shippingZone: ShippingZone_shippingZone = {
value: 0 value: 0
}, },
name: "DB Schenker", name: "DB Schenker",
privateMetadata: [], postalCodeRules: [
type: ShippingMethodTypeEnum.WEIGHT,
zipCodeRules: [
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-220", end: "51-220",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-210" start: "51-210"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-240", end: "51-240",
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-235" start: "51-235"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: null, end: null,
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-274" start: "51-274"
} }
] ],
privateMetadata: [],
type: ShippingMethodTypeEnum.WEIGHT
}, },
{ {
__typename: "ShippingMethod", __typename: "ShippingMethod",
@ -1693,28 +1700,31 @@ export const shippingZone: ShippingZone_shippingZone = {
value: 0 value: 0
}, },
name: "Registred priority", name: "Registred priority",
privateMetadata: [], postalCodeRules: [
type: ShippingMethodTypeEnum.WEIGHT,
zipCodeRules: [
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-220", end: "51-220",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-210" start: "51-210"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-240", end: "51-240",
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-235" start: "51-235"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: null, end: null,
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-274" start: "51-274"
} }
] ],
privateMetadata: [],
type: ShippingMethodTypeEnum.WEIGHT
}, },
{ {
__typename: "ShippingMethod", __typename: "ShippingMethod",
@ -1754,28 +1764,31 @@ export const shippingZone: ShippingZone_shippingZone = {
value: 0 value: 0
}, },
name: "UPS", name: "UPS",
privateMetadata: [], postalCodeRules: [
type: ShippingMethodTypeEnum.PRICE,
zipCodeRules: [
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-220", end: "51-220",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-210" start: "51-210"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-240", end: "51-240",
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-235" start: "51-235"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: null, end: null,
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-274" start: "51-274"
} }
] ],
privateMetadata: [],
type: ShippingMethodTypeEnum.PRICE
}, },
{ {
__typename: "ShippingMethod", __typename: "ShippingMethod",
@ -1802,28 +1815,31 @@ export const shippingZone: ShippingZone_shippingZone = {
value: 0 value: 0
}, },
name: "DHL", name: "DHL",
privateMetadata: [], postalCodeRules: [
type: ShippingMethodTypeEnum.PRICE,
zipCodeRules: [
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-220", end: "51-220",
id: "1", id: "1",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-210" start: "51-210"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: "51-240", end: "51-240",
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-235" start: "51-235"
}, },
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: null, end: null,
id: "2", id: "2",
inclusionType: PostalCodeRuleInclusionTypeEnum.EXCLUDE,
start: "51-274" start: "51-274"
} }
] ],
privateMetadata: [],
type: ShippingMethodTypeEnum.PRICE
} }
], ],
warehouses: [ warehouses: [

View file

@ -1,5 +1,5 @@
import { ChannelShippingData } from "@saleor/channels/utils"; import { ChannelShippingData } from "@saleor/channels/utils";
import { ShippingMethodFragment_zipCodeRules } from "@saleor/fragments/types/ShippingMethodFragment"; import { ShippingMethodFragment_postalCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
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 { commonMessages } from "@saleor/intl"; import { commonMessages } from "@saleor/intl";
@ -8,13 +8,16 @@ import { FormData as ShippingZoneRatesPageFormData } from "@saleor/shipping/comp
import { CreateShippingRateVariables } from "@saleor/shipping/types/CreateShippingRate"; import { CreateShippingRateVariables } from "@saleor/shipping/types/CreateShippingRate";
import { ShippingMethodChannelListingUpdateVariables } from "@saleor/shipping/types/ShippingMethodChannelListingUpdate"; import { ShippingMethodChannelListingUpdateVariables } from "@saleor/shipping/types/ShippingMethodChannelListingUpdate";
import { UpdateShippingRateVariables } from "@saleor/shipping/types/UpdateShippingRate"; import { UpdateShippingRateVariables } from "@saleor/shipping/types/UpdateShippingRate";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum,
ShippingPostalCodeRulesCreateInputRange
} from "@saleor/types/globalTypes";
import { diff } from "fast-array-diff"; import { diff } from "fast-array-diff";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
import { import {
useShippingMethodChannelListingUpdate, useShippingMethodChannelListingUpdate,
useShippingMethodZipCodeRangeAssign,
useShippingRateCreate, useShippingRateCreate,
useShippingRateDelete useShippingRateDelete
} from "./mutations"; } from "./mutations";
@ -43,14 +46,32 @@ export const createChannelsChangeHandler = (
triggerChange(); triggerChange();
}; };
const getPostalCodeRulesToAdd = (
rules: ShippingMethodFragment_postalCodeRules[]
) =>
rules
.filter(code => !code.id || code.id === "0")
.map(
code =>
({
end: code.end,
start: code.start
} as ShippingPostalCodeRulesCreateInputRange)
);
export function getCreateShippingPriceRateVariables( export function getCreateShippingPriceRateVariables(
data: ShippingZoneRatesPageFormData, data: ShippingZoneRatesPageFormData,
id: string id: string,
addPostalCodeRules: ShippingMethodFragment_postalCodeRules[],
inclusionType: PostalCodeRuleInclusionTypeEnum
): CreateShippingRateVariables { ): CreateShippingRateVariables {
const parsedMinDays = parseInt(data.minDays, 10); const parsedMinDays = parseInt(data.minDays, 10);
const parsedMaxDays = parseInt(data.maxDays, 10); const parsedMaxDays = parseInt(data.maxDays, 10);
const postalCodeRules = getPostalCodeRulesToAdd(addPostalCodeRules);
return { return {
input: { input: {
addPostalCodeRules: postalCodeRules,
inclusionType,
maximumDeliveryDays: parsedMaxDays, maximumDeliveryDays: parsedMaxDays,
minimumDeliveryDays: parsedMinDays, minimumDeliveryDays: parsedMinDays,
name: data.name, name: data.name,
@ -62,15 +83,20 @@ export function getCreateShippingPriceRateVariables(
export function getCreateShippingWeightRateVariables( export function getCreateShippingWeightRateVariables(
data: ShippingZoneRatesPageFormData, data: ShippingZoneRatesPageFormData,
id: string id: string,
addPostalCodeRules: ShippingMethodFragment_postalCodeRules[],
inclusionType: PostalCodeRuleInclusionTypeEnum
): CreateShippingRateVariables { ): CreateShippingRateVariables {
const parsedMinValue = parseFloat(data.minValue); const parsedMinValue = parseFloat(data.minValue);
const parsedMaxValue = parseFloat(data.maxValue); const parsedMaxValue = parseFloat(data.maxValue);
const parsedMinDays = parseInt(data.minDays, 10); const parsedMinDays = parseInt(data.minDays, 10);
const parsedMaxDays = parseInt(data.maxDays, 10); const parsedMaxDays = parseInt(data.maxDays, 10);
const isWeightSet = !data.noLimits; const isWeightSet = !data.noLimits;
const postalCodeRules = getPostalCodeRulesToAdd(addPostalCodeRules);
return { return {
input: { input: {
addPostalCodeRules: postalCodeRules,
inclusionType,
maximumDeliveryDays: parsedMaxDays, maximumDeliveryDays: parsedMaxDays,
maximumOrderWeight: isWeightSet ? parsedMaxValue : null, maximumOrderWeight: isWeightSet ? parsedMaxValue : null,
minimumDeliveryDays: parsedMinDays, minimumDeliveryDays: parsedMinDays,
@ -85,13 +111,21 @@ export function getCreateShippingWeightRateVariables(
export function getUpdateShippingPriceRateVariables( export function getUpdateShippingPriceRateVariables(
data: ShippingZoneRatesPageFormData, data: ShippingZoneRatesPageFormData,
id: string, id: string,
rateId: string rateId: string,
addPostalCodeRules: ShippingMethodFragment_postalCodeRules[],
deletePostalCodeRules: string[]
): UpdateShippingRateVariables { ): UpdateShippingRateVariables {
const parsedMinDays = parseInt(data.minDays, 10); const parsedMinDays = parseInt(data.minDays, 10);
const parsedMaxDays = parseInt(data.maxDays, 10); const parsedMaxDays = parseInt(data.maxDays, 10);
const postalCodeRules = getPostalCodeRulesToAdd(addPostalCodeRules);
return { return {
id: rateId, id: rateId,
input: { input: {
addPostalCodeRules: postalCodeRules,
deletePostalCodeRules,
inclusionType:
addPostalCodeRules[0]?.inclusionType ||
PostalCodeRuleInclusionTypeEnum.EXCLUDE,
maximumDeliveryDays: parsedMaxDays, maximumDeliveryDays: parsedMaxDays,
minimumDeliveryDays: parsedMinDays, minimumDeliveryDays: parsedMinDays,
name: data.name, name: data.name,
@ -104,16 +138,24 @@ export function getUpdateShippingPriceRateVariables(
export function getUpdateShippingWeightRateVariables( export function getUpdateShippingWeightRateVariables(
data: ShippingZoneRatesPageFormData, data: ShippingZoneRatesPageFormData,
id: string, id: string,
rateId: string rateId: string,
addPostalCodeRules: ShippingMethodFragment_postalCodeRules[],
deletePostalCodeRules: string[]
): UpdateShippingRateVariables { ): UpdateShippingRateVariables {
const parsedMinValue = parseFloat(data.minValue); const parsedMinValue = parseFloat(data.minValue);
const parsedMaxValue = parseFloat(data.maxValue); const parsedMaxValue = parseFloat(data.maxValue);
const parsedMinDays = parseInt(data.minDays, 10); const parsedMinDays = parseInt(data.minDays, 10);
const parsedMaxDays = parseInt(data.maxDays, 10); const parsedMaxDays = parseInt(data.maxDays, 10);
const isWeightSet = !data.noLimits; const isWeightSet = !data.noLimits;
const postalCodeRules = getPostalCodeRulesToAdd(addPostalCodeRules);
return { return {
id: rateId, id: rateId,
input: { input: {
addPostalCodeRules: postalCodeRules,
deletePostalCodeRules,
inclusionType:
addPostalCodeRules[0]?.inclusionType ||
PostalCodeRuleInclusionTypeEnum.EXCLUDE,
maximumDeliveryDays: parsedMaxDays, maximumDeliveryDays: parsedMaxDays,
maximumOrderWeight: isWeightSet ? parsedMaxValue : null, maximumOrderWeight: isWeightSet ? parsedMaxValue : null,
minimumDeliveryDays: parsedMinDays, minimumDeliveryDays: parsedMinDays,
@ -156,7 +198,8 @@ export function getShippingMethodChannelVariables(
export function useShippingRateCreator( export function useShippingRateCreator(
shippingZoneId: string, shippingZoneId: string,
type: ShippingMethodTypeEnum, type: ShippingMethodTypeEnum,
zipCodes: ShippingMethodFragment_zipCodeRules[] postalCodes: ShippingMethodFragment_postalCodeRules[],
inclusionType: PostalCodeRuleInclusionTypeEnum
) { ) {
const intl = useIntl(); const intl = useIntl();
const notify = useNotifier(); const notify = useNotifier();
@ -165,10 +208,6 @@ export function useShippingRateCreator(
createBaseShippingRate, createBaseShippingRate,
createBaseShippingRateOpts createBaseShippingRateOpts
] = useShippingRateCreate({}); ] = useShippingRateCreate({});
const [
assignZipCodeRules,
assignZipCodeRulesOpts
] = useShippingMethodZipCodeRangeAssign({});
const [ const [
updateShippingMethodChannelListing, updateShippingMethodChannelListing,
updateShippingMethodChannelListingOpts updateShippingMethodChannelListingOpts
@ -186,7 +225,7 @@ export function useShippingRateCreator(
const createShippingRate = async (data: ShippingZoneRatesPageFormData) => { const createShippingRate = async (data: ShippingZoneRatesPageFormData) => {
const response = await createBaseShippingRate({ const response = await createBaseShippingRate({
variables: getVariables(data, shippingZoneId) variables: getVariables(data, shippingZoneId, postalCodes, inclusionType)
}); });
const createErrors = response.data.shippingPriceCreate.errors; const createErrors = response.data.shippingPriceCreate.errors;
@ -200,17 +239,6 @@ export function useShippingRateCreator(
data.noLimits, data.noLimits,
data.channelListings data.channelListings
) )
}),
assignZipCodeRules({
variables: {
id: rateId,
input: {
zipCodeRules: zipCodes.map(zipCodeRule => ({
end: zipCodeRule.end || null,
start: zipCodeRule.start
}))
}
}
}) })
]); ]);
@ -236,16 +264,12 @@ export function useShippingRateCreator(
const called = const called =
createBaseShippingRateOpts.called || createBaseShippingRateOpts.called ||
updateShippingMethodChannelListingOpts.called || updateShippingMethodChannelListingOpts.called;
assignZipCodeRulesOpts.called;
const loading = const loading =
createBaseShippingRateOpts.loading || createBaseShippingRateOpts.loading ||
updateShippingMethodChannelListingOpts.loading || updateShippingMethodChannelListingOpts.loading;
assignZipCodeRulesOpts.loading;
const errors = [ const errors = [
...(createBaseShippingRateOpts.data?.shippingPriceCreate.errors || []), ...(createBaseShippingRateOpts.data?.shippingPriceCreate.errors || [])
...(assignZipCodeRulesOpts.data?.shippingMethodZipCodeRulesCreate.errors ||
[])
]; ];
const channelErrors = const channelErrors =
updateShippingMethodChannelListingOpts.data updateShippingMethodChannelListingOpts.data

View file

@ -4,7 +4,6 @@ import {
} from "@saleor/fragments/errors"; } from "@saleor/fragments/errors";
import { import {
shippingMethodFragment, shippingMethodFragment,
shippingMethodWithZipCodesFragment,
shippingZoneDetailsFragment shippingZoneDetailsFragment
} from "@saleor/fragments/shipping"; } from "@saleor/fragments/shipping";
import { countryFragment } from "@saleor/fragments/taxes"; import { countryFragment } from "@saleor/fragments/taxes";
@ -39,14 +38,6 @@ import {
ShippingMethodChannelListingUpdate, ShippingMethodChannelListingUpdate,
ShippingMethodChannelListingUpdateVariables ShippingMethodChannelListingUpdateVariables
} from "./types/ShippingMethodChannelListingUpdate"; } from "./types/ShippingMethodChannelListingUpdate";
import {
ShippingMethodZipCodeRangeAssign,
ShippingMethodZipCodeRangeAssignVariables
} from "./types/ShippingMethodZipCodeRangeAssign";
import {
ShippingMethodZipCodeRangeUnassign,
ShippingMethodZipCodeRangeUnassignVariables
} from "./types/ShippingMethodZipCodeRangeUnassign";
import { import {
ShippingPriceExcludeProduct, ShippingPriceExcludeProduct,
ShippingPriceExcludeProductVariables ShippingPriceExcludeProductVariables
@ -263,49 +254,6 @@ export const useShippingMethodChannelListingUpdate = makeMutation<
ShippingMethodChannelListingUpdateVariables ShippingMethodChannelListingUpdateVariables
>(shippingMethodChannelListingUpdate); >(shippingMethodChannelListingUpdate);
export const shippingMethodZipCodeRangeAssign = gql`
${shippingChannelsErrorFragment}
${shippingMethodWithZipCodesFragment}
mutation ShippingMethodZipCodeRangeAssign(
$id: ID!
$input: ShippingZipCodeRulesCreateInput!
) {
shippingMethodZipCodeRulesCreate(shippingMethodId: $id, input: $input) {
errors: shippingErrors {
...ShippingChannelsErrorFragment
}
shippingMethod {
...ShippingMethodWithZipCodesFragment
}
}
}
`;
export const useShippingMethodZipCodeRangeAssign = makeMutation<
ShippingMethodZipCodeRangeAssign,
ShippingMethodZipCodeRangeAssignVariables
>(shippingMethodZipCodeRangeAssign);
export const shippingMethodZipCodeRulesDelete = gql`
${shippingChannelsErrorFragment}
${shippingMethodWithZipCodesFragment}
mutation ShippingMethodZipCodeRangeUnassign($id: ID!) {
shippingMethodZipCodeRulesDelete(id: $id) {
errors: shippingErrors {
...ShippingChannelsErrorFragment
}
shippingMethod {
...ShippingMethodWithZipCodesFragment
}
}
}
`;
export const useShippingMethodZipCodeRangeUnassign = makeMutation<
ShippingMethodZipCodeRangeUnassign,
ShippingMethodZipCodeRangeUnassignVariables
>(shippingMethodZipCodeRulesDelete);
export const shippingPriceExcludeProducts = gql` export const shippingPriceExcludeProducts = gql`
${shippingErrorFragment} ${shippingErrorFragment}
mutation ShippingPriceExcludeProduct( mutation ShippingPriceExcludeProduct(

View file

@ -2,7 +2,7 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { ShippingPriceInput, ShippingErrorCode, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { ShippingPriceInput, ShippingErrorCode, PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL mutation operation: CreateShippingRate // GraphQL mutation operation: CreateShippingRate
@ -32,9 +32,10 @@ export interface CreateShippingRate_shippingPriceCreate_shippingZone_countries {
country: string; country: string;
} }
export interface CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_zipCodeRules { export interface CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -100,7 +101,7 @@ export interface CreateShippingRate_shippingPriceCreate_shippingZone_shippingMet
export interface CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods { export interface CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_zipCodeRules | null)[] | null; postalCodeRules: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_postalCodeRules | null)[] | null;
metadata: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_metadata | null)[]; metadata: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_metadata | null)[];
privateMetadata: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_privateMetadata | null)[]; privateMetadata: (CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_privateMetadata | null)[];
minimumOrderWeight: CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_minimumOrderWeight | null; minimumOrderWeight: CreateShippingRate_shippingPriceCreate_shippingZone_shippingMethods_minimumOrderWeight | null;
@ -131,9 +132,10 @@ export interface CreateShippingRate_shippingPriceCreate_shippingZone {
warehouses: (CreateShippingRate_shippingPriceCreate_shippingZone_warehouses | null)[] | null; warehouses: (CreateShippingRate_shippingPriceCreate_shippingZone_warehouses | null)[] | null;
} }
export interface CreateShippingRate_shippingPriceCreate_shippingMethod_zipCodeRules { export interface CreateShippingRate_shippingPriceCreate_shippingMethod_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -199,7 +201,7 @@ export interface CreateShippingRate_shippingPriceCreate_shippingMethod_channelLi
export interface CreateShippingRate_shippingPriceCreate_shippingMethod { export interface CreateShippingRate_shippingPriceCreate_shippingMethod {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (CreateShippingRate_shippingPriceCreate_shippingMethod_zipCodeRules | null)[] | null; postalCodeRules: (CreateShippingRate_shippingPriceCreate_shippingMethod_postalCodeRules | null)[] | null;
metadata: (CreateShippingRate_shippingPriceCreate_shippingMethod_metadata | null)[]; metadata: (CreateShippingRate_shippingPriceCreate_shippingMethod_metadata | null)[];
privateMetadata: (CreateShippingRate_shippingPriceCreate_shippingMethod_privateMetadata | null)[]; privateMetadata: (CreateShippingRate_shippingPriceCreate_shippingMethod_privateMetadata | null)[];
minimumOrderWeight: CreateShippingRate_shippingPriceCreate_shippingMethod_minimumOrderWeight | null; minimumOrderWeight: CreateShippingRate_shippingPriceCreate_shippingMethod_minimumOrderWeight | null;

View file

@ -2,7 +2,7 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { ShippingErrorCode, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { ShippingErrorCode, PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL mutation operation: DeleteShippingRate // GraphQL mutation operation: DeleteShippingRate
@ -32,9 +32,10 @@ export interface DeleteShippingRate_shippingPriceDelete_shippingZone_countries {
country: string; country: string;
} }
export interface DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_zipCodeRules { export interface DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -100,7 +101,7 @@ export interface DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMet
export interface DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods { export interface DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_zipCodeRules | null)[] | null; postalCodeRules: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_postalCodeRules | null)[] | null;
metadata: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_metadata | null)[]; metadata: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_metadata | null)[];
privateMetadata: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_privateMetadata | null)[]; privateMetadata: (DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_privateMetadata | null)[];
minimumOrderWeight: DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_minimumOrderWeight | null; minimumOrderWeight: DeleteShippingRate_shippingPriceDelete_shippingZone_shippingMethods_minimumOrderWeight | null;

View file

@ -2,15 +2,16 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { ShippingMethodChannelListingInput, WeightUnitsEnum, ShippingMethodTypeEnum, ShippingErrorCode } from "./../../types/globalTypes"; import { ShippingMethodChannelListingInput, PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum, ShippingErrorCode } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL mutation operation: ShippingMethodChannelListingUpdate // GraphQL mutation operation: ShippingMethodChannelListingUpdate
// ==================================================== // ====================================================
export interface ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_zipCodeRules { export interface ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -76,7 +77,7 @@ export interface ShippingMethodChannelListingUpdate_shippingMethodChannelListing
export interface ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod { export interface ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_zipCodeRules | null)[] | null; postalCodeRules: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_postalCodeRules | null)[] | null;
metadata: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_metadata | null)[]; metadata: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_metadata | null)[];
privateMetadata: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_privateMetadata | null)[]; privateMetadata: (ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_privateMetadata | null)[];
minimumOrderWeight: ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_minimumOrderWeight | null; minimumOrderWeight: ShippingMethodChannelListingUpdate_shippingMethodChannelListingUpdate_shippingMethod_minimumOrderWeight | null;

View file

@ -1,44 +0,0 @@
/* tslint:disable */
/* eslint-disable */
// This file was automatically generated and should not be edited.
import { ShippingZipCodeRulesCreateInput, ShippingErrorCode } from "./../../types/globalTypes";
// ====================================================
// GraphQL mutation operation: ShippingMethodZipCodeRangeAssign
// ====================================================
export interface ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_errors {
__typename: "ShippingError";
code: ShippingErrorCode;
field: string | null;
channels: string[] | null;
}
export interface ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_shippingMethod_zipCodeRules {
__typename: "ShippingMethodZipCodeRule";
id: string;
start: string | null;
end: string | null;
}
export interface ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_shippingMethod {
__typename: "ShippingMethod";
id: string;
zipCodeRules: (ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_shippingMethod_zipCodeRules | null)[] | null;
}
export interface ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate {
__typename: "ShippingZipCodeRulesCreate";
errors: ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_errors[];
shippingMethod: ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate_shippingMethod | null;
}
export interface ShippingMethodZipCodeRangeAssign {
shippingMethodZipCodeRulesCreate: ShippingMethodZipCodeRangeAssign_shippingMethodZipCodeRulesCreate | null;
}
export interface ShippingMethodZipCodeRangeAssignVariables {
id: string;
input: ShippingZipCodeRulesCreateInput;
}

View file

@ -1,43 +0,0 @@
/* tslint:disable */
/* eslint-disable */
// This file was automatically generated and should not be edited.
import { ShippingErrorCode } from "./../../types/globalTypes";
// ====================================================
// GraphQL mutation operation: ShippingMethodZipCodeRangeUnassign
// ====================================================
export interface ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_errors {
__typename: "ShippingError";
code: ShippingErrorCode;
field: string | null;
channels: string[] | null;
}
export interface ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_shippingMethod_zipCodeRules {
__typename: "ShippingMethodZipCodeRule";
id: string;
start: string | null;
end: string | null;
}
export interface ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_shippingMethod {
__typename: "ShippingMethod";
id: string;
zipCodeRules: (ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_shippingMethod_zipCodeRules | null)[] | null;
}
export interface ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete {
__typename: "ShippingZipCodeRulesDelete";
errors: ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_errors[];
shippingMethod: ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete_shippingMethod | null;
}
export interface ShippingMethodZipCodeRangeUnassign {
shippingMethodZipCodeRulesDelete: ShippingMethodZipCodeRangeUnassign_shippingMethodZipCodeRulesDelete | null;
}
export interface ShippingMethodZipCodeRangeUnassignVariables {
id: string;
}

View file

@ -2,7 +2,7 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL query operation: ShippingZone // GraphQL query operation: ShippingZone
@ -26,9 +26,10 @@ export interface ShippingZone_shippingZone_countries {
country: string; country: string;
} }
export interface ShippingZone_shippingZone_shippingMethods_zipCodeRules { export interface ShippingZone_shippingZone_shippingMethods_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -125,7 +126,7 @@ export interface ShippingZone_shippingZone_shippingMethods_excludedProducts {
export interface ShippingZone_shippingZone_shippingMethods { export interface ShippingZone_shippingZone_shippingMethods {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (ShippingZone_shippingZone_shippingMethods_zipCodeRules | null)[] | null; postalCodeRules: (ShippingZone_shippingZone_shippingMethods_postalCodeRules | null)[] | null;
metadata: (ShippingZone_shippingZone_shippingMethods_metadata | null)[]; metadata: (ShippingZone_shippingZone_shippingMethods_metadata | null)[];
privateMetadata: (ShippingZone_shippingZone_shippingMethods_privateMetadata | null)[]; privateMetadata: (ShippingZone_shippingZone_shippingMethods_privateMetadata | null)[];
minimumOrderWeight: ShippingZone_shippingZone_shippingMethods_minimumOrderWeight | null; minimumOrderWeight: ShippingZone_shippingZone_shippingMethods_minimumOrderWeight | null;

View file

@ -2,7 +2,7 @@
/* eslint-disable */ /* eslint-disable */
// This file was automatically generated and should not be edited. // This file was automatically generated and should not be edited.
import { ShippingPriceInput, ShippingErrorCode, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes"; import { ShippingPriceInput, ShippingErrorCode, PostalCodeRuleInclusionTypeEnum, WeightUnitsEnum, ShippingMethodTypeEnum } from "./../../types/globalTypes";
// ==================================================== // ====================================================
// GraphQL mutation operation: UpdateShippingRate // GraphQL mutation operation: UpdateShippingRate
@ -14,9 +14,10 @@ export interface UpdateShippingRate_shippingPriceUpdate_errors {
field: string | null; field: string | null;
} }
export interface UpdateShippingRate_shippingPriceUpdate_shippingMethod_zipCodeRules { export interface UpdateShippingRate_shippingPriceUpdate_shippingMethod_postalCodeRules {
__typename: "ShippingMethodZipCodeRule"; __typename: "ShippingMethodPostalCodeRule";
id: string; id: string;
inclusionType: PostalCodeRuleInclusionTypeEnum | null;
start: string | null; start: string | null;
end: string | null; end: string | null;
} }
@ -82,7 +83,7 @@ export interface UpdateShippingRate_shippingPriceUpdate_shippingMethod_channelLi
export interface UpdateShippingRate_shippingPriceUpdate_shippingMethod { export interface UpdateShippingRate_shippingPriceUpdate_shippingMethod {
__typename: "ShippingMethod"; __typename: "ShippingMethod";
id: string; id: string;
zipCodeRules: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_zipCodeRules | null)[] | null; postalCodeRules: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_postalCodeRules | null)[] | null;
metadata: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_metadata | null)[]; metadata: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_metadata | null)[];
privateMetadata: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_privateMetadata | null)[]; privateMetadata: (UpdateShippingRate_shippingPriceUpdate_shippingMethod_privateMetadata | null)[];
minimumOrderWeight: UpdateShippingRate_shippingPriceUpdate_shippingMethod_minimumOrderWeight | null; minimumOrderWeight: UpdateShippingRate_shippingPriceUpdate_shippingMethod_minimumOrderWeight | null;

View file

@ -2,13 +2,11 @@ import { useChannelsList } from "@saleor/channels/queries";
import { createSortedShippingChannels } from "@saleor/channels/utils"; import { createSortedShippingChannels } from "@saleor/channels/utils";
import ChannelsAvailabilityDialog from "@saleor/components/ChannelsAvailabilityDialog"; import ChannelsAvailabilityDialog from "@saleor/components/ChannelsAvailabilityDialog";
import { WindowTitle } from "@saleor/components/WindowTitle"; import { WindowTitle } from "@saleor/components/WindowTitle";
import { ShippingMethodFragment_zipCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
import useChannels from "@saleor/hooks/useChannels"; import useChannels from "@saleor/hooks/useChannels";
import useNavigator from "@saleor/hooks/useNavigator"; import useNavigator from "@saleor/hooks/useNavigator";
import { sectionNames } from "@saleor/intl"; import { sectionNames } from "@saleor/intl";
import ShippingRateZipCodeRangeRemoveDialog from "@saleor/shipping/components/ShippingRateZipCodeRangeRemoveDialog"; import ShippingZonePostalCodeRangeDialog from "@saleor/shipping/components/ShippingZonePostalCodeRangeDialog";
import ShippingZoneRatesCreatePage from "@saleor/shipping/components/ShippingZoneRatesCreatePage"; import ShippingZoneRatesCreatePage from "@saleor/shipping/components/ShippingZoneRatesCreatePage";
import ShippingZoneZipCodeRangeDialog from "@saleor/shipping/components/ShippingZoneZipCodeRangeDialog";
import { useShippingRateCreator } from "@saleor/shipping/handlers"; import { useShippingRateCreator } from "@saleor/shipping/handlers";
import { import {
shippingPriceRatesUrl, shippingPriceRatesUrl,
@ -16,10 +14,13 @@ import {
ShippingRateCreateUrlQueryParams, ShippingRateCreateUrlQueryParams,
shippingZoneUrl shippingZoneUrl
} from "@saleor/shipping/urls"; } from "@saleor/shipping/urls";
import filterPostalCodes from "@saleor/shipping/views/utils";
import { MinMax } from "@saleor/types"; import { MinMax } from "@saleor/types";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import { remove } from "@saleor/utils/lists";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -35,9 +36,10 @@ export const PriceRatesCreate: React.FC<PriceRatesCreateProps> = ({
const navigate = useNavigator(); const navigate = useNavigator();
const intl = useIntl(); const intl = useIntl();
const [zipCodes, setZipCodes] = React.useState< const [postalCodes, setPostalCodes] = React.useState([]);
ShippingMethodFragment_zipCodeRules[] const [radioInclusionType, setRadioInclusionType] = React.useState(
>([]); PostalCodeRuleInclusionTypeEnum.EXCLUDE
);
const { data: channelsData, loading: channelsLoading } = useChannelsList({}); const { data: channelsData, loading: channelsLoading } = useChannelsList({});
@ -66,30 +68,35 @@ export const PriceRatesCreate: React.FC<PriceRatesCreateProps> = ({
createShippingRate, createShippingRate,
errors, errors,
status status
} = useShippingRateCreator(id, ShippingMethodTypeEnum.PRICE, zipCodes); } = useShippingRateCreator(
id,
ShippingMethodTypeEnum.PRICE,
postalCodes,
radioInclusionType
);
const handleBack = () => navigate(shippingZoneUrl(id)); const handleBack = () => navigate(shippingZoneUrl(id));
const handleZipCodeRangeAdd = (data: MinMax) => { const handlePostalCodeRangeAdd = (data: MinMax) => {
setZipCodes(zipCodes => [ setPostalCodes(postalCodes => [
...zipCodes, ...postalCodes,
{ {
__typename: "ShippingMethodZipCodeRule",
end: data.max, end: data.max,
id: zipCodes.length.toString(),
start: data.min start: data.min
} }
]); ]);
closeModal(); closeModal();
}; };
const handleZipCodeRangeDelete = (id: string) => {
setZipCodes(zipCodes => const onPostalCodeInclusionChange = (
remove( inclusion: PostalCodeRuleInclusionTypeEnum
zipCodes.find(zipCode => zipCode.id === id), ) => {
zipCodes, setRadioInclusionType(inclusion);
(a, b) => a.id === b.id setPostalCodes([]);
) };
);
const onPostalCodeUnassign = code => {
setPostalCodes(filterPostalCodes(postalCodes, code));
closeModal(); closeModal();
}; };
@ -123,29 +130,20 @@ export const PriceRatesCreate: React.FC<PriceRatesCreateProps> = ({
onBack={handleBack} onBack={handleBack}
errors={errors} errors={errors}
channelErrors={channelErrors} channelErrors={channelErrors}
zipCodes={zipCodes} postalCodes={postalCodes}
openChannelsModal={handleChannelsModalOpen} openChannelsModal={handleChannelsModalOpen}
onChannelsChange={setCurrentChannels} onChannelsChange={setCurrentChannels}
onZipCodeAssign={() => openModal("add-range")} onPostalCodeAssign={() => openModal("add-range")}
onZipCodeUnassign={id => onPostalCodeUnassign={onPostalCodeUnassign}
openModal("remove-range", { onPostalCodeInclusionChange={onPostalCodeInclusionChange}
id
})
}
variant={ShippingMethodTypeEnum.PRICE} variant={ShippingMethodTypeEnum.PRICE}
/> />
<ShippingZoneZipCodeRangeDialog <ShippingZonePostalCodeRangeDialog
confirmButtonState="default" confirmButtonState="default"
onClose={closeModal} onClose={closeModal}
onSubmit={handleZipCodeRangeAdd} onSubmit={handlePostalCodeRangeAdd}
open={params.action === "add-range"} open={params.action === "add-range"}
/> />
<ShippingRateZipCodeRangeRemoveDialog
confirmButtonState="default"
onClose={closeModal}
onConfirm={() => handleZipCodeRangeDelete(params.id)}
open={params.action === "remove-range"}
/>
</> </>
); );
}; };

View file

@ -20,11 +20,10 @@ import { commonMessages } from "@saleor/intl";
import useProductSearch from "@saleor/searches/useProductSearch"; import useProductSearch from "@saleor/searches/useProductSearch";
import DeleteShippingRateDialog from "@saleor/shipping/components/DeleteShippingRateDialog"; import DeleteShippingRateDialog from "@saleor/shipping/components/DeleteShippingRateDialog";
import ShippingMethodProductsAddDialog from "@saleor/shipping/components/ShippingMethodProductsAddDialog"; import ShippingMethodProductsAddDialog from "@saleor/shipping/components/ShippingMethodProductsAddDialog";
import ShippingRateZipCodeRangeRemoveDialog from "@saleor/shipping/components/ShippingRateZipCodeRangeRemoveDialog"; import ShippingZonePostalCodeRangeDialog from "@saleor/shipping/components/ShippingZonePostalCodeRangeDialog";
import ShippingZoneRatesPage, { import ShippingZoneRatesPage, {
FormData FormData
} from "@saleor/shipping/components/ShippingZoneRatesPage"; } from "@saleor/shipping/components/ShippingZoneRatesPage";
import ShippingZoneZipCodeRangeDialog from "@saleor/shipping/components/ShippingZoneZipCodeRangeDialog";
import UnassignDialog from "@saleor/shipping/components/UnassignDialog"; import UnassignDialog from "@saleor/shipping/components/UnassignDialog";
import { import {
getShippingMethodChannelVariables, getShippingMethodChannelVariables,
@ -32,8 +31,6 @@ import {
} from "@saleor/shipping/handlers"; } from "@saleor/shipping/handlers";
import { import {
useShippingMethodChannelListingUpdate, useShippingMethodChannelListingUpdate,
useShippingMethodZipCodeRangeAssign,
useShippingMethodZipCodeRangeUnassign,
useShippingPriceExcludeProduct, useShippingPriceExcludeProduct,
useShippingPriceRemoveProductsFromExclude, useShippingPriceRemoveProductsFromExclude,
useShippingRateDelete, useShippingRateDelete,
@ -46,7 +43,12 @@ import {
ShippingRateUrlQueryParams, ShippingRateUrlQueryParams,
shippingZoneUrl shippingZoneUrl
} from "@saleor/shipping/urls"; } from "@saleor/shipping/urls";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import filterPostalCodes from "@saleor/shipping/views/utils";
import { MinMax } from "@saleor/types";
import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler"; import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler";
import { import {
@ -110,43 +112,6 @@ export const PriceRatesUpdate: React.FC<PriceRatesUpdateProps> = ({
updateShippingMethodChannelListingOpts updateShippingMethodChannelListingOpts
] = useShippingMethodChannelListingUpdate({}); ] = useShippingMethodChannelListingUpdate({});
const [
assignZipCodeRange,
assignZipCodeRangeOpts
] = useShippingMethodZipCodeRangeAssign({
onCompleted: data => {
if (data.shippingMethodZipCodeRulesCreate.errors.length === 0) {
notify({
status: "success",
text: intl.formatMessage(commonMessages.savedChanges)
});
closeModal();
} else {
notify({
status: "error",
text: intl.formatMessage({
defaultMessage: "Cannot add specified postal codes range.",
description: "postal code range add error text"
})
});
}
}
});
const [
unassignZipCodeRange,
unassignZipCodeRangeOpts
] = useShippingMethodZipCodeRangeUnassign({
onCompleted: data => {
if (data.shippingMethodZipCodeRulesDelete.errors.length === 0) {
notify({
status: "success",
text: intl.formatMessage(commonMessages.savedChanges)
});
}
}
});
const [ const [
unassignProduct, unassignProduct,
unassignProductOpts unassignProductOpts
@ -209,10 +174,40 @@ export const PriceRatesUpdate: React.FC<PriceRatesUpdateProps> = ({
const [updateMetadata] = useMetadataUpdate({}); const [updateMetadata] = useMetadataUpdate({});
const [updatePrivateMetadata] = usePrivateMetadataUpdate({}); const [updatePrivateMetadata] = usePrivateMetadataUpdate({});
const [codesToDelete, setCodesToDelete] = React.useState([]);
const [havePostalCodesChanged, setHavePostalCodesChanged] = React.useState(
false
);
const [originalCodes, setOriginalCodes] = React.useState([]);
const [inclusionType, setInclusionType] = React.useState(
rate?.postalCodeRules[0]?.inclusionType
);
const onPostalCodeInclusionChange = (
inclusion: PostalCodeRuleInclusionTypeEnum
) => {
setInclusionType(inclusion);
setCodesToDelete(
rate.postalCodeRules
.filter(code => code.id !== undefined)
.map(code => code.id)
);
setHavePostalCodesChanged(true);
rate.postalCodeRules = [];
};
const updateData = async (formData: FormData): Promise<unknown[]> => { const updateData = async (formData: FormData): Promise<unknown[]> => {
const response = await updateShippingRate({ const response = await updateShippingRate({
variables: getUpdateShippingPriceRateVariables(formData, id, rateId) variables: getUpdateShippingPriceRateVariables(
formData,
id,
rateId,
rate.postalCodeRules,
codesToDelete
)
}); });
setCodesToDelete([]);
setHavePostalCodesChanged(false);
const errors = response.data.shippingPriceUpdate.errors; const errors = response.data.shippingPriceUpdate.errors;
if (errors.length === 0) { if (errors.length === 0) {
handleSuccess(); handleSuccess();
@ -248,6 +243,41 @@ export const PriceRatesUpdate: React.FC<PriceRatesUpdateProps> = ({
reset(); reset();
}; };
const onPostalCodeAssign = (rule: MinMax) => {
if (!originalCodes.length) {
setOriginalCodes([...rate.postalCodeRules]);
}
if (
rate.postalCodeRules.filter(
item => item.start === rule.min && item.end === rule.max
).length > 0
) {
closeModal();
return;
}
const newCode = {
__typename: undefined,
end: rule.max,
id: undefined,
inclusionType,
start: rule.min
};
rate.postalCodeRules.push(newCode);
closeModal();
};
const onPostalCodeUnassign = code => {
if (code.id !== undefined) {
setCodesToDelete([...codesToDelete, code.id]);
rate.postalCodeRules = rate.postalCodeRules.filter(
rule => rule.id !== code.id
);
} else {
rate.postalCodeRules = filterPostalCodes(rate.postalCodeRules, code);
}
setHavePostalCodesChanged(true);
};
const handleBack = () => navigate(shippingZoneUrl(id)); const handleBack = () => navigate(shippingZoneUrl(id));
return ( return (
@ -314,6 +344,7 @@ export const PriceRatesUpdate: React.FC<PriceRatesUpdateProps> = ({
assignProductOpts?.status === "loading" assignProductOpts?.status === "loading"
} }
hasChannelChanged={shippingChannels?.length !== currentChannels?.length} hasChannelChanged={shippingChannels?.length !== currentChannels?.length}
havePostalCodesChanged={havePostalCodesChanged}
saveButtonBarState={updateShippingRateOpts.status} saveButtonBarState={updateShippingRateOpts.status}
onDelete={() => openModal("remove")} onDelete={() => openModal("remove")}
onSubmit={handleSubmit} onSubmit={handleSubmit}
@ -344,45 +375,19 @@ export const PriceRatesUpdate: React.FC<PriceRatesUpdateProps> = ({
/> />
</Button> </Button>
} }
onZipCodeAssign={() => openModal("add-range")} onPostalCodeInclusionChange={onPostalCodeInclusionChange}
onZipCodeUnassign={id => onPostalCodeAssign={() => openModal("add-range")}
openModal("remove-range", { onPostalCodeUnassign={onPostalCodeUnassign}
id
})
}
/> />
<ShippingZoneZipCodeRangeDialog <ShippingZonePostalCodeRangeDialog
confirmButtonState={assignZipCodeRangeOpts.status} confirmButtonState={"default"}
onClose={closeModal} onClose={closeModal}
onSubmit={data => onSubmit={code => {
assignZipCodeRange({ onPostalCodeAssign(code);
variables: { setHavePostalCodesChanged(true);
id: rateId, }}
input: {
zipCodeRules: [
{
end: data.max || null,
start: data.min
}
]
}
}
})
}
open={params.action === "add-range"} open={params.action === "add-range"}
/> />
<ShippingRateZipCodeRangeRemoveDialog
confirmButtonState={unassignZipCodeRangeOpts.status}
onClose={closeModal}
onConfirm={() =>
unassignZipCodeRange({
variables: {
id: params.id
}
})
}
open={params.action === "remove-range"}
/>
</> </>
); );
}; };

View file

@ -5,13 +5,11 @@ import {
} from "@saleor/channels/utils"; } from "@saleor/channels/utils";
import ChannelsAvailabilityDialog from "@saleor/components/ChannelsAvailabilityDialog"; import ChannelsAvailabilityDialog from "@saleor/components/ChannelsAvailabilityDialog";
import { WindowTitle } from "@saleor/components/WindowTitle"; import { WindowTitle } from "@saleor/components/WindowTitle";
import { ShippingMethodFragment_zipCodeRules } from "@saleor/fragments/types/ShippingMethodFragment";
import useChannels from "@saleor/hooks/useChannels"; import useChannels from "@saleor/hooks/useChannels";
import useNavigator from "@saleor/hooks/useNavigator"; import useNavigator from "@saleor/hooks/useNavigator";
import { sectionNames } from "@saleor/intl"; import { sectionNames } from "@saleor/intl";
import ShippingRateZipCodeRangeRemoveDialog from "@saleor/shipping/components/ShippingRateZipCodeRangeRemoveDialog"; import ShippingZonePostalCodeRangeDialog from "@saleor/shipping/components/ShippingZonePostalCodeRangeDialog";
import ShippingZoneRatesCreatePage from "@saleor/shipping/components/ShippingZoneRatesCreatePage"; import ShippingZoneRatesCreatePage from "@saleor/shipping/components/ShippingZoneRatesCreatePage";
import ShippingZoneZipCodeRangeDialog from "@saleor/shipping/components/ShippingZoneZipCodeRangeDialog";
import { useShippingRateCreator } from "@saleor/shipping/handlers"; import { useShippingRateCreator } from "@saleor/shipping/handlers";
import { import {
ShippingRateCreateUrlDialog, ShippingRateCreateUrlDialog,
@ -19,10 +17,13 @@ import {
shippingWeightRatesUrl, shippingWeightRatesUrl,
shippingZoneUrl shippingZoneUrl
} from "@saleor/shipping/urls"; } from "@saleor/shipping/urls";
import filterPostalCodes from "@saleor/shipping/views/utils";
import { MinMax } from "@saleor/types"; import { MinMax } from "@saleor/types";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import { remove } from "@saleor/utils/lists";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -38,9 +39,10 @@ export const WeightRatesCreate: React.FC<WeightRatesCreateProps> = ({
const navigate = useNavigator(); const navigate = useNavigator();
const intl = useIntl(); const intl = useIntl();
const [zipCodes, setZipCodes] = React.useState< const [postalCodes, setPostalCodes] = React.useState([]);
ShippingMethodFragment_zipCodeRules[] const [radioInclusionType, setRadioInclusionType] = React.useState(
>([]); PostalCodeRuleInclusionTypeEnum.EXCLUDE
);
const { data: channelsData, loading: channelsLoading } = useChannelsList({}); const { data: channelsData, loading: channelsLoading } = useChannelsList({});
@ -70,30 +72,38 @@ export const WeightRatesCreate: React.FC<WeightRatesCreateProps> = ({
createShippingRate, createShippingRate,
errors, errors,
status status
} = useShippingRateCreator(id, ShippingMethodTypeEnum.WEIGHT, zipCodes); } = useShippingRateCreator(
id,
ShippingMethodTypeEnum.WEIGHT,
postalCodes,
radioInclusionType
);
const handleBack = () => navigate(shippingZoneUrl(id)); const handleBack = () => navigate(shippingZoneUrl(id));
const handleZipCodeRangeAdd = (data: MinMax) => { const handlePostalCodeRangeAdd = (data: MinMax) => {
setZipCodes(zipCodes => [ setPostalCodes(postalCodes => [
...zipCodes, ...postalCodes,
{ {
__typename: "ShippingMethodZipCodeRule", __typename: "ShippingMethodPostalCodeRule",
end: data.max, end: data.max,
id: zipCodes.length.toString(), id: postalCodes.length.toString(),
inclusionType: postalCodes?.[0]?.inclusionType,
start: data.min start: data.min
} }
]); ]);
closeModal(); closeModal();
}; };
const handleZipCodeRangeDelete = (id: string) => {
setZipCodes(zipCodes => const onPostalCodeInclusionChange = (
remove( inclusion: PostalCodeRuleInclusionTypeEnum
zipCodes.find(zipCode => zipCode.id === id), ) => {
zipCodes, setRadioInclusionType(inclusion);
(a, b) => a.id === b.id setPostalCodes([]);
) };
);
const onPostalCodeUnassign = code => {
setPostalCodes(filterPostalCodes(postalCodes, code));
closeModal(); closeModal();
}; };
@ -126,29 +136,20 @@ export const WeightRatesCreate: React.FC<WeightRatesCreateProps> = ({
onBack={handleBack} onBack={handleBack}
errors={errors} errors={errors}
channelErrors={channelErrors} channelErrors={channelErrors}
zipCodes={zipCodes} postalCodes={postalCodes}
openChannelsModal={handleChannelsModalOpen} openChannelsModal={handleChannelsModalOpen}
onChannelsChange={setCurrentChannels} onChannelsChange={setCurrentChannels}
onZipCodeAssign={() => openModal("add-range")} onPostalCodeAssign={() => openModal("add-range")}
onZipCodeUnassign={id => onPostalCodeUnassign={onPostalCodeUnassign}
openModal("remove-range", { onPostalCodeInclusionChange={onPostalCodeInclusionChange}
id
})
}
variant={ShippingMethodTypeEnum.WEIGHT} variant={ShippingMethodTypeEnum.WEIGHT}
/> />
<ShippingZoneZipCodeRangeDialog <ShippingZonePostalCodeRangeDialog
confirmButtonState="default" confirmButtonState="default"
onClose={closeModal} onClose={closeModal}
onSubmit={handleZipCodeRangeAdd} onSubmit={handlePostalCodeRangeAdd}
open={params.action === "add-range"} open={params.action === "add-range"}
/> />
<ShippingRateZipCodeRangeRemoveDialog
confirmButtonState="default"
onClose={closeModal}
onConfirm={() => handleZipCodeRangeDelete(params.id)}
open={params.action === "remove-range"}
/>
</> </>
); );
}; };

View file

@ -20,11 +20,10 @@ import { commonMessages } from "@saleor/intl";
import useProductSearch from "@saleor/searches/useProductSearch"; import useProductSearch from "@saleor/searches/useProductSearch";
import DeleteShippingRateDialog from "@saleor/shipping/components/DeleteShippingRateDialog"; import DeleteShippingRateDialog from "@saleor/shipping/components/DeleteShippingRateDialog";
import ShippingMethodProductsAddDialog from "@saleor/shipping/components/ShippingMethodProductsAddDialog"; import ShippingMethodProductsAddDialog from "@saleor/shipping/components/ShippingMethodProductsAddDialog";
import ShippingRateZipCodeRangeRemoveDialog from "@saleor/shipping/components/ShippingRateZipCodeRangeRemoveDialog"; import ShippingZonePostalCodeRangeDialog from "@saleor/shipping/components/ShippingZonePostalCodeRangeDialog";
import ShippingZoneRatesPage, { import ShippingZoneRatesPage, {
FormData FormData
} from "@saleor/shipping/components/ShippingZoneRatesPage"; } from "@saleor/shipping/components/ShippingZoneRatesPage";
import ShippingZoneZipCodeRangeDialog from "@saleor/shipping/components/ShippingZoneZipCodeRangeDialog";
import UnassignDialog from "@saleor/shipping/components/UnassignDialog"; import UnassignDialog from "@saleor/shipping/components/UnassignDialog";
import { import {
getShippingMethodChannelVariables, getShippingMethodChannelVariables,
@ -32,8 +31,6 @@ import {
} from "@saleor/shipping/handlers"; } from "@saleor/shipping/handlers";
import { import {
useShippingMethodChannelListingUpdate, useShippingMethodChannelListingUpdate,
useShippingMethodZipCodeRangeAssign,
useShippingMethodZipCodeRangeUnassign,
useShippingPriceExcludeProduct, useShippingPriceExcludeProduct,
useShippingPriceRemoveProductsFromExclude, useShippingPriceRemoveProductsFromExclude,
useShippingRateDelete, useShippingRateDelete,
@ -46,7 +43,12 @@ import {
shippingWeightRatesEditUrl, shippingWeightRatesEditUrl,
shippingZoneUrl shippingZoneUrl
} from "@saleor/shipping/urls"; } from "@saleor/shipping/urls";
import { ShippingMethodTypeEnum } from "@saleor/types/globalTypes"; import filterPostalCodes from "@saleor/shipping/views/utils";
import { MinMax } from "@saleor/types";
import {
PostalCodeRuleInclusionTypeEnum,
ShippingMethodTypeEnum
} from "@saleor/types/globalTypes";
import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers"; import createDialogActionHandlers from "@saleor/utils/handlers/dialogActionHandlers";
import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler"; import createMetadataUpdateHandler from "@saleor/utils/handlers/metadataUpdateHandler";
import { import {
@ -84,6 +86,51 @@ export const WeightRatesUpdate: React.FC<WeightRatesUpdateProps> = ({
ShippingRateUrlQueryParams ShippingRateUrlQueryParams
>(navigate, params => shippingWeightRatesEditUrl(id, rateId, params), params); >(navigate, params => shippingWeightRatesEditUrl(id, rateId, params), params);
const [codesToDelete, setCodesToDelete] = React.useState([]);
const [havePostalCodesChanged, setHavePostalCodesChanged] = React.useState(
false
);
const [originalCodes, setOriginalCodes] = React.useState([]);
const [inclusionType, setInclusionType] = React.useState(
PostalCodeRuleInclusionTypeEnum.EXCLUDE
);
const onPostalCodeInclusionChange = (
inclusion: PostalCodeRuleInclusionTypeEnum
) => {
setInclusionType(inclusion);
setCodesToDelete(
rate.postalCodeRules
.filter(code => code.id !== undefined)
.map(code => code.id)
);
setHavePostalCodesChanged(true);
rate.postalCodeRules = [];
};
const onPostalCodeAssign = (rule: MinMax) => {
if (!originalCodes.length) {
setOriginalCodes([...rate.postalCodeRules]);
}
if (
rate.postalCodeRules.filter(
item => item.start === rule.min && item.end === rule.max
).length > 0
) {
closeModal();
return;
}
const newCode = {
__typename: undefined,
end: rule.max,
id: undefined,
inclusionType,
start: rule.min
};
rate.postalCodeRules.push(newCode);
closeModal();
};
const { const {
loadMore, loadMore,
search: productsSearch, search: productsSearch,
@ -171,50 +218,21 @@ export const WeightRatesUpdate: React.FC<WeightRatesUpdateProps> = ({
} }
}); });
const [
assignZipCodeRange,
assignZipCodeRangeOpts
] = useShippingMethodZipCodeRangeAssign({
onCompleted: data => {
if (data.shippingMethodZipCodeRulesCreate.errors.length === 0) {
notify({
status: "success",
text: intl.formatMessage(commonMessages.savedChanges)
});
closeModal();
} else {
notify({
status: "error",
text: intl.formatMessage({
defaultMessage: "Cannot add specified postal codes range.",
description: "postal code range add error text"
})
});
}
}
});
const [
unassignZipCodeRange,
unassignZipCodeRangeOpts
] = useShippingMethodZipCodeRangeUnassign({
onCompleted: data => {
if (data.shippingMethodZipCodeRulesDelete.errors.length === 0) {
notify({
status: "success",
text: intl.formatMessage(commonMessages.savedChanges)
});
closeModal();
}
}
});
const [updateMetadata] = useMetadataUpdate({}); const [updateMetadata] = useMetadataUpdate({});
const [updatePrivateMetadata] = usePrivateMetadataUpdate({}); const [updatePrivateMetadata] = usePrivateMetadataUpdate({});
const updateData = async (data: FormData) => { const updateData = async (data: FormData) => {
const response = await updateShippingRate({ const response = await updateShippingRate({
variables: getUpdateShippingWeightRateVariables(data, id, rateId) variables: getUpdateShippingWeightRateVariables(
data,
id,
rateId,
rate.postalCodeRules,
codesToDelete
)
}); });
setCodesToDelete([]);
setHavePostalCodesChanged(false);
const errors = response.data.shippingPriceUpdate.errors; const errors = response.data.shippingPriceUpdate.errors;
if (errors.length === 0) { if (errors.length === 0) {
handleSuccess(); handleSuccess();
@ -231,6 +249,18 @@ export const WeightRatesUpdate: React.FC<WeightRatesUpdateProps> = ({
return errors; return errors;
}; };
const onPostalCodeUnassign = code => {
if (code.id !== undefined) {
setCodesToDelete([...codesToDelete, code.id]);
rate.postalCodeRules = rate.postalCodeRules.filter(
rule => rule.id !== code.id
);
} else {
rate.postalCodeRules = filterPostalCodes(rate.postalCodeRules, code);
}
setHavePostalCodesChanged(true);
};
const handleSubmit = createMetadataUpdateHandler( const handleSubmit = createMetadataUpdateHandler(
rate, rate,
updateData, updateData,
@ -316,6 +346,7 @@ export const WeightRatesUpdate: React.FC<WeightRatesUpdateProps> = ({
assignProductOpts?.status === "loading" assignProductOpts?.status === "loading"
} }
hasChannelChanged={shippingChannels?.length !== currentChannels?.length} hasChannelChanged={shippingChannels?.length !== currentChannels?.length}
havePostalCodesChanged={havePostalCodesChanged}
saveButtonBarState={updateShippingRateOpts.status} saveButtonBarState={updateShippingRateOpts.status}
onDelete={() => openModal("remove")} onDelete={() => openModal("remove")}
onSubmit={handleSubmit} onSubmit={handleSubmit}
@ -346,45 +377,19 @@ export const WeightRatesUpdate: React.FC<WeightRatesUpdateProps> = ({
/> />
</Button> </Button>
} }
onZipCodeAssign={() => openModal("add-range")} onPostalCodeInclusionChange={onPostalCodeInclusionChange}
onZipCodeUnassign={id => onPostalCodeAssign={() => openModal("add-range")}
openModal("remove-range", { onPostalCodeUnassign={onPostalCodeUnassign}
id
})
}
/> />
<ShippingZoneZipCodeRangeDialog <ShippingZonePostalCodeRangeDialog
confirmButtonState={assignZipCodeRangeOpts.status} confirmButtonState={"default"}
onClose={closeModal} onClose={closeModal}
onSubmit={data => onSubmit={code => {
assignZipCodeRange({ onPostalCodeAssign(code);
variables: { setHavePostalCodesChanged(true);
id: rateId, }}
input: {
zipCodeRules: [
{
end: data.max || null,
start: data.min
}
]
}
}
})
}
open={params.action === "add-range"} open={params.action === "add-range"}
/> />
<ShippingRateZipCodeRangeRemoveDialog
confirmButtonState={unassignZipCodeRangeOpts.status}
onClose={closeModal}
onConfirm={() =>
unassignZipCodeRange({
variables: {
id: params.id
}
})
}
open={params.action === "remove-range"}
/>
</> </>
); );
}; };

View file

@ -0,0 +1,7 @@
const filterPostalCodes = (postalCodes, codeToFilterOut) =>
postalCodes.filter(
rule =>
rule.start !== codeToFilterOut.start && rule.end !== codeToFilterOut.end
);
export default filterPostalCodes;

File diff suppressed because it is too large Load diff

View file

@ -5,7 +5,10 @@ import LanguageSwitch from "@saleor/components/LanguageSwitch";
import PageHeader from "@saleor/components/PageHeader"; import PageHeader from "@saleor/components/PageHeader";
import { CategoryTranslationFragment } from "@saleor/fragments/types/CategoryTranslationFragment"; import { CategoryTranslationFragment } from "@saleor/fragments/types/CategoryTranslationFragment";
import { commonMessages, sectionNames } from "@saleor/intl"; import { commonMessages, sectionNames } from "@saleor/intl";
import { TranslationsEntitiesPageProps } from "@saleor/translations/types"; import {
TranslationInputFieldName,
TranslationsEntitiesPageProps
} from "@saleor/translations/types";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -17,13 +20,6 @@ export interface TranslationsCategoriesPageProps
data: CategoryTranslationFragment; data: CategoryTranslationFragment;
} }
export const fieldNames = {
description: "description",
name: "name",
seoDescription: "seoDescription",
seoTitle: "seoTitle"
};
const TranslationsCategoriesPage: React.FC<TranslationsCategoriesPageProps> = ({ const TranslationsCategoriesPage: React.FC<TranslationsCategoriesPageProps> = ({
activeField, activeField,
disabled, disabled,
@ -72,14 +68,14 @@ const TranslationsCategoriesPage: React.FC<TranslationsCategoriesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Category Name" defaultMessage: "Category Name"
}), }),
name: fieldNames.name, name: TranslationInputFieldName.name,
translation: data?.translation?.name || null, translation: data?.translation?.name || null,
type: "short" as "short", type: "short" as "short",
value: data?.category?.name value: data?.category?.name
}, },
{ {
displayName: intl.formatMessage(commonMessages.description), displayName: intl.formatMessage(commonMessages.description),
name: fieldNames.description, name: TranslationInputFieldName.description,
translation: data?.translation?.description || null, translation: data?.translation?.description || null,
type: "rich" as "rich", type: "rich" as "rich",
value: data?.category?.description value: data?.category?.description
@ -103,7 +99,7 @@ const TranslationsCategoriesPage: React.FC<TranslationsCategoriesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Title" defaultMessage: "Search Engine Title"
}), }),
name: fieldNames.seoTitle, name: TranslationInputFieldName.seoTitle,
translation: data?.translation?.seoTitle || null, translation: data?.translation?.seoTitle || null,
type: "short" as "short", type: "short" as "short",
value: data?.category?.seoTitle value: data?.category?.seoTitle
@ -112,7 +108,7 @@ const TranslationsCategoriesPage: React.FC<TranslationsCategoriesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Description" defaultMessage: "Search Engine Description"
}), }),
name: fieldNames.seoDescription, name: TranslationInputFieldName.seoDescription,
translation: data?.translation?.seoDescription || null, translation: data?.translation?.seoDescription || null,
type: "long" as "long", type: "long" as "long",
value: data?.category?.seoDescription value: data?.category?.seoDescription

View file

@ -5,7 +5,10 @@ import LanguageSwitch from "@saleor/components/LanguageSwitch";
import PageHeader from "@saleor/components/PageHeader"; import PageHeader from "@saleor/components/PageHeader";
import { CollectionTranslationFragment } from "@saleor/fragments/types/CollectionTranslationFragment"; import { CollectionTranslationFragment } from "@saleor/fragments/types/CollectionTranslationFragment";
import { commonMessages, sectionNames } from "@saleor/intl"; import { commonMessages, sectionNames } from "@saleor/intl";
import { TranslationsEntitiesPageProps } from "@saleor/translations/types"; import {
TranslationInputFieldName,
TranslationsEntitiesPageProps
} from "@saleor/translations/types";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -17,13 +20,6 @@ export interface TranslationsCollectionsPageProps
data: CollectionTranslationFragment; data: CollectionTranslationFragment;
} }
export const fieldNames = {
description: "description",
name: "name",
seoDescription: "seoDescription",
seoTitle: "seoTitle"
};
const TranslationsCollectionsPage: React.FC<TranslationsCollectionsPageProps> = ({ const TranslationsCollectionsPage: React.FC<TranslationsCollectionsPageProps> = ({
activeField, activeField,
disabled, disabled,
@ -73,14 +69,14 @@ const TranslationsCollectionsPage: React.FC<TranslationsCollectionsPageProps> =
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Collection Name" defaultMessage: "Collection Name"
}), }),
name: fieldNames.name, name: TranslationInputFieldName.name,
translation: data?.translation?.name || null, translation: data?.translation?.name || null,
type: "short" as "short", type: "short" as "short",
value: data?.collection?.name value: data?.collection?.name
}, },
{ {
displayName: intl.formatMessage(commonMessages.description), displayName: intl.formatMessage(commonMessages.description),
name: fieldNames.description, name: TranslationInputFieldName.description,
translation: data?.translation?.description || null, translation: data?.translation?.description || null,
type: "rich" as "rich", type: "rich" as "rich",
value: data?.collection?.description value: data?.collection?.description
@ -104,7 +100,7 @@ const TranslationsCollectionsPage: React.FC<TranslationsCollectionsPageProps> =
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Title" defaultMessage: "Search Engine Title"
}), }),
name: fieldNames.seoTitle, name: TranslationInputFieldName.seoTitle,
translation: data?.translation?.seoTitle || null, translation: data?.translation?.seoTitle || null,
type: "short" as "short", type: "short" as "short",
value: data?.collection?.seoTitle value: data?.collection?.seoTitle
@ -113,7 +109,7 @@ const TranslationsCollectionsPage: React.FC<TranslationsCollectionsPageProps> =
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Description" defaultMessage: "Search Engine Description"
}), }),
name: fieldNames.seoDescription, name: TranslationInputFieldName.seoDescription,
translation: data?.translation?.seoDescription || null, translation: data?.translation?.seoDescription || null,
type: "long" as "long", type: "long" as "long",
value: data?.collection?.seoDescription value: data?.collection?.seoDescription

View file

@ -5,7 +5,10 @@ import LanguageSwitch from "@saleor/components/LanguageSwitch";
import PageHeader from "@saleor/components/PageHeader"; import PageHeader from "@saleor/components/PageHeader";
import { PageTranslationFragment } from "@saleor/fragments/types/PageTranslationFragment"; import { PageTranslationFragment } from "@saleor/fragments/types/PageTranslationFragment";
import { commonMessages, sectionNames } from "@saleor/intl"; import { commonMessages, sectionNames } from "@saleor/intl";
import { TranslationsEntitiesPageProps } from "@saleor/translations/types"; import {
PageTranslationInputFieldName,
TranslationsEntitiesPageProps
} from "@saleor/translations/types";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -17,13 +20,6 @@ export interface TranslationsPagesPageProps
data: PageTranslationFragment; data: PageTranslationFragment;
} }
export const fieldNames = {
content: "content",
seoDescription: "seoDescription",
seoTitle: "seoTitle",
title: "title"
};
const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({ const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({
activeField, activeField,
disabled, disabled,
@ -72,7 +68,7 @@ const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Page Title" defaultMessage: "Page Title"
}), }),
name: fieldNames.title, name: PageTranslationInputFieldName.title,
translation: data?.translation?.title || null, translation: data?.translation?.title || null,
type: "short" as "short", type: "short" as "short",
value: data?.page?.title value: data?.page?.title
@ -82,7 +78,7 @@ const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({
defaultMessage: "Content", defaultMessage: "Content",
description: "page content" description: "page content"
}), }),
name: fieldNames.content, name: PageTranslationInputFieldName.content,
translation: data?.translation?.content || null, translation: data?.translation?.content || null,
type: "rich" as "rich", type: "rich" as "rich",
value: data?.page?.content value: data?.page?.content
@ -106,7 +102,7 @@ const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Title" defaultMessage: "Search Engine Title"
}), }),
name: fieldNames.seoTitle, name: PageTranslationInputFieldName.seoTitle,
translation: data?.translation?.seoTitle || null, translation: data?.translation?.seoTitle || null,
type: "short" as "short", type: "short" as "short",
value: data?.page?.seoTitle value: data?.page?.seoTitle
@ -115,7 +111,7 @@ const TranslationsPagesPage: React.FC<TranslationsPagesPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Description" defaultMessage: "Search Engine Description"
}), }),
name: fieldNames.seoDescription, name: PageTranslationInputFieldName.seoDescription,
translation: data?.translation?.seoDescription || null, translation: data?.translation?.seoDescription || null,
type: "long" as "long", type: "long" as "long",
value: data?.page?.seoDescription value: data?.page?.seoDescription

View file

@ -5,7 +5,10 @@ import LanguageSwitch from "@saleor/components/LanguageSwitch";
import PageHeader from "@saleor/components/PageHeader"; import PageHeader from "@saleor/components/PageHeader";
import { ProductTranslationFragment } from "@saleor/fragments/types/ProductTranslationFragment"; import { ProductTranslationFragment } from "@saleor/fragments/types/ProductTranslationFragment";
import { commonMessages, sectionNames } from "@saleor/intl"; import { commonMessages, sectionNames } from "@saleor/intl";
import { TranslationsEntitiesPageProps } from "@saleor/translations/types"; import {
TranslationInputFieldName,
TranslationsEntitiesPageProps
} from "@saleor/translations/types";
import React from "react"; import React from "react";
import { useIntl } from "react-intl"; import { useIntl } from "react-intl";
@ -17,13 +20,6 @@ export interface TranslationsProductsPageProps
data: ProductTranslationFragment; data: ProductTranslationFragment;
} }
export const fieldNames = {
description: "description",
name: "name",
seoDescription: "seoDescription",
seoTitle: "seoTitle"
};
const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({ const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({
activeField, activeField,
disabled, disabled,
@ -73,7 +69,7 @@ const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Product Name" defaultMessage: "Product Name"
}), }),
name: fieldNames.name, name: TranslationInputFieldName.name,
translation: data?.translation?.name || null, translation: data?.translation?.name || null,
type: "short" as "short", type: "short" as "short",
value: data?.product?.name value: data?.product?.name
@ -82,7 +78,7 @@ const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Description" defaultMessage: "Description"
}), }),
name: fieldNames.description, name: TranslationInputFieldName.description,
translation: data?.translation?.description || null, translation: data?.translation?.description || null,
type: "rich" as "rich", type: "rich" as "rich",
value: data?.product?.description value: data?.product?.description
@ -106,7 +102,7 @@ const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Title" defaultMessage: "Search Engine Title"
}), }),
name: fieldNames.seoTitle, name: TranslationInputFieldName.seoTitle,
translation: data?.translation?.seoTitle || null, translation: data?.translation?.seoTitle || null,
type: "short" as "short", type: "short" as "short",
value: data?.product?.seoTitle value: data?.product?.seoTitle
@ -115,7 +111,7 @@ const TranslationsProductsPage: React.FC<TranslationsProductsPageProps> = ({
displayName: intl.formatMessage({ displayName: intl.formatMessage({
defaultMessage: "Search Engine Description" defaultMessage: "Search Engine Description"
}), }),
name: fieldNames.seoDescription, name: TranslationInputFieldName.seoDescription,
translation: data?.translation?.seoDescription || null, translation: data?.translation?.seoDescription || null,
type: "long" as "long", type: "long" as "long",
value: data?.product?.seoDescription value: data?.product?.seoDescription

View file

@ -107,6 +107,7 @@ const updateCategoryTranslations = gql`
} }
} }
`; `;
export const TypedUpdateCategoryTranslations = TypedMutation< export const TypedUpdateCategoryTranslations = TypedMutation<
UpdateCategoryTranslations, UpdateCategoryTranslations,
UpdateCategoryTranslationsVariables UpdateCategoryTranslationsVariables
@ -143,6 +144,7 @@ const updateCollectionTranslations = gql`
} }
} }
`; `;
export const TypedUpdateCollectionTranslations = TypedMutation< export const TypedUpdateCollectionTranslations = TypedMutation<
UpdateCollectionTranslations, UpdateCollectionTranslations,
UpdateCollectionTranslationsVariables UpdateCollectionTranslationsVariables

View file

@ -14,3 +14,17 @@ export interface TranslationsEntitiesPageProps {
onLanguageChange: (lang: string) => void; onLanguageChange: (lang: string) => void;
onSubmit: (field: string, data: string | OutputData) => void; onSubmit: (field: string, data: string | OutputData) => void;
} }
export enum TranslationInputFieldName {
description = "description",
name = "name",
seoDescription = "seoDescription",
seoTitle = "seoTitle"
}
export enum PageTranslationInputFieldName {
content = "content",
title = "title",
seoDescription = "seoDescription",
seoTitle = "seoTitle"
}

View file

@ -20,7 +20,7 @@ export interface CategoryTranslationDetails_translation_CategoryTranslatableCont
export interface CategoryTranslationDetails_translation_CategoryTranslatableContent_translation { export interface CategoryTranslationDetails_translation_CategoryTranslatableContent_translation {
__typename: "CategoryTranslation"; __typename: "CategoryTranslation";
id: string; id: string;
description: any; description: any | null;
language: CategoryTranslationDetails_translation_CategoryTranslatableContent_translation_language; language: CategoryTranslationDetails_translation_CategoryTranslatableContent_translation_language;
name: string; name: string;
seoDescription: string | null; seoDescription: string | null;
@ -31,7 +31,7 @@ export interface CategoryTranslationDetails_translation_CategoryTranslatableCont
__typename: "Category"; __typename: "Category";
id: string; id: string;
name: string; name: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

View file

@ -20,7 +20,7 @@ export interface CategoryTranslations_translations_edges_node_CategoryTranslatab
export interface CategoryTranslations_translations_edges_node_CategoryTranslatableContent_translation { export interface CategoryTranslations_translations_edges_node_CategoryTranslatableContent_translation {
__typename: "CategoryTranslation"; __typename: "CategoryTranslation";
id: string; id: string;
description: any; description: any | null;
language: CategoryTranslations_translations_edges_node_CategoryTranslatableContent_translation_language; language: CategoryTranslations_translations_edges_node_CategoryTranslatableContent_translation_language;
name: string; name: string;
seoDescription: string | null; seoDescription: string | null;
@ -31,7 +31,7 @@ export interface CategoryTranslations_translations_edges_node_CategoryTranslatab
__typename: "Category"; __typename: "Category";
id: string; id: string;
name: string; name: string;
description: any; description: any | null;
seoDescription: string | null; seoDescription: string | null;
seoTitle: string | null; seoTitle: string | null;
} }

Some files were not shown because too many files have changed in this diff Show more