@shopgate/pwa-common-commerce 7.30.0-alpha.7 → 7.30.0-alpha.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/cart/action-creators/addCouponsToCart.js +9 -2
- package/cart/action-creators/addProductsToCart.js +9 -2
- package/cart/action-creators/deleteCouponsFromCart.js +9 -2
- package/cart/action-creators/deleteProductsFromCart.js +9 -2
- package/cart/action-creators/errorAddCouponsToCart.js +10 -2
- package/cart/action-creators/errorAddProductsToCart.js +10 -2
- package/cart/action-creators/errorCart.js +8 -2
- package/cart/action-creators/errorDeleteCouponsFromCart.js +10 -2
- package/cart/action-creators/errorDeleteProductsFromCart.js +10 -2
- package/cart/action-creators/errorUpdateProductsInCart.js +10 -2
- package/cart/action-creators/receiveCart.js +9 -2
- package/cart/action-creators/requestCart.js +8 -2
- package/cart/action-creators/setCartProductPendingCount.js +9 -2
- package/cart/action-creators/setCouponFieldError.js +9 -2
- package/cart/action-creators/setCouponFieldValue.js +9 -2
- package/cart/action-creators/setFulfillmentSlot.js +9 -2
- package/cart/action-creators/successAddCouponsToCart.js +10 -2
- package/cart/action-creators/successAddProductsToCart.js +8 -2
- package/cart/action-creators/successDeleteCouponsFromCart.js +8 -2
- package/cart/action-creators/successDeleteProductsFromCart.js +8 -2
- package/cart/action-creators/successUpdateProductsInCart.js +8 -2
- package/cart/action-creators/updateProductsInCart.js +9 -2
- package/cart/actions/addCouponsToCart.js +52 -8
- package/cart/actions/addProductsToCart.js +80 -11
- package/cart/actions/deleteCouponsFromCart.js +39 -6
- package/cart/actions/deleteProductsFromCart.js +38 -6
- package/cart/actions/fetchCart.js +52 -8
- package/cart/actions/updateProductsInCart.js +44 -6
- package/cart/constants/PipelineErrors.js +6 -1
- package/cart/constants/Pipelines.js +6 -1
- package/cart/constants/Portals.js +85 -1
- package/cart/constants/index.js +39 -2
- package/cart/helpers/config.js +47 -2
- package/cart/helpers/createPipelineErrorList.js +30 -4
- package/cart/helpers/fulfillmentSlots.js +37 -4
- package/cart/helpers/index.js +14 -3
- package/cart/helpers/quantity.js +23 -4
- package/cart/helpers/shipping.js +57 -2
- package/cart/helpers/tax.js +26 -2
- package/cart/index.js +25 -5
- package/cart/mock.js +130 -1
- package/cart/reducers/couponField.js +30 -2
- package/cart/reducers/data.js +98 -6
- package/cart/reducers/index.js +7 -1
- package/cart/selectors/index.js +181 -31
- package/cart/selectors/spec.js +189 -2
- package/cart/streams/index.js +176 -29
- package/cart/subscriptions/index.js +307 -30
- package/category/action-creators/errorCategory.js +10 -2
- package/category/action-creators/errorCategoryChildren.js +9 -2
- package/category/action-creators/errorRootCategories.js +8 -2
- package/category/action-creators/receiveCategory.js +12 -2
- package/category/action-creators/receiveCategoryChildren.js +10 -2
- package/category/action-creators/receiveRootCategories.js +9 -2
- package/category/action-creators/requestCategory.js +9 -2
- package/category/action-creators/requestCategoryChildren.js +9 -2
- package/category/action-creators/requestRootCategories.js +8 -2
- package/category/actions/fetchCategory.js +47 -5
- package/category/actions/fetchCategoryChildren.js +30 -2
- package/category/actions/fetchCategoryOrRootCategories.js +16 -2
- package/category/actions/fetchCategoryProducts.js +36 -2
- package/category/actions/fetchRootCategories.js +31 -2
- package/category/actions/getCategory.js +10 -2
- package/category/constants/Pipelines.js +3 -1
- package/category/constants/Portals.js +56 -3
- package/category/constants/index.js +17 -2
- package/category/helpers/index.js +27 -3
- package/category/index.js +19 -5
- package/category/mock.js +176 -1
- package/category/reducers/categoriesById.js +65 -3
- package/category/reducers/childrenByCategoryId.js +55 -4
- package/category/reducers/helpers/handleCategoryCollection.js +24 -3
- package/category/reducers/helpers/handleReceivedCategories.js +3 -1
- package/category/reducers/index.js +12 -2
- package/category/reducers/rootCategories.js +31 -2
- package/category/selectors/index.js +115 -16
- package/category/streams/index.js +82 -4
- package/category/subscriptions/index.js +96 -3
- package/checkout/action-creators/successCheckout.js +9 -2
- package/checkout/actions/fetchCheckoutUrl.js +28 -3
- package/checkout/constants/Pipelines.js +1 -1
- package/checkout/constants/index.js +3 -2
- package/checkout/index.js +11 -4
- package/checkout/selectors/index.js +7 -2
- package/checkout/streams/index.js +8 -2
- package/checkout/subscriptions/index.js +35 -6
- package/favorites/action-creators/index.js +206 -24
- package/favorites/actions/addFavorites.js +41 -3
- package/favorites/actions/addFavoritesList.js +27 -2
- package/favorites/actions/fetchFavoriteIds.js +49 -5
- package/favorites/actions/fetchFavorites.js +60 -5
- package/favorites/actions/fetchFavoritesList.js +47 -3
- package/favorites/actions/fetchFavoritesListsWithItems.js +32 -3
- package/favorites/actions/getFavorites.js +6 -2
- package/favorites/actions/removeFavorites.js +32 -3
- package/favorites/actions/removeFavoritesList.js +24 -2
- package/favorites/actions/toggleFavorites.js +68 -10
- package/favorites/actions/updateFavorites.js +39 -3
- package/favorites/actions/updateFavoritesList.js +26 -2
- package/favorites/constants/Pipelines.js +9 -1
- package/favorites/constants/Portals.js +32 -4
- package/favorites/constants/index.js +37 -5
- package/favorites/index.js +14 -4
- package/favorites/mock.js +89 -4
- package/favorites/reducers/index.js +7 -1
- package/favorites/reducers/lists.js +74 -2
- package/favorites/reducers/products.js +231 -24
- package/favorites/selectors/index.js +188 -24
- package/favorites/streams/index.js +135 -23
- package/favorites/streams/spec.js +517 -8
- package/favorites/subscriptions/index.js +260 -25
- package/favorites/subscriptions/spec.js +701 -28
- package/filter/action-creators/errorFilters.js +9 -2
- package/filter/action-creators/index.js +4 -1
- package/filter/action-creators/receiveFilters.js +10 -2
- package/filter/action-creators/requestFilters.js +9 -2
- package/filter/action-creators/updateFilters.js +8 -2
- package/filter/actions/fetchFilters.js +46 -3
- package/filter/actions/getFilters.js +6 -2
- package/filter/actions/helpers/buildFilterParams.js +34 -2
- package/filter/actions/helpers/buildRequestFilters.js +35 -2
- package/filter/actions/helpers/processFilters.js +10 -2
- package/filter/actions/helpers/processParams.js +26 -2
- package/filter/constants/Pipelines.js +1 -1
- package/filter/constants/Portals.js +39 -3
- package/filter/constants/index.js +8 -1
- package/filter/index.js +12 -4
- package/filter/reducers/helpers/enrichFilters.js +11 -3
- package/filter/reducers/index.js +5 -1
- package/filter/reducers/resultsByHash.js +43 -3
- package/filter/selectors/index.js +47 -6
- package/filter/streams/index.js +30 -1
- package/filter/subscriptions/index.js +34 -2
- package/market/constants/Portals.js +22 -4
- package/market/constants/index.js +2 -1
- package/market/helpers/showReturnPolicy.js +3 -1
- package/market/helpers/showTaxDisclaimer.js +3 -1
- package/market/index.js +6 -2
- package/orders/constants.js +2 -1
- package/package.json +3 -3
- package/product/action-creators/deleteProductsByIds.js +10 -2
- package/product/action-creators/errorProduct.js +10 -2
- package/product/action-creators/errorProductDescription.js +10 -2
- package/product/action-creators/errorProductImages.js +10 -2
- package/product/action-creators/errorProductMedia.js +10 -2
- package/product/action-creators/errorProductOptions.js +10 -2
- package/product/action-creators/errorProductProperties.js +10 -2
- package/product/action-creators/errorProductRelations.js +9 -2
- package/product/action-creators/errorProductShipping.js +10 -2
- package/product/action-creators/errorProductVariants.js +10 -2
- package/product/action-creators/errorProducts.js +9 -2
- package/product/action-creators/expireProductById.js +10 -2
- package/product/action-creators/expireProductData.js +11 -2
- package/product/action-creators/expireProductsByHash.js +9 -2
- package/product/action-creators/productNotAvailable.js +10 -2
- package/product/action-creators/provideProduct.js +9 -2
- package/product/action-creators/receiveProduct.js +10 -2
- package/product/action-creators/receiveProductCached.js +9 -2
- package/product/action-creators/receiveProductDescription.js +10 -2
- package/product/action-creators/receiveProductImages.js +10 -2
- package/product/action-creators/receiveProductMedia.js +10 -2
- package/product/action-creators/receiveProductOptions.js +10 -2
- package/product/action-creators/receiveProductProperties.js +10 -2
- package/product/action-creators/receiveProductRelations.js +12 -2
- package/product/action-creators/receiveProductShipping.js +10 -2
- package/product/action-creators/receiveProductVariants.js +10 -2
- package/product/action-creators/receiveProducts.js +16 -2
- package/product/action-creators/receiveProductsCached.js +9 -2
- package/product/action-creators/refreshExpiredPDPData.js +8 -2
- package/product/action-creators/requestProduct.js +10 -2
- package/product/action-creators/requestProductDescription.js +9 -2
- package/product/action-creators/requestProductImages.js +9 -2
- package/product/action-creators/requestProductMedia.js +9 -2
- package/product/action-creators/requestProductOptions.js +9 -2
- package/product/action-creators/requestProductProperties.js +9 -2
- package/product/action-creators/requestProductRelations.js +10 -2
- package/product/action-creators/requestProductShipping.js +9 -2
- package/product/action-creators/requestProductVariants.js +9 -2
- package/product/action-creators/requestProducts.js +9 -2
- package/product/action-creators/setProductId.js +9 -2
- package/product/action-creators/setProductQuantity.js +9 -2
- package/product/action-creators/setProductVariantId.js +9 -2
- package/product/actions/changeSortOrder.js +21 -2
- package/product/actions/fetchHighlightProducts.js +18 -2
- package/product/actions/fetchLiveshoppingProducts.js +14 -2
- package/product/actions/fetchProduct.js +52 -3
- package/product/actions/fetchProductDescription.js +30 -2
- package/product/actions/fetchProductImages.js +31 -2
- package/product/actions/fetchProductMedia.js +35 -2
- package/product/actions/fetchProductOptions.js +31 -2
- package/product/actions/fetchProductProperties.js +30 -2
- package/product/actions/fetchProductRelations.js +63 -2
- package/product/actions/fetchProductShipping.js +31 -2
- package/product/actions/fetchProductVariants.js +31 -2
- package/product/actions/fetchProducts.js +189 -17
- package/product/actions/fetchProductsById.js +68 -8
- package/product/actions/fetchProductsByQuery.js +102 -18
- package/product/actions/getHighlightProducts.js +6 -2
- package/product/actions/getLiveshoppingProducts.js +6 -2
- package/product/actions/getProduct.js +6 -2
- package/product/actions/getProductDescription.js +6 -2
- package/product/actions/getProductImages.js +6 -2
- package/product/actions/getProductOptions.js +6 -2
- package/product/actions/getProductProperties.js +6 -2
- package/product/actions/getProductRelations.js +6 -2
- package/product/actions/getProductShipping.js +6 -2
- package/product/actions/getProductVariants.js +6 -2
- package/product/actions/getProducts.js +6 -2
- package/product/actions/getProductsById.js +6 -2
- package/product/actions/getProductsByQuery.js +6 -2
- package/product/actions/processProductFlags.js +35 -3
- package/product/actions/updateMetadata.js +17 -2
- package/product/collections/ProductImageFormats.js +48 -8
- package/product/collections/index.js +1 -1
- package/product/constants/Pipelines.js +12 -1
- package/product/constants/Portals.js +200 -33
- package/product/constants/index.js +90 -18
- package/product/helpers/index.js +61 -8
- package/product/index.js +36 -6
- package/product/mock.js +1002 -2
- package/product/reducers/descriptionsByProductId.js +54 -5
- package/product/reducers/helpers/formatOptions.js +17 -2
- package/product/reducers/helpers/handleProductCollection.js +19 -2
- package/product/reducers/imagesByProductId.js +51 -4
- package/product/reducers/index.js +23 -1
- package/product/reducers/mediaByProductId.js +55 -3
- package/product/reducers/optionsByProductId.js +41 -2
- package/product/reducers/productRelationsByHash.js +43 -2
- package/product/reducers/productsById.js +122 -7
- package/product/reducers/propertiesByProductId.js +48 -2
- package/product/reducers/resultsByHash.js +125 -9
- package/product/reducers/shippingByProductId.js +37 -2
- package/product/reducers/variantsByProductId.js +56 -2
- package/product/selectors/options.js +90 -13
- package/product/selectors/page.js +62 -13
- package/product/selectors/price.js +81 -18
- package/product/selectors/product.js +549 -59
- package/product/selectors/product.mock.js +327 -12
- package/product/selectors/relations.js +35 -5
- package/product/selectors/variants.js +91 -15
- package/product/streams/index.js +167 -13
- package/product/subscriptions/index.js +210 -4
- package/reviews/action-creators/errorProductReviews.js +9 -2
- package/reviews/action-creators/errorReviews.js +9 -2
- package/reviews/action-creators/errorSubmitReview.js +9 -2
- package/reviews/action-creators/errorUserReview.js +9 -2
- package/reviews/action-creators/flushUserReview.js +8 -2
- package/reviews/action-creators/receiveProductReviews.js +11 -2
- package/reviews/action-creators/receiveReviews.js +12 -2
- package/reviews/action-creators/receiveSubmitReview.js +9 -2
- package/reviews/action-creators/receiveUserReview.js +10 -2
- package/reviews/action-creators/requestProductReviews.js +10 -2
- package/reviews/action-creators/requestReviews.js +9 -2
- package/reviews/action-creators/requestSubmitReview.js +9 -2
- package/reviews/action-creators/requestUserReview.js +9 -2
- package/reviews/action-creators/resetSubmittedReview.js +9 -2
- package/reviews/action-creators/spec.js +40 -1
- package/reviews/actions/fetchProductReviews.js +37 -2
- package/reviews/actions/fetchReviews.js +38 -2
- package/reviews/actions/fetchUserReview.js +31 -2
- package/reviews/actions/flushUserReview.js +5 -1
- package/reviews/actions/getProductReviews.js +6 -2
- package/reviews/actions/getUserReview.js +6 -2
- package/reviews/actions/spec.js +241 -4
- package/reviews/actions/submitReview.js +63 -3
- package/reviews/constants/Pipelines.js +4 -1
- package/reviews/constants/Portals.js +4 -1
- package/reviews/constants/index.js +26 -7
- package/reviews/index.js +15 -4
- package/reviews/mock.js +172 -11
- package/reviews/reducers/index.js +11 -1
- package/reviews/reducers/mock.js +14 -2
- package/reviews/reducers/reviewsByHash.js +52 -6
- package/reviews/reducers/reviewsById.js +27 -2
- package/reviews/reducers/reviewsByProductId.js +47 -2
- package/reviews/reducers/spec.js +211 -2
- package/reviews/reducers/userReviewsByProductId.js +68 -2
- package/reviews/selectors/index.js +123 -19
- package/reviews/selectors/mock.js +100 -1
- package/reviews/selectors/spec.js +100 -1
- package/reviews/streams/index.js +37 -5
- package/reviews/streams/spec.js +25 -1
- package/reviews/subscriptions/index.js +27 -2
- package/scanner/action-creators/errorHandleScanner.js +11 -2
- package/scanner/action-creators/scannerFinished.js +11 -2
- package/scanner/action-creators/startScanner.js +8 -2
- package/scanner/action-creators/successHandleScanner.js +11 -2
- package/scanner/actions/handleBarCode.js +22 -2
- package/scanner/actions/handleNoResults.js +23 -2
- package/scanner/actions/handleQrCode.js +116 -6
- package/scanner/actions/handleSearch.js +33 -2
- package/scanner/constants/Portals.js +22 -1
- package/scanner/constants/index.js +17 -1
- package/scanner/helpers/index.js +115 -5
- package/scanner/index.js +19 -5
- package/scanner/streams/index.js +36 -1
- package/scanner/subscriptions/index.js +78 -8
- package/search/action-creators/errorSearchResults.js +10 -2
- package/search/action-creators/receiveSearchResults.js +11 -2
- package/search/action-creators/receiveSearchSuggestions.js +10 -2
- package/search/action-creators/requestSearchResults.js +10 -2
- package/search/action-creators/requestSearchSuggestions.js +9 -2
- package/search/actions/fetchSearchResults.js +66 -8
- package/search/actions/fetchSearchSuggestions.js +36 -2
- package/search/constants/Pipelines.js +1 -1
- package/search/constants/Portals.js +9 -2
- package/search/constants/index.js +10 -2
- package/search/helpers/index.js +5 -2
- package/search/helpers/removeHighlightingPlaceholders.js +4 -1
- package/search/helpers/spec.js +19 -1
- package/search/index.js +17 -5
- package/search/reducers/index.js +38 -2
- package/search/selectors/index.js +23 -4
- package/search/streams/index.js +51 -3
- package/search/subscriptions/index.js +132 -5
|
@@ -1,5 +1,12 @@
|
|
|
1
|
-
import{RESET_SUBMIT_REVIEW}from"../constants"
|
|
1
|
+
import { RESET_SUBMIT_REVIEW } from "../constants";
|
|
2
|
+
|
|
3
|
+
/**
|
|
2
4
|
* Dispatches the RESET_SUBMIT_REVIEW action.
|
|
3
5
|
* @param {Object} review Review data to which the state should reset to.
|
|
4
6
|
* @returns {Object} The RESET_SUBMIT_REVIEW action.
|
|
5
|
-
*/
|
|
7
|
+
*/
|
|
8
|
+
const resetSubmittedReview = review => ({
|
|
9
|
+
type: RESET_SUBMIT_REVIEW,
|
|
10
|
+
review
|
|
11
|
+
});
|
|
12
|
+
export default resetSubmittedReview;
|
|
@@ -1 +1,40 @@
|
|
|
1
|
-
import errorReviews from"./errorReviews";
|
|
1
|
+
import errorReviews from "./errorReviews";
|
|
2
|
+
import receiveReviews from "./receiveReviews";
|
|
3
|
+
import requestReviews from "./requestReviews";
|
|
4
|
+
import { ERROR_REVIEWS, RECEIVE_REVIEWS, REQUEST_REVIEWS } from "../constants/index";
|
|
5
|
+
const hash = 'foo';
|
|
6
|
+
const productId = '1';
|
|
7
|
+
describe('Reviews action-creators', () => {
|
|
8
|
+
describe('errorReviews', () => {
|
|
9
|
+
it('should return correct action', () => {
|
|
10
|
+
const action = errorReviews(hash);
|
|
11
|
+
expect(action).toEqual({
|
|
12
|
+
type: ERROR_REVIEWS,
|
|
13
|
+
hash
|
|
14
|
+
});
|
|
15
|
+
});
|
|
16
|
+
});
|
|
17
|
+
describe('receiveReviews', () => {
|
|
18
|
+
it('should return correct action', () => {
|
|
19
|
+
const reviews = [];
|
|
20
|
+
const totalReviewCount = 20;
|
|
21
|
+
const action = receiveReviews(hash, productId, reviews, totalReviewCount);
|
|
22
|
+
expect(action).toEqual({
|
|
23
|
+
type: RECEIVE_REVIEWS,
|
|
24
|
+
hash,
|
|
25
|
+
productId,
|
|
26
|
+
reviews,
|
|
27
|
+
totalReviewCount
|
|
28
|
+
});
|
|
29
|
+
});
|
|
30
|
+
});
|
|
31
|
+
describe('requestReviews', () => {
|
|
32
|
+
it('should return correct action', () => {
|
|
33
|
+
const action = requestReviews(hash);
|
|
34
|
+
expect(action).toEqual({
|
|
35
|
+
type: REQUEST_REVIEWS,
|
|
36
|
+
hash
|
|
37
|
+
});
|
|
38
|
+
});
|
|
39
|
+
});
|
|
40
|
+
});
|
|
@@ -1,7 +1,42 @@
|
|
|
1
|
-
import PipelineRequest from'@shopgate/pwa-core/classes/PipelineRequest';
|
|
1
|
+
import PipelineRequest from '@shopgate/pwa-core/classes/PipelineRequest';
|
|
2
|
+
import { shouldFetchData, mutable } from '@shopgate/pwa-common/helpers/redux';
|
|
3
|
+
import { SORT_RELEVANCE } from '@shopgate/pwa-common/constants/DisplayOptions';
|
|
4
|
+
import { SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS } from "../constants/Pipelines";
|
|
5
|
+
import { REVIEW_PREVIEW_COUNT } from "../constants";
|
|
6
|
+
import requestProductReviews from "../action-creators/requestProductReviews";
|
|
7
|
+
import receiveProductReviews from "../action-creators/receiveProductReviews";
|
|
8
|
+
import errorProductReviews from "../action-creators/errorProductReviews";
|
|
9
|
+
|
|
10
|
+
/**
|
|
2
11
|
* Request product reviews for a product from server.
|
|
3
12
|
* @param {string} productId The product ID
|
|
4
13
|
* @param {number} [limit=REVIEW_PREVIEW_COUNT] The maximum number of reviews to fetch
|
|
5
14
|
* @param {('relevance'|'dateDesc'|'dateAsc'|'rateDesc'|'rateAsc')} [sort=SORT_RELEVANCE] Sorting.
|
|
6
15
|
* @returns {Promise} The dispatched action.
|
|
7
|
-
*/
|
|
16
|
+
*/
|
|
17
|
+
function fetchProductReviews(productId, limit = REVIEW_PREVIEW_COUNT, sort = SORT_RELEVANCE) {
|
|
18
|
+
return (dispatch, getState) => {
|
|
19
|
+
const data = getState().reviews.reviewsByProductId[productId];
|
|
20
|
+
if (!shouldFetchData(data)) {
|
|
21
|
+
return Promise.resolve(null);
|
|
22
|
+
}
|
|
23
|
+
dispatch(requestProductReviews(productId, limit));
|
|
24
|
+
const request = new PipelineRequest(SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS).setInput({
|
|
25
|
+
productId,
|
|
26
|
+
limit,
|
|
27
|
+
sort
|
|
28
|
+
}).dispatch();
|
|
29
|
+
request.then(({
|
|
30
|
+
reviews,
|
|
31
|
+
totalReviewCount
|
|
32
|
+
}) => {
|
|
33
|
+
dispatch(receiveProductReviews(productId, reviews, totalReviewCount));
|
|
34
|
+
}).catch(() => {
|
|
35
|
+
dispatch(errorProductReviews(productId));
|
|
36
|
+
});
|
|
37
|
+
return request;
|
|
38
|
+
};
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
/** @mixes {MutableFunction} */
|
|
42
|
+
export default mutable(fetchProductReviews);
|
|
@@ -1,8 +1,44 @@
|
|
|
1
|
-
import PipelineRequest from'@shopgate/pwa-core/classes/PipelineRequest';
|
|
1
|
+
import PipelineRequest from '@shopgate/pwa-core/classes/PipelineRequest';
|
|
2
|
+
import { SORT_DATE_DESC } from '@shopgate/pwa-common/constants/DisplayOptions';
|
|
3
|
+
import { generateResultHash, mutable } from '@shopgate/pwa-common/helpers/redux';
|
|
4
|
+
import { REVIEW_PREVIEW_COUNT } from "../constants";
|
|
5
|
+
import { SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS } from "../constants/Pipelines";
|
|
6
|
+
import requestProductReviewsList from "../action-creators/requestReviews";
|
|
7
|
+
import receiveProductReviewsList from "../action-creators/receiveReviews";
|
|
8
|
+
import errorProductReviewsList from "../action-creators/errorReviews";
|
|
9
|
+
|
|
10
|
+
/**
|
|
2
11
|
* Request product reviews for a product by the given id.
|
|
3
12
|
* @param {string} productId The product ID.
|
|
4
13
|
* @param {number} [limit=REVIEW_PREVIEW_COUNT] The maximum number of reviews to fetch.
|
|
5
14
|
* @param {number} [offset=0] The list offset (defaults to 0).
|
|
6
15
|
* @param {('relevance'|'dateDesc'|'dateAsc'|'rateDesc'|'rateAsc')} sort Sorting.
|
|
7
16
|
* @returns {Function} The dispatched action.
|
|
8
|
-
*/
|
|
17
|
+
*/
|
|
18
|
+
function fetchReviews(productId, limit = REVIEW_PREVIEW_COUNT, offset = 0, sort = SORT_DATE_DESC) {
|
|
19
|
+
return dispatch => {
|
|
20
|
+
const hash = generateResultHash({
|
|
21
|
+
pipeline: SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS,
|
|
22
|
+
productId
|
|
23
|
+
}, false);
|
|
24
|
+
dispatch(requestProductReviewsList(hash));
|
|
25
|
+
const request = new PipelineRequest(SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS).setInput({
|
|
26
|
+
productId,
|
|
27
|
+
limit,
|
|
28
|
+
offset,
|
|
29
|
+
sort
|
|
30
|
+
}).dispatch();
|
|
31
|
+
request.then(({
|
|
32
|
+
reviews,
|
|
33
|
+
totalReviewCount
|
|
34
|
+
}) => {
|
|
35
|
+
dispatch(receiveProductReviewsList(hash, productId, reviews, totalReviewCount));
|
|
36
|
+
}).catch(() => {
|
|
37
|
+
dispatch(errorProductReviewsList(hash));
|
|
38
|
+
});
|
|
39
|
+
return request;
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
/** @mixes {MutableFunction} */
|
|
44
|
+
export default mutable(fetchReviews);
|
|
@@ -1,5 +1,34 @@
|
|
|
1
|
-
import PipelineRequest from'@shopgate/pwa-core/classes/PipelineRequest';
|
|
1
|
+
import PipelineRequest from '@shopgate/pwa-core/classes/PipelineRequest';
|
|
2
|
+
import { EUNKNOWN, EACCESS } from '@shopgate/pwa-core/constants/Pipeline';
|
|
3
|
+
import { shouldFetchData, mutable } from '@shopgate/pwa-common/helpers/redux';
|
|
4
|
+
import { SHOPGATE_USER_GET_REVIEW } from "../constants/Pipelines";
|
|
5
|
+
import requestUserReview from "../action-creators/requestUserReview";
|
|
6
|
+
import receiveUserReview from "../action-creators/receiveUserReview";
|
|
7
|
+
import errorUserReview from "../action-creators/errorUserReview";
|
|
8
|
+
|
|
9
|
+
/**
|
|
2
10
|
* Request a user review for a product from server.
|
|
3
11
|
* @param {string} productId The product ID.
|
|
4
12
|
* @returns {Function} The dispatched action.
|
|
5
|
-
*/
|
|
13
|
+
*/
|
|
14
|
+
function fetchUserReview(productId) {
|
|
15
|
+
return (dispatch, getState) => {
|
|
16
|
+
const data = getState().reviews.userReviewsByProductId[productId];
|
|
17
|
+
if (!shouldFetchData(data)) {
|
|
18
|
+
return Promise.resolve(null);
|
|
19
|
+
}
|
|
20
|
+
dispatch(requestUserReview(productId));
|
|
21
|
+
const request = new PipelineRequest(SHOPGATE_USER_GET_REVIEW).setErrorBlacklist([EUNKNOWN, EACCESS]).setInput({
|
|
22
|
+
productId
|
|
23
|
+
}).dispatch();
|
|
24
|
+
request.then(result => {
|
|
25
|
+
dispatch(receiveUserReview(productId, result));
|
|
26
|
+
}).catch(() => {
|
|
27
|
+
dispatch(errorUserReview(productId));
|
|
28
|
+
});
|
|
29
|
+
return request;
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
/** @mixes {MutableFunction} */
|
|
34
|
+
export default mutable(fetchUserReview);
|
|
@@ -1 +1,5 @@
|
|
|
1
|
-
import{mutable}from'@shopgate/pwa-common/helpers/redux';
|
|
1
|
+
import { mutable } from '@shopgate/pwa-common/helpers/redux';
|
|
2
|
+
import flushUserReviewAction from "../action-creators/flushUserReview";
|
|
3
|
+
|
|
4
|
+
/** @mixes {MutableFunction} */
|
|
5
|
+
export default mutable(() => dispatch => dispatch(flushUserReviewAction()));
|
|
@@ -1,8 +1,12 @@
|
|
|
1
|
-
import fetchProductReviews from"./fetchProductReviews"
|
|
1
|
+
import fetchProductReviews from "./fetchProductReviews";
|
|
2
|
+
|
|
3
|
+
/**
|
|
2
4
|
* Request product reviews for a product from server.
|
|
3
5
|
* @param {string} productId The product ID
|
|
4
6
|
* @param {number} [limit=REVIEW_PREVIEW_COUNT] The maximum number of reviews to fetch
|
|
5
7
|
* @param {('relevance'|'dateDesc'|'dateAsc'|'rateDesc'|'rateAsc')} [sort=SORT_RELEVANCE] Sorting.
|
|
6
8
|
* @returns {Promise} The dispatched action.
|
|
7
9
|
* @deprecated
|
|
8
|
-
*/
|
|
10
|
+
*/
|
|
11
|
+
const getProductReviews = fetchProductReviews;
|
|
12
|
+
export default getProductReviews;
|
|
@@ -1,6 +1,10 @@
|
|
|
1
|
-
import fetchUserReview from"./fetchUserReview"
|
|
1
|
+
import fetchUserReview from "./fetchUserReview";
|
|
2
|
+
|
|
3
|
+
/**
|
|
2
4
|
* Request a user review for a product from server.
|
|
3
5
|
* @param {string} productId The product ID.
|
|
4
6
|
* @returns {Promise} The dispatched action.
|
|
5
7
|
* @deprecated
|
|
6
|
-
*/
|
|
8
|
+
*/
|
|
9
|
+
const getUserReview = fetchUserReview;
|
|
10
|
+
export default getUserReview;
|
package/reviews/actions/spec.js
CHANGED
|
@@ -1,18 +1,255 @@
|
|
|
1
|
-
import
|
|
1
|
+
import { logger } from '@shopgate/pwa-core/helpers';
|
|
2
|
+
import { mockedPipelineRequestFactory } from '@shopgate/pwa-core/classes/PipelineRequest/mock';
|
|
3
|
+
import { EUNKNOWN, EACCESS } from '@shopgate/pwa-core/constants/Pipeline';
|
|
4
|
+
import fetchReviews from "./fetchReviews";
|
|
5
|
+
import fetchProductReviews from "./fetchProductReviews";
|
|
6
|
+
import fetchUserReview from "./fetchUserReview";
|
|
7
|
+
import submitReview from "./submitReview";
|
|
8
|
+
import { finalState } from "../selectors/mock";
|
|
9
|
+
import * as pipelines from "../constants/Pipelines";
|
|
10
|
+
let mockedResolver;
|
|
11
|
+
jest.mock('@shopgate/pwa-core/classes/PipelineRequest', () => mockedPipelineRequestFactory((mockInstance, resolve, reject) => {
|
|
12
|
+
mockedResolver(mockInstance, resolve, reject);
|
|
13
|
+
}));
|
|
14
|
+
jest.mock('@shopgate/pwa-core/helpers', () => ({
|
|
15
|
+
logger: {
|
|
16
|
+
error: jest.fn()
|
|
17
|
+
}
|
|
18
|
+
}));
|
|
19
|
+
describe.skip('Reviews actions', () => {
|
|
20
|
+
describe('fetchReviews', () => {
|
|
21
|
+
beforeEach(() => {
|
|
22
|
+
jest.clearAllMocks();
|
|
23
|
+
});
|
|
24
|
+
it('should resolve and call appropriate actions', async done => {
|
|
25
|
+
mockedResolver = (mockInstance, resolve) => {
|
|
26
|
+
resolve({
|
|
27
|
+
reviews: [],
|
|
28
|
+
mockInstance
|
|
29
|
+
});
|
|
30
|
+
};
|
|
31
|
+
const mockedDispatch = jest.fn();
|
|
32
|
+
try {
|
|
33
|
+
const result = await fetchReviews('foo', 2, 1)(mockedDispatch);
|
|
34
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS);
|
|
35
|
+
expect(result.mockInstance.input).toEqual({
|
|
36
|
+
productId: 'foo',
|
|
37
|
+
limit: 2,
|
|
38
|
+
offset: 1,
|
|
39
|
+
sort: 'dateDesc'
|
|
40
|
+
});
|
|
41
|
+
expect(logger.error).toHaveBeenCalledTimes(0);
|
|
42
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
43
|
+
done();
|
|
44
|
+
} catch (err) {
|
|
45
|
+
done(err);
|
|
46
|
+
}
|
|
47
|
+
});
|
|
48
|
+
it('should fail and call appropriate actions', async done => {
|
|
49
|
+
mockedResolver = (mockInstance, resolve, reject) => {
|
|
50
|
+
reject({
|
|
51
|
+
mockInstance
|
|
52
|
+
});
|
|
53
|
+
};
|
|
54
|
+
const mockedDispatch = jest.fn();
|
|
55
|
+
let result;
|
|
56
|
+
try {
|
|
57
|
+
result = await fetchReviews('foo', 2, 1)(mockedDispatch);
|
|
58
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS);
|
|
59
|
+
expect(result.mockInstance.input).toEqual({
|
|
60
|
+
productId: 'foo',
|
|
61
|
+
limit: 2,
|
|
62
|
+
offset: 1,
|
|
63
|
+
sort: 'dateDesc'
|
|
64
|
+
});
|
|
65
|
+
expect(logger.error).toHaveBeenCalledTimes(1);
|
|
66
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
67
|
+
done();
|
|
68
|
+
} catch (err) {
|
|
69
|
+
done(err);
|
|
70
|
+
}
|
|
71
|
+
});
|
|
72
|
+
});
|
|
73
|
+
describe('fetchProductReviews', () => {
|
|
74
|
+
/**
|
|
2
75
|
* Assertion helper function
|
|
3
76
|
* @param {string} variant ('then' or 'catch')
|
|
4
77
|
* @param {Function} done Async test case done callback function.
|
|
5
78
|
* @param {Object} state React state.
|
|
6
|
-
*/
|
|
79
|
+
*/
|
|
80
|
+
const testFetchProductReviews = (variant, done, state) => {
|
|
81
|
+
const mockedDispatch = jest.fn();
|
|
82
|
+
const promise = fetchProductReviews('foo', 10, 'invalidSort')(mockedDispatch, () => state);
|
|
83
|
+
setTimeout(() => {
|
|
84
|
+
promise[variant](result => {
|
|
85
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS);
|
|
86
|
+
expect(result.mockInstance.input).toEqual({
|
|
87
|
+
productId: 'foo',
|
|
88
|
+
limit: 10,
|
|
89
|
+
sort: 'invalidSort'
|
|
90
|
+
});
|
|
91
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
92
|
+
done();
|
|
93
|
+
});
|
|
94
|
+
}, 0);
|
|
95
|
+
};
|
|
96
|
+
it('should resolve and call appropriate actions', async done => {
|
|
97
|
+
mockedResolver = (mockInstance, resolve) => {
|
|
98
|
+
resolve({
|
|
99
|
+
reviews: [],
|
|
100
|
+
mockInstance
|
|
101
|
+
});
|
|
102
|
+
};
|
|
103
|
+
const mockedDispatch = jest.fn();
|
|
104
|
+
try {
|
|
105
|
+
const result = await fetchProductReviews('foo', 10, 'invalidSort')(mockedDispatch, () => finalState);
|
|
106
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS);
|
|
107
|
+
expect(result.mockInstance.input).toEqual({
|
|
108
|
+
productId: 'foo',
|
|
109
|
+
limit: 10,
|
|
110
|
+
sort: 'invalidSort'
|
|
111
|
+
});
|
|
112
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
113
|
+
done();
|
|
114
|
+
} catch (err) {
|
|
115
|
+
done(err);
|
|
116
|
+
}
|
|
117
|
+
});
|
|
118
|
+
it('should reject and call appropriate actions', async done => {
|
|
119
|
+
mockedResolver = (mockInstance, resolve, reject) => {
|
|
120
|
+
reject({
|
|
121
|
+
mockInstance
|
|
122
|
+
});
|
|
123
|
+
};
|
|
124
|
+
const mockedDispatch = jest.fn();
|
|
125
|
+
let result;
|
|
126
|
+
try {
|
|
127
|
+
result = await fetchProductReviews('foo', 10, 'invalidSort')(mockedDispatch, () => finalState);
|
|
128
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS);
|
|
129
|
+
expect(result.mockInstance.input).toEqual({
|
|
130
|
+
productId: 'foo',
|
|
131
|
+
limit: 10,
|
|
132
|
+
sort: 'invalidSort'
|
|
133
|
+
});
|
|
134
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
135
|
+
done();
|
|
136
|
+
} catch (err) {
|
|
137
|
+
done(err);
|
|
138
|
+
}
|
|
139
|
+
testFetchProductReviews('catch', done, finalState);
|
|
140
|
+
});
|
|
141
|
+
});
|
|
142
|
+
describe('fetchUserReview', () => {
|
|
143
|
+
/**
|
|
7
144
|
* Assertion helper function
|
|
8
145
|
* @param {string} variant ('then' or 'catch')
|
|
9
146
|
* @param {Function} done Async test case done callback function.
|
|
10
147
|
* @param {Object} state React state.
|
|
11
|
-
*/
|
|
148
|
+
*/
|
|
149
|
+
const testFetchUserReview = (variant, done, state) => {
|
|
150
|
+
const mockedDispatch = jest.fn();
|
|
151
|
+
const promise = fetchUserReview('foo')(mockedDispatch, () => state);
|
|
152
|
+
setTimeout(() => {
|
|
153
|
+
promise[variant](result => {
|
|
154
|
+
expect(result.mockInstance.name).toBe(pipelines.SHOPGATE_USER_GET_REVIEW);
|
|
155
|
+
expect(result.mockInstance.errorBlacklist).toEqual([EUNKNOWN, EACCESS]);
|
|
156
|
+
expect(result.mockInstance.input).toEqual({
|
|
157
|
+
productId: 'foo'
|
|
158
|
+
});
|
|
159
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(2);
|
|
160
|
+
done();
|
|
161
|
+
});
|
|
162
|
+
}, 0);
|
|
163
|
+
};
|
|
164
|
+
it('should resolve and call appropriate actions', done => {
|
|
165
|
+
mockedResolver = (mockInstance, resolve) => {
|
|
166
|
+
resolve({
|
|
167
|
+
reviews: [],
|
|
168
|
+
mockInstance
|
|
169
|
+
});
|
|
170
|
+
};
|
|
171
|
+
testFetchUserReview('then', done, finalState);
|
|
172
|
+
});
|
|
173
|
+
it('should reject and call appropriate actions', done => {
|
|
174
|
+
mockedResolver = (mockInstance, resolve, reject) => {
|
|
175
|
+
reject({
|
|
176
|
+
mockInstance
|
|
177
|
+
});
|
|
178
|
+
};
|
|
179
|
+
testFetchUserReview('catch', done, finalState);
|
|
180
|
+
});
|
|
181
|
+
});
|
|
182
|
+
describe('submitReview', () => {
|
|
183
|
+
const testReviewInput = {
|
|
184
|
+
productId: 'foo',
|
|
185
|
+
rate: 10,
|
|
186
|
+
title: ' Title ',
|
|
187
|
+
author: ' Author ',
|
|
188
|
+
review: 'RRRR '
|
|
189
|
+
};
|
|
190
|
+
const testReviewSanitized = {
|
|
191
|
+
productId: 'foo',
|
|
192
|
+
rate: 10,
|
|
193
|
+
title: 'Title',
|
|
194
|
+
author: 'Author',
|
|
195
|
+
review: 'RRRR'
|
|
196
|
+
};
|
|
197
|
+
/**
|
|
12
198
|
* Assertion helper function
|
|
13
199
|
* @param {string} variant ('then' or 'catch')
|
|
14
200
|
* @param {Object} review Review.
|
|
15
201
|
* @param {boolean} update Update.
|
|
16
202
|
* @param {Object} state React state.
|
|
17
203
|
* @param {Function} done Async test case done callback function.
|
|
18
|
-
*/
|
|
204
|
+
*/
|
|
205
|
+
const testSubmitReview = (variant, review, update, state, done) => {
|
|
206
|
+
const expectedDispatches = variant === 'then' ? 3 : 2;
|
|
207
|
+
const mockedDispatch = jest.fn();
|
|
208
|
+
const promise = submitReview(review, update)(mockedDispatch, () => state);
|
|
209
|
+
setTimeout(() => {
|
|
210
|
+
promise[variant](result => {
|
|
211
|
+
expect(result.mockInstance.name).toBe(update ? pipelines.SHOPGATE_CATALOG_UPDATE_PRODUCT_REVIEW : pipelines.SHOPGATE_CATALOG_ADD_PRODUCT_REVIEW);
|
|
212
|
+
expect(result.mockInstance.input).toEqual(testReviewSanitized);
|
|
213
|
+
expect(mockedDispatch).toHaveBeenCalledTimes(expectedDispatches);
|
|
214
|
+
done();
|
|
215
|
+
});
|
|
216
|
+
}, 0);
|
|
217
|
+
};
|
|
218
|
+
it('should resolve and call appropriate actions on update', done => {
|
|
219
|
+
mockedResolver = (mockInstance, resolve) => {
|
|
220
|
+
resolve({
|
|
221
|
+
reviews: [],
|
|
222
|
+
mockInstance
|
|
223
|
+
});
|
|
224
|
+
};
|
|
225
|
+
testSubmitReview('then', testReviewInput, true, finalState, done);
|
|
226
|
+
});
|
|
227
|
+
it('should resolve and call appropriate actions on add', done => {
|
|
228
|
+
mockedResolver = (mockInstance, resolve) => {
|
|
229
|
+
resolve({
|
|
230
|
+
reviews: [],
|
|
231
|
+
mockInstance
|
|
232
|
+
});
|
|
233
|
+
};
|
|
234
|
+
testSubmitReview('then', testReviewInput, false, finalState, done);
|
|
235
|
+
});
|
|
236
|
+
it('should reject and call appropriate actions on add', done => {
|
|
237
|
+
mockedResolver = (mockInstance, resolve, reject) => {
|
|
238
|
+
reject({
|
|
239
|
+
reviews: [],
|
|
240
|
+
mockInstance
|
|
241
|
+
});
|
|
242
|
+
};
|
|
243
|
+
testSubmitReview('catch', testReviewInput, false, finalState, done);
|
|
244
|
+
});
|
|
245
|
+
it('should reject and call appropriate actions on update', done => {
|
|
246
|
+
mockedResolver = (mockInstance, resolve, reject) => {
|
|
247
|
+
reject({
|
|
248
|
+
reviews: [],
|
|
249
|
+
mockInstance
|
|
250
|
+
});
|
|
251
|
+
};
|
|
252
|
+
testSubmitReview('catch', testReviewInput, true, finalState, done);
|
|
253
|
+
});
|
|
254
|
+
});
|
|
255
|
+
});
|
|
@@ -1,7 +1,67 @@
|
|
|
1
|
-
import PipelineRequest from'@shopgate/pwa-core/classes/PipelineRequest';
|
|
1
|
+
import PipelineRequest from '@shopgate/pwa-core/classes/PipelineRequest';
|
|
2
|
+
import { EEXIST } from '@shopgate/pwa-core/constants/Pipeline';
|
|
3
|
+
import showModal from '@shopgate/pwa-common/actions/modal/showModal';
|
|
4
|
+
import { mutable } from '@shopgate/pwa-common/helpers/redux';
|
|
5
|
+
import { SHOPGATE_CATALOG_UPDATE_PRODUCT_REVIEW, SHOPGATE_CATALOG_ADD_PRODUCT_REVIEW } from "../constants/Pipelines";
|
|
6
|
+
import requestSubmitReview from "../action-creators/requestSubmitReview";
|
|
7
|
+
import receiveSubmitReview from "../action-creators/receiveSubmitReview";
|
|
8
|
+
import errorSubmitReview from "../action-creators/errorSubmitReview";
|
|
9
|
+
import resetSubmittedReview from "../action-creators/resetSubmittedReview";
|
|
10
|
+
import { getUserReviewForProduct } from "../selectors/index";
|
|
11
|
+
import fetchProduct from "../../product/actions/fetchProduct";
|
|
12
|
+
|
|
13
|
+
/**
|
|
2
14
|
* Request a user review for a product from server.
|
|
3
15
|
* @param {Object} review The review data.
|
|
4
16
|
* @param {boolean} update Indicate whether the update pipeline be called or not.
|
|
5
17
|
* @returns {Function} The dispatched action.
|
|
6
|
-
*/
|
|
7
|
-
|
|
18
|
+
*/
|
|
19
|
+
function submitReview(review, update = false) {
|
|
20
|
+
return (dispatch, getState) => {
|
|
21
|
+
const newReview = review;
|
|
22
|
+
const originalReview = getUserReviewForProduct(getState(), {
|
|
23
|
+
productId: review.productId
|
|
24
|
+
});
|
|
25
|
+
const fields = ['rate', 'title', 'review', 'author', 'productId'];
|
|
26
|
+
const pipelineData = {};
|
|
27
|
+
|
|
28
|
+
// Sanitize pipeline input
|
|
29
|
+
Object.keys(newReview).forEach(field => {
|
|
30
|
+
if (typeof newReview[field] === 'string') {
|
|
31
|
+
newReview[field] = newReview[field].trim();
|
|
32
|
+
}
|
|
33
|
+
if (fields.indexOf(field) !== -1) {
|
|
34
|
+
pipelineData[field] = newReview[field];
|
|
35
|
+
}
|
|
36
|
+
});
|
|
37
|
+
dispatch(requestSubmitReview(review));
|
|
38
|
+
if (update) {
|
|
39
|
+
const request = new PipelineRequest(SHOPGATE_CATALOG_UPDATE_PRODUCT_REVIEW).setInput(pipelineData).setRetries(0).dispatch();
|
|
40
|
+
request.then(() => {
|
|
41
|
+
dispatch(receiveSubmitReview(newReview));
|
|
42
|
+
dispatch(fetchProduct(newReview.productId, true));
|
|
43
|
+
}).catch(() => {
|
|
44
|
+
dispatch(resetSubmittedReview(originalReview));
|
|
45
|
+
});
|
|
46
|
+
return request;
|
|
47
|
+
}
|
|
48
|
+
const request = new PipelineRequest(SHOPGATE_CATALOG_ADD_PRODUCT_REVIEW).setRetries(0).setErrorBlacklist([EEXIST]).setInput(pipelineData).dispatch();
|
|
49
|
+
request.then(() => {
|
|
50
|
+
dispatch(receiveSubmitReview(newReview));
|
|
51
|
+
dispatch(fetchProduct(newReview.productId, true));
|
|
52
|
+
}).catch(error => {
|
|
53
|
+
if (error.code === EEXIST) {
|
|
54
|
+
dispatch(showModal({
|
|
55
|
+
confirm: null,
|
|
56
|
+
title: 'modal.title_error',
|
|
57
|
+
message: 'modal.body_error'
|
|
58
|
+
}));
|
|
59
|
+
}
|
|
60
|
+
dispatch(errorSubmitReview(newReview.productId));
|
|
61
|
+
});
|
|
62
|
+
return request;
|
|
63
|
+
};
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/** @mixes {MutableFunction} */
|
|
67
|
+
export default mutable(submitReview);
|
|
@@ -1 +1,4 @@
|
|
|
1
|
-
export
|
|
1
|
+
export const SHOPGATE_CATALOG_GET_PRODUCT_REVIEWS = 'shopgate.catalog.getProductReviews';
|
|
2
|
+
export const SHOPGATE_USER_GET_REVIEW = 'shopgate.user.getReview';
|
|
3
|
+
export const SHOPGATE_CATALOG_UPDATE_PRODUCT_REVIEW = 'shopgate.catalog.updateProductReview';
|
|
4
|
+
export const SHOPGATE_CATALOG_ADD_PRODUCT_REVIEW = 'shopgate.catalog.addProductReview';
|
|
@@ -1 +1,4 @@
|
|
|
1
|
-
|
|
1
|
+
const PRODUCT = 'product';
|
|
2
|
+
const REVIEWS = 'reviews';
|
|
3
|
+
const ALL = 'all';
|
|
4
|
+
export const PRODUCT_REVIEWS_ALL = `${PRODUCT}.${REVIEWS}.${ALL}`;
|
|
@@ -1,10 +1,29 @@
|
|
|
1
1
|
// PRODUCT REVIEWS LIST
|
|
2
|
-
export
|
|
3
|
-
export
|
|
4
|
-
export
|
|
5
|
-
export
|
|
6
|
-
|
|
7
|
-
|
|
2
|
+
export const REVIEWS_LIFETIME = 900000; // 15 minutes
|
|
3
|
+
export const REQUEST_REVIEWS = 'REQUEST_REVIEWS';
|
|
4
|
+
export const RECEIVE_REVIEWS = 'RECEIVE_REVIEWS';
|
|
5
|
+
export const ERROR_REVIEWS = 'ERROR_REVIEWS';
|
|
6
|
+
|
|
7
|
+
// PRODUCT REVIEWS
|
|
8
|
+
export const REQUEST_PRODUCT_REVIEWS = 'REQUEST_PRODUCT_REVIEWS';
|
|
9
|
+
export const RECEIVE_PRODUCT_REVIEWS = 'RECEIVE_PRODUCT_REVIEWS';
|
|
10
|
+
export const ERROR_PRODUCT_REVIEWS = 'ERROR_PRODUCT_REVIEWS';
|
|
11
|
+
|
|
12
|
+
// USER REVIEW
|
|
13
|
+
export const USER_REVIEW_LIFETIME = 300000; // 5 minutes
|
|
14
|
+
export const REQUEST_USER_REVIEW = 'REQUEST_USER_REVIEW';
|
|
15
|
+
export const RECEIVE_USER_REVIEW = 'RECEIVE_USER_REVIEW';
|
|
16
|
+
export const ERROR_USER_REVIEW = 'ERROR_USER_REVIEW';
|
|
17
|
+
export const FLUSH_USER_REVIEWS = 'FLUSH_USER_REVIEWS';
|
|
18
|
+
|
|
19
|
+
// SUBMIT REVIEW
|
|
20
|
+
export const REQUEST_SUBMIT_REVIEW = 'REQUEST_SUBMIT_REVIEW';
|
|
21
|
+
export const RECEIVE_SUBMIT_REVIEW = 'RECEIVE_SUBMIT_REVIEW';
|
|
22
|
+
export const ERROR_SUBMIT_REVIEW = 'ERROR_SUBMIT_REVIEW';
|
|
23
|
+
export const RESET_SUBMIT_REVIEW = 'RESET_SUBMIT_REVIEW';
|
|
24
|
+
|
|
25
|
+
/**
|
|
8
26
|
* Max number of reviews shown
|
|
9
27
|
* @type {number}
|
|
10
|
-
*/
|
|
28
|
+
*/
|
|
29
|
+
export const REVIEW_PREVIEW_COUNT = 2;
|