From 260e86c9c5793c038dd2a5f78dea38c7ad011913 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 09:22:38 -0700 Subject: [PATCH 01/57] chore: update package lock --- package-lock.json | 180 +++++++++++++++++++++++++--------------------- 1 file changed, 100 insertions(+), 80 deletions(-) diff --git a/package-lock.json b/package-lock.json index 1d9973f8b9d..0a96732595b 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2633,8 +2633,7 @@ "builtin-modules": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/builtin-modules/-/builtin-modules-1.1.1.tgz", - "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=", - "dev": true + "integrity": "sha1-Jw8HbFpywC9bZaR9+Uxf46J4iS8=" }, "bunyan-format": { "version": "0.2.1", @@ -2728,8 +2727,7 @@ "camelcase": { "version": "4.1.0", "resolved": "https://registry.npmjs.org/camelcase/-/camelcase-4.1.0.tgz", - "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=", - "dev": true + "integrity": "sha1-1UVjW+HjPFQmScaRc+Xeas+uNN0=" }, "caniuse-lite": { "version": "1.0.30000813", @@ -3294,7 +3292,6 @@ "version": "5.1.0", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", - "dev": true, "requires": { "lru-cache": "4.1.1", "shebang-command": "1.2.0", @@ -3955,7 +3952,6 @@ "version": "1.3.1", "resolved": "https://registry.npmjs.org/error-ex/-/error-ex-1.3.1.tgz", "integrity": "sha1-+FWobOYa3E6GIcPNoh56dhLDqNw=", - "dev": true, "requires": { "is-arrayish": "0.2.1" } @@ -4297,7 +4293,6 @@ "version": "0.7.0", "resolved": "https://registry.npmjs.org/execa/-/execa-0.7.0.tgz", "integrity": "sha1-lEvs00zEHuMqY6n68nrVpl/Fl3c=", - "dev": true, "requires": { "cross-spawn": "5.1.0", "get-stream": "3.0.0", @@ -4617,7 +4612,6 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/find-up/-/find-up-2.1.0.tgz", "integrity": "sha1-RdG35QbHF93UgndaK3eSCjwMV6c=", - "dev": true, "requires": { "locate-path": "2.0.0" } @@ -5342,8 +5336,7 @@ "get-caller-file": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/get-caller-file/-/get-caller-file-1.0.2.tgz", - "integrity": "sha1-9wLmMSfn4jHBYKgMFVSstw1QR+U=", - "dev": true + "integrity": "sha1-9wLmMSfn4jHBYKgMFVSstw1QR+U=" }, "get-func-name": { "version": "2.0.0", @@ -5874,8 +5867,7 @@ "hosted-git-info": { "version": "2.5.0", "resolved": "https://registry.npmjs.org/hosted-git-info/-/hosted-git-info-2.5.0.tgz", - "integrity": "sha512-pNgbURSuab90KbTqvRPsseaTxOJCZBD0a7t+haSN33piP9cCM4l0CqdzAif2hUqm716UovKB2ROmiabGAKVXyg==", - "dev": true + "integrity": "sha512-pNgbURSuab90KbTqvRPsseaTxOJCZBD0a7t+haSN33piP9cCM4l0CqdzAif2hUqm716UovKB2ROmiabGAKVXyg==" }, "html-encoding-sniffer": { "version": "1.0.2", @@ -6138,8 +6130,7 @@ "invert-kv": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/invert-kv/-/invert-kv-1.0.0.tgz", - "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=", - "dev": true + "integrity": "sha1-EEqOSqym09jNFXqO+L+rLXo//bY=" }, "ip": { "version": "1.1.5", @@ -6177,8 +6168,7 @@ "is-arrayish": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/is-arrayish/-/is-arrayish-0.2.1.tgz", - "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=", - "dev": true + "integrity": "sha1-d8mYQFJ6qOyxqLppe4BkWnqSap0=" }, "is-binary-path": { "version": "1.0.1", @@ -6204,7 +6194,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-builtin-module/-/is-builtin-module-1.0.0.tgz", "integrity": "sha1-VAVy0096wxGfj3bDDLwbHgN6/74=", - "dev": true, "requires": { "builtin-modules": "1.1.1" } @@ -6302,8 +6291,7 @@ "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", - "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", - "dev": true + "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=" }, "is-generator-fn": { "version": "1.0.0", @@ -6559,8 +6547,7 @@ "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", - "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", - "dev": true + "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=" }, "isobj": { "version": "1.0.0", @@ -7559,7 +7546,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/lcid/-/lcid-1.0.0.tgz", "integrity": "sha1-MIrMr6C8SDo4Z7S28rlQYlHRuDU=", - "dev": true, "requires": { "invert-kv": "1.0.0" } @@ -7623,7 +7609,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/load-json-file/-/load-json-file-2.0.0.tgz", "integrity": "sha1-eUfkIUmvgNaWy/eXvKq8/h/inKg=", - "dev": true, "requires": { "graceful-fs": "4.1.11", "parse-json": "2.2.0", @@ -7644,7 +7629,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/locate-path/-/locate-path-2.0.0.tgz", "integrity": "sha1-K1aLJl7slExtnA3pw9u7ygNUzY4=", - "dev": true, "requires": { "p-locate": "2.0.0", "path-exists": "3.0.0" @@ -7991,7 +7975,6 @@ "version": "4.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.1.tgz", "integrity": "sha512-q4spe4KTfsAS1SUHLO0wz8Qiyf1+vMIAgpRYioFYDMNqKfHQbg+AVDH3i4fvpl71/P1L0dBl+fQi+P37UYf0ew==", - "dev": true, "requires": { "pseudomap": "1.0.2", "yallist": "2.1.2" @@ -8086,7 +8069,6 @@ "version": "1.1.0", "resolved": "https://registry.npmjs.org/mem/-/mem-1.1.0.tgz", "integrity": "sha1-Xt1StIXKHZAP5kiVUFOZoN+kX3Y=", - "dev": true, "requires": { "mimic-fn": "1.1.0" } @@ -8829,8 +8811,7 @@ "mimic-fn": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.1.0.tgz", - "integrity": "sha1-5md4PZLonb00KBi1IwudYqZyrRg=", - "dev": true + "integrity": "sha1-5md4PZLonb00KBi1IwudYqZyrRg=" }, "mimic-response": { "version": "1.0.0", @@ -9816,7 +9797,6 @@ "version": "2.4.0", "resolved": "https://registry.npmjs.org/normalize-package-data/-/normalize-package-data-2.4.0.tgz", "integrity": "sha512-9jjUFbTPfEy3R/ad/2oNbKtW9Hgovl5O1FvFWKkKblNXoN/Oou6+9+KKohPK13Yc3/TyunyWhJp6gvRNR/PPAw==", - "dev": true, "requires": { "hosted-git-info": "2.5.0", "is-builtin-module": "1.0.0", @@ -9862,7 +9842,6 @@ "version": "2.0.2", "resolved": "https://registry.npmjs.org/npm-run-path/-/npm-run-path-2.0.2.tgz", "integrity": "sha1-NakjLfo11wZ7TLLd8jV7GHFTbF8=", - "dev": true, "requires": { "path-key": "2.0.1" } @@ -10152,7 +10131,6 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/os-locale/-/os-locale-2.1.0.tgz", "integrity": "sha512-3sslG3zJbEYcaC4YVAvDorjGxc7tv6KVATnLPZONiljsUncvihe9BQoVCEs0RZ1kmf4Hk9OBqlZfJZWI4GanKA==", - "dev": true, "requires": { "execa": "0.7.0", "lcid": "1.0.0", @@ -10202,14 +10180,12 @@ "p-limit": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/p-limit/-/p-limit-1.1.0.tgz", - "integrity": "sha1-sH/y2aXYi+yAYDWJWiurZqJ5iLw=", - "dev": true + "integrity": "sha1-sH/y2aXYi+yAYDWJWiurZqJ5iLw=" }, "p-locate": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/p-locate/-/p-locate-2.0.0.tgz", "integrity": "sha1-IKAQOyIqcMj9OcwuWAaA893l7EM=", - "dev": true, "requires": { "p-limit": "1.1.0" } @@ -10326,7 +10302,6 @@ "version": "2.2.0", "resolved": "https://registry.npmjs.org/parse-json/-/parse-json-2.2.0.tgz", "integrity": "sha1-9ID0BDTvgHQfhGkJn43qGPVaTck=", - "dev": true, "requires": { "error-ex": "1.3.1" } @@ -10366,8 +10341,7 @@ "path-exists": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/path-exists/-/path-exists-3.0.0.tgz", - "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=", - "dev": true + "integrity": "sha1-zg6+ql94yxiSXqfYENe1mwEP1RU=" }, "path-extra": { "version": "1.0.3", @@ -10389,8 +10363,7 @@ "path-key": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/path-key/-/path-key-2.0.1.tgz", - "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=", - "dev": true + "integrity": "sha1-QRyttXTFoUDTpLGRDUDYDMn0C0A=" }, "path-parse": { "version": "1.0.5", @@ -10414,7 +10387,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/path-type/-/path-type-2.0.0.tgz", "integrity": "sha1-8BLMuEFbcJb8LaoQVMPXI4lZTHM=", - "dev": true, "requires": { "pify": "2.3.0" } @@ -10451,8 +10423,7 @@ "pify": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", - "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", - "dev": true + "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=" }, "pinkie": { "version": "2.0.4", @@ -10858,8 +10829,7 @@ "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", - "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", - "dev": true + "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=" }, "pstree.remy": { "version": "1.1.0", @@ -11517,7 +11487,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/read-pkg/-/read-pkg-2.0.0.tgz", "integrity": "sha1-jvHAYjxqbbDcZxPEv6xGMysjaPg=", - "dev": true, "requires": { "load-json-file": "2.0.0", "normalize-package-data": "2.4.0", @@ -11528,7 +11497,6 @@ "version": "2.0.0", "resolved": "https://registry.npmjs.org/read-pkg-up/-/read-pkg-up-2.0.0.tgz", "integrity": "sha1-a3KoBImE4MQeeVEP1en6mbO1Sb4=", - "dev": true, "requires": { "find-up": "2.1.0", "read-pkg": "2.0.0" @@ -11804,14 +11772,12 @@ "require-directory": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/require-directory/-/require-directory-2.1.1.tgz", - "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=", - "dev": true + "integrity": "sha1-jGStX9MNqxyXbiNE/+f3kqam30I=" }, "require-main-filename": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/require-main-filename/-/require-main-filename-1.0.1.tgz", - "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=", - "dev": true + "integrity": "sha1-l/cXtp1IeE9fUmpsWqj/3aBVpNE=" }, "require-package-name": { "version": "2.0.1", @@ -12141,8 +12107,7 @@ "set-blocking": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/set-blocking/-/set-blocking-2.0.0.tgz", - "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=", - "dev": true + "integrity": "sha1-BF+XgtARrppoA93TgrJDkrPYkPc=" }, "set-immediate-shim": { "version": "1.0.1", @@ -12240,7 +12205,6 @@ "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", - "dev": true, "requires": { "shebang-regex": "1.0.0" } @@ -12248,8 +12212,7 @@ "shebang-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", - "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", - "dev": true + "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=" }, "shellwords": { "version": "0.1.1", @@ -12952,7 +12915,6 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/spdx-correct/-/spdx-correct-1.0.2.tgz", "integrity": "sha1-SzBz2TP/UfORLwOsVRlJikFQ20A=", - "dev": true, "requires": { "spdx-license-ids": "1.2.2" } @@ -12960,14 +12922,12 @@ "spdx-expression-parse": { "version": "1.0.4", "resolved": "https://registry.npmjs.org/spdx-expression-parse/-/spdx-expression-parse-1.0.4.tgz", - "integrity": "sha1-m98vIOH0DtRH++JzJmGR/O1RYmw=", - "dev": true + "integrity": "sha1-m98vIOH0DtRH++JzJmGR/O1RYmw=" }, "spdx-license-ids": { "version": "1.2.2", "resolved": "https://registry.npmjs.org/spdx-license-ids/-/spdx-license-ids-1.2.2.tgz", - "integrity": "sha1-yd96NCRZSt5r0RkA1ZZpbcBrrFc=", - "dev": true + "integrity": "sha1-yd96NCRZSt5r0RkA1ZZpbcBrrFc=" }, "split": { "version": "0.3.3", @@ -13182,7 +13142,6 @@ "version": "2.1.1", "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", - "dev": true, "requires": { "is-fullwidth-code-point": "2.0.0", "strip-ansi": "4.0.0" @@ -13205,7 +13164,6 @@ "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", - "dev": true, "requires": { "ansi-regex": "3.0.0" }, @@ -13213,22 +13171,19 @@ "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", - "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", - "dev": true + "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=" } } }, "strip-bom": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/strip-bom/-/strip-bom-3.0.0.tgz", - "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=", - "dev": true + "integrity": "sha1-IzTBjpx1n3vdVv3vfprj1YjmjtM=" }, "strip-eof": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/strip-eof/-/strip-eof-1.0.0.tgz", - "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=", - "dev": true + "integrity": "sha1-u0P/VZim6wXYm1n80SnJgzE2Br8=" }, "strip-json-comments": { "version": "2.0.1", @@ -13667,6 +13622,12 @@ } } }, + "transliteration": { + "version": "github:reactioncommerce/transliteration#699d48cc8dd9a64f1a2773e1b36b6faa4bbdca2f", + "requires": { + "yargs": "8.0.2" + } + }, "trim-right": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/trim-right/-/trim-right-1.0.1.tgz", @@ -14144,7 +14105,6 @@ "version": "3.0.1", "resolved": "https://registry.npmjs.org/validate-npm-package-license/-/validate-npm-package-license-3.0.1.tgz", "integrity": "sha1-KAS6vnEq0zeUWaz74kdGqywwP7w=", - "dev": true, "requires": { "spdx-correct": "1.0.2", "spdx-expression-parse": "1.0.4" @@ -14277,7 +14237,6 @@ "version": "1.3.0", "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", - "dev": true, "requires": { "isexe": "2.0.0" } @@ -14285,8 +14244,7 @@ "which-module": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/which-module/-/which-module-2.0.0.tgz", - "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=", - "dev": true + "integrity": "sha1-2e8H3Od7mQK4o6j6SzHD4/fm6Ho=" }, "wide-align": { "version": "1.1.2", @@ -14365,7 +14323,6 @@ "version": "2.1.0", "resolved": "https://registry.npmjs.org/wrap-ansi/-/wrap-ansi-2.1.0.tgz", "integrity": "sha1-2Pw9KE3QV5T+hJc8rs3Rz4JP3YU=", - "dev": true, "requires": { "string-width": "1.0.2", "strip-ansi": "3.0.1" @@ -14375,7 +14332,6 @@ "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", - "dev": true, "requires": { "number-is-nan": "1.0.1" } @@ -14384,7 +14340,6 @@ "version": "1.0.2", "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", - "dev": true, "requires": { "code-point-at": "1.1.0", "is-fullwidth-code-point": "1.0.0", @@ -14395,7 +14350,6 @@ "version": "3.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", - "dev": true, "requires": { "ansi-regex": "2.1.1" } @@ -14497,14 +14451,80 @@ "y18n": { "version": "3.2.1", "resolved": "https://registry.npmjs.org/y18n/-/y18n-3.2.1.tgz", - "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=", - "dev": true + "integrity": "sha1-bRX7qITAhnnA136I53WegR4H+kE=" }, "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", - "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", - "dev": true + "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=" + }, + "yargs": { + "version": "8.0.2", + "resolved": "https://registry.npmjs.org/yargs/-/yargs-8.0.2.tgz", + "integrity": "sha1-YpmpBVsc78lp/355wdkY3Osiw2A=", + "requires": { + "camelcase": "4.1.0", + "cliui": "3.2.0", + "decamelize": "1.2.0", + "get-caller-file": "1.0.2", + "os-locale": "2.1.0", + "read-pkg-up": "2.0.0", + "require-directory": "2.1.1", + "require-main-filename": "1.0.1", + "set-blocking": "2.0.0", + "string-width": "2.1.1", + "which-module": "2.0.0", + "y18n": "3.2.1", + "yargs-parser": "7.0.0" + }, + "dependencies": { + "cliui": { + "version": "3.2.0", + "resolved": "https://registry.npmjs.org/cliui/-/cliui-3.2.0.tgz", + "integrity": "sha1-EgYBU3qRbSmUD5NNo7SNWFo5IT0=", + "requires": { + "string-width": "1.0.2", + "strip-ansi": "3.0.1", + "wrap-ansi": "2.1.0" + }, + "dependencies": { + "string-width": { + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/string-width/-/string-width-1.0.2.tgz", + "integrity": "sha1-EYvfW4zcUaKn5w0hHgfisLmxB9M=", + "requires": { + "code-point-at": "1.1.0", + "is-fullwidth-code-point": "1.0.0", + "strip-ansi": "3.0.1" + } + } + } + }, + "is-fullwidth-code-point": { + "version": "1.0.0", + "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz", + "integrity": "sha1-754xOG8DGn8NZDr4L95QxFfvAMs=", + "requires": { + "number-is-nan": "1.0.1" + } + }, + "strip-ansi": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", + "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", + "requires": { + "ansi-regex": "2.1.1" + } + } + } + }, + "yargs-parser": { + "version": "7.0.0", + "resolved": "https://registry.npmjs.org/yargs-parser/-/yargs-parser-7.0.0.tgz", + "integrity": "sha1-jQrELxbqVd69MyyvTEA4s+P139k=", + "requires": { + "camelcase": "4.1.0" + } }, "zen-observable": { "version": "0.7.1", From 04cf316b261f9d3fecfc650eb6c3bc275034f1fc Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 09:33:53 -0700 Subject: [PATCH 02/57] refactor: remove revision control from publication --- server/publications/collections/product.js | 51 +--------------------- 1 file changed, 1 insertion(+), 50 deletions(-) diff --git a/server/publications/collections/product.js b/server/publications/collections/product.js index a557151a706..c6c0c68bb11 100644 --- a/server/publications/collections/product.js +++ b/server/publications/collections/product.js @@ -1,8 +1,7 @@ import { Meteor } from "meteor/meteor"; import { check, Match } from "meteor/check"; -import { Products, Revisions, Shops } from "/lib/collections"; +import { Products, Shops } from "/lib/collections"; import { Logger, Reaction } from "/server/api"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; /** * product detail publication @@ -65,54 +64,6 @@ Meteor.publish("Product", function (productIdOrHandle, shopIdOrSlug) { selector.isVisible = { $in: [true, false, undefined] }; - - if (RevisionApi.isRevisionControlEnabled()) { - const handle = Revisions.find({ - "workflow.status": { - $nin: [ - "revision/published" - ] - }, - "$or": [ - { "documentData._id": _id }, - { "documentData.ancestors": _id } - ] - }).observe({ - added: (revision) => { - this.added("Revisions", revision._id, revision); - if (revision.documentType === "product") { - // Check merge box (session collection view), if product is already in cache. - // If yes, we send a `changed`, otherwise `added`. I'm assuming - // that this._documents.Products is somewhat equivalent to the - // merge box Meteor.server.sessions[sessionId].getCollectionView("Products").documents - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [revision] }); - } else { - this.added("Products", revision.documentId, { __revisions: [revision] }); - } - } - }, - changed: (revision) => { - this.changed("Revisions", revision._id, revision); - if (revision.documentType === "product") { - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [revision] }); - } - } - }, - removed: (revision) => { - this.removed("Revisions", revision._id); - if (revision.documentType === "product") { - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [] }); - } - } - } - }); - this.onStop(() => { - handle.stop(); - }); - } } return Products.find(selector); From 4ce419aab263533010a8309d5da4bde13ebd3e61 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 09:46:01 -0700 Subject: [PATCH 03/57] refactor: remove revisions from publication --- server/publications/collections/products.js | 125 +------------------- 1 file changed, 1 insertion(+), 124 deletions(-) diff --git a/server/publications/collections/products.js b/server/publications/collections/products.js index b3f601cc0fb..2543f5d93e4 100644 --- a/server/publications/collections/products.js +++ b/server/publications/collections/products.js @@ -4,9 +4,8 @@ import { Meteor } from "meteor/meteor"; import { Tracker } from "meteor/tracker"; import { check, Match } from "meteor/check"; import { registerSchema } from "@reactioncommerce/schemas"; -import { Products, Shops, Revisions, Catalog } from "/lib/collections"; +import { Products, Shops, Catalog } from "/lib/collections"; import { Reaction, Logger } from "/server/api"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; // // define search filters as a schema so we can validate @@ -71,62 +70,6 @@ const filters = new SimpleSchema({ registerSchema("filters", filters); -/** - * Broadens an existing selector to include all variants of the given top-level productIds - * Additionally considers the tags product filter, if given - * Can operate on the "Revisions" and the "Products" collection - * @memberof Helpers - * @param collectionName {String} - "Revisions" or "Products" - * @param selector {object} - the selector that should be extended - * @param productFilters { object } - the product filter (e.g. orginating from query parameters) - * @param productIds {String[]} - the top-level productIds we want to get the variants of. - */ -function extendSelectorWithVariants(collectionName, selector, productFilters, productIds) { - let prefix = ""; - - if (collectionName.toLowerCase() === "revisions") { - prefix = "documentData."; - } else if (collectionName.toLowerCase() !== "products") { - throw new Error(`Can't extend selector for collection ${collectionName}.`); - } - - // Remove hashtag filter from selector (hashtags are not applied to variants, we need to get variants) - const newSelector = _.omit(selector, ["hashtags", "ancestors"]); - if (productFilters && productFilters.tags) { - // Re-configure selector to pick either Variants of one of the top-level products, or the top-level products in the filter - _.extend(newSelector, { - $or: [{ - [`${prefix}ancestors`]: { - $in: productIds - } - }, { - $and: [{ - [`${prefix}hashtags`]: { - $in: productFilters.tags - } - }, { - [`${prefix}_id`]: { - $in: productIds - } - }] - }] - }); - } else { - _.extend(newSelector, { - $or: [{ - [`${prefix}ancestors`]: { - $in: productIds - } - }, { - [`${prefix}_id`]: { - $in: productIds - } - }] - }); - } - return newSelector; -} - function filterProducts(productFilters) { // if there are filter/params that don't match the schema // validate, catch except but return no results @@ -336,8 +279,6 @@ Meteor.publish("Products", function (productScrollLimit = 24, productFilters, so } // We publish an admin version of this publication to admins of products who are in "Edit Mode" - // Authorized content curators for shops get special publication of the product - // with all relevant revisions all is one package // userAdminShopIds is a list of shopIds that the user has createProduct or owner access for if (editMode && userAdminShopIds && Array.isArray(userAdminShopIds) && userAdminShopIds.length > 0) { selector.isVisible = { @@ -346,70 +287,6 @@ Meteor.publish("Products", function (productScrollLimit = 24, productFilters, so selector.shopId = { $in: activeShopsIds }; - - // Get _ids of top-level products - const productIds = Products.find(selector, { - sort, - limit: productScrollLimit - }).map((product) => product._id); - - - const productSelectorWithVariants = extendSelectorWithVariants("Products", selector, productFilters, productIds); - - if (RevisionApi.isRevisionControlEnabled()) { - const revisionSelector = { - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }; - const revisionSelectorWithVariants = extendSelectorWithVariants("Revisions", revisionSelector, productFilters, productIds); - const handle = Revisions.find(revisionSelectorWithVariants).observe({ - added: (revision) => { - this.added("Revisions", revision._id, revision); - if (revision.documentType === "product") { - // Check merge box (session collection view), if product is already in cache. - // If yes, we send a `changed`, otherwise `added`. I'm assuming - // that this._documents.Products is somewhat equivalent to - // the merge box Meteor.server.sessions[sessionId].getCollectionView("Products").documents - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [revision] }); - } else { - this.added("Products", revision.documentId, { __revisions: [revision] }); - } - } - }, - changed: (revision) => { - this.changed("Revisions", revision._id, revision); - if (revision.documentType === "product") { - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [revision] }); - } - } - }, - removed: (revision) => { - this.removed("Revisions", revision._id); - if (revision.documentType === "product") { - if (this._documents.Products && this._documents.Products[revision.documentId]) { - this.changed("Products", revision.documentId, { __revisions: [] }); - } - } - } - }); - - this.onStop(() => { - handle.stop(); - }); - - return Products.find(productSelectorWithVariants); - } - - // Revision control is disabled, but is admin - return Products.find(productSelectorWithVariants, { - sort, - limit: productScrollLimit - }); } // This is where the publication begins for non-admin users From 2ffa0cc0cc7743b1f1ae5701c69f5ee003c16b6d Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:27:21 -0700 Subject: [PATCH 04/57] refactor: move publish controls to `reaction-catalog` package --- .../client/components/publishControls.js | 37 +++++-------------- .../client/containers/publishContainer.js | 3 -- .../client/containers/publish.js | 2 +- .../containers/gridPublishContainer.js | 2 +- 4 files changed, 11 insertions(+), 33 deletions(-) rename imports/plugins/core/{revisions => catalog}/client/components/publishControls.js (92%) rename imports/plugins/core/{revisions => catalog}/client/containers/publishContainer.js (97%) diff --git a/imports/plugins/core/revisions/client/components/publishControls.js b/imports/plugins/core/catalog/client/components/publishControls.js similarity index 92% rename from imports/plugins/core/revisions/client/components/publishControls.js rename to imports/plugins/core/catalog/client/components/publishControls.js index 8381547b691..39322a5cef3 100644 --- a/imports/plugins/core/revisions/client/components/publishControls.js +++ b/imports/plugins/core/catalog/client/components/publishControls.js @@ -11,7 +11,6 @@ import { Switch, Icon } from "/imports/plugins/core/ui/client/components"; -import SimpleDiff from "./simpleDiff"; import { Translatable } from "/imports/plugins/core/ui/client/providers"; /** TMP **/ @@ -176,19 +175,6 @@ class PublishControls extends Component { return false; } - renderChanges() { - if (this.showDiffs) { - const diffs = this.props.revisions.map((revision) => ); - - return ( -
- {diffs} -
- ); - } - return null; - } - renderDeletionStatus() { if (this.hasChanges) { if (this.primaryRevision && this.primaryRevision.documentData.isDeleted) { @@ -378,20 +364,15 @@ class PublishControls extends Component { } render() { - if (this.props.isEnabled) { - return ( - - {this.renderDeletionStatus()} - {this.renderUndoButton()} - {this.renderArchiveButton()} - {this.renderViewControls()} - {this.renderPublishButton()} - {/* this.renderMoreOptionsButton() */} - - ); - } - - return null; + return ( + + {this.renderDeletionStatus()} + {this.renderArchiveButton()} + {this.renderViewControls()} + {this.renderPublishButton()} + {/* this.renderMoreOptionsButton() */} + + ); } } diff --git a/imports/plugins/core/revisions/client/containers/publishContainer.js b/imports/plugins/core/catalog/client/containers/publishContainer.js similarity index 97% rename from imports/plugins/core/revisions/client/containers/publishContainer.js rename to imports/plugins/core/catalog/client/containers/publishContainer.js index e5c456b9fe4..f4531e14a18 100644 --- a/imports/plugins/core/revisions/client/containers/publishContainer.js +++ b/imports/plugins/core/catalog/client/containers/publishContainer.js @@ -5,7 +5,6 @@ import PublishControls from "../components/publishControls"; import { Revisions } from "/lib/collections"; import { Meteor } from "meteor/meteor"; import TranslationProvider from "/imports/plugins/core/ui/client/providers/translationProvider"; -import { isRevisionControlEnabled } from "../../lib/api"; import { Reaction, i18next } from "/client/api"; /* @@ -151,7 +150,6 @@ function composer(props, onData) { }).fetch(); onData(null, { - isEnabled: isRevisionControlEnabled(), documentIds: props.documentIds, documents: props.documents, revisions, @@ -163,7 +161,6 @@ function composer(props, onData) { } onData(null, { - isEnabled: isRevisionControlEnabled(), isPreview: viewAs === "customer" }); } diff --git a/imports/plugins/included/product-detail-simple/client/containers/publish.js b/imports/plugins/included/product-detail-simple/client/containers/publish.js index 07a10f6dd19..13d55f5fe3a 100644 --- a/imports/plugins/included/product-detail-simple/client/containers/publish.js +++ b/imports/plugins/included/product-detail-simple/client/containers/publish.js @@ -4,7 +4,7 @@ import { registerComponent, composeWithTracker } from "@reactioncommerce/reactio import { Meteor } from "meteor/meteor"; import { ReactionProduct } from "/lib/api"; import { Products } from "/lib/collections"; -import PublishContainer from "/imports/plugins/core/revisions/client/containers/publishContainer"; +import PublishContainer from "/imports/plugins/core/catalog/client/containers/publishContainer"; class ProductPublishContainer extends Component { handleMetaRemove = (productId, metafield) => { diff --git a/imports/plugins/included/product-variant/containers/gridPublishContainer.js b/imports/plugins/included/product-variant/containers/gridPublishContainer.js index 52df62f8448..d18c46c2170 100644 --- a/imports/plugins/included/product-variant/containers/gridPublishContainer.js +++ b/imports/plugins/included/product-variant/containers/gridPublishContainer.js @@ -5,7 +5,7 @@ import { Meteor } from "meteor/meteor"; import { Session } from "meteor/session"; import { ReactionProduct } from "/lib/api"; import { Products } from "/lib/collections"; -import PublishContainer from "/imports/plugins/core/revisions/client/containers/publishContainer"; +import PublishContainer from "/imports/plugins/core/catalog/client/containers/publishContainer"; class GridProductPublishContainer extends Component { static propTypes = { From 86f852bec314d97c8390cb527431f36171991b28 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:34:16 -0700 Subject: [PATCH 05/57] refactor: remove publish from revisions to products --- .../client/containers/publishContainer.js | 34 ++----------------- 1 file changed, 2 insertions(+), 32 deletions(-) diff --git a/imports/plugins/core/catalog/client/containers/publishContainer.js b/imports/plugins/core/catalog/client/containers/publishContainer.js index f4531e14a18..e640e41083a 100644 --- a/imports/plugins/core/catalog/client/containers/publishContainer.js +++ b/imports/plugins/core/catalog/client/containers/publishContainer.js @@ -21,42 +21,12 @@ class PublishContainer extends Component { }); } - handlePublishClick = (revisions) => { + handlePublishClick = () => { const productIds = this.props.documents .filter((doc) => doc.type === "simple") .map((doc) => doc._id); - if (Array.isArray(revisions) && revisions.length) { - let documentIds = revisions.map((revision) => { - if (revision.parentDocument && revision.documentType !== "product") { - return revision.parentDocument; - } - return revision.documentId; - }); - - const documentIdsSet = new Set(documentIds); // ensures they are unique - documentIds = Array.from(documentIdsSet); - Meteor.call("revisions/publish", documentIds, (error, result) => { - if (result && result.status === "success") { - const message = i18next.t("revisions.changedPublished", { - defaultValue: "Changes published successfully" - }); - Alerts.toast(message, "success"); - - if (this.props.onPublishSuccess) { - this.props.onPublishSuccess(result); - } - - // Publish to catalog after revisions have been published - this.publishToCatalog("products", productIds); - } else { - Alerts.toast((error && error.message) || (result && result.status) || i18next.t("app.error"), "error"); - } - }); - } else { - // Publish to catalog immediately if there are no revisions to publish beforehand - this.publishToCatalog("products", productIds); - } + this.publishToCatalog("products", productIds); } handlePublishActions = (event, action, documentIds) => { From a28e27c5e41050a8a4ab5519173596690429cc41 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:56:32 -0700 Subject: [PATCH 06/57] refactor: remove `applyProductRevision` --- lib/api/catalog.js | 25 ++++++------------------- 1 file changed, 6 insertions(+), 19 deletions(-) diff --git a/lib/api/catalog.js b/lib/api/catalog.js index 8b953197189..1a1d5ed0bba 100644 --- a/lib/api/catalog.js +++ b/lib/api/catalog.js @@ -1,7 +1,6 @@ import _ from "lodash"; import { Products } from "/lib/collections"; import { ReactionProduct } from "/lib/api"; -import { applyProductRevision } from "/lib/api/products"; /** * @file Catalog methods @@ -43,7 +42,7 @@ export default { * @return {Object} range, min, max */ getProductPriceRange(productId) { - const product = applyProductRevision(Products.findOne(productId)); + const product = Products.findOne(productId); if (!product) { return { range: "0", @@ -115,7 +114,7 @@ export default { switch (visibleChildren.length) { case 0: { - const topVariant = applyProductRevision(Products.findOne(variantId)); + const topVariant = Products.findOne(variantId); // topVariant could be undefined when we removing last top variant return topVariant && topVariant.price; } @@ -162,17 +161,6 @@ export default { return variant.inventoryQuantity || 0; }, - /** - * @method getPublishedOrRevision - * @memberof Catalog - * @description return top product revision if available - * @param {Object} product product or variant document - * @return {Object} product document - */ - getPublishedOrRevision(product) { - return applyProductRevision(product); - }, - /** * @method getProduct * @method @@ -198,7 +186,7 @@ export default { return Products.find({ ancestors: { $in: [id] }, type: type || "variant" - }).map(this.getPublishedOrRevision); + }).fetch(); }, /** @@ -210,11 +198,10 @@ export default { * @return {Array} Parent variant or empty */ getVariantParent(variant) { - const parent = Products.findOne({ + return Products.findOne({ _id: { $in: variant.ancestors }, type: "variant" }); - return this.getPublishedOrRevision(parent); }, /** @@ -231,7 +218,7 @@ export default { return Products.find({ ancestors: variant.ancestors, type: type || "variant" - }).map(this.getPublishedOrRevision); + }).fetch(); }, /** @@ -245,6 +232,6 @@ export default { return Products.find({ ancestors: [id], type: "variant" - }).map(this.getPublishedOrRevision); + }).fetch(); } }; From e8f58a7a694838149dbe3fbc8da3584f4b021e96 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:56:38 -0700 Subject: [PATCH 07/57] refactor: remove `applyProductRevision` --- .../product-variant/containers/variantEditContainer.js | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/imports/plugins/included/product-variant/containers/variantEditContainer.js b/imports/plugins/included/product-variant/containers/variantEditContainer.js index 6480ed5dd9f..ea27e327c70 100644 --- a/imports/plugins/included/product-variant/containers/variantEditContainer.js +++ b/imports/plugins/included/product-variant/containers/variantEditContainer.js @@ -7,7 +7,6 @@ import { ReactionProduct } from "/lib/api"; import { Products } from "/lib/collections"; import { Countries } from "/client/collections"; import { Reaction, i18next } from "/client/api"; -import { applyProductRevision } from "/lib/api/products"; import VariantEdit from "../components/variantEdit"; @@ -72,14 +71,13 @@ function composer(props, onData) { _id: ReactionProduct.selectedTopVariant()._id }); - const revisedVariant = applyProductRevision(variant); - const childVariants = ReactionProduct.getVariants(revisedVariant._id); + const childVariants = ReactionProduct.getVariants(variant._id); onData(null, { countries: Countries.find({}).fetch(), editFocus: Reaction.state.get("edit/focus"), childVariants, - variant: revisedVariant + variant }); } else { onData(null, { From ddaa4c8f3419277fd452b1a9008214ac0ffe5ddc Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:57:01 -0700 Subject: [PATCH 08/57] refactor: remove `applyProductRevision` and `resubscribeAfterCloning` --- .../containers/productsContainerAdmin.js | 13 ++----------- 1 file changed, 2 insertions(+), 11 deletions(-) diff --git a/imports/plugins/included/product-variant/containers/productsContainerAdmin.js b/imports/plugins/included/product-variant/containers/productsContainerAdmin.js index 426a2add2a2..e6956e7609c 100644 --- a/imports/plugins/included/product-variant/containers/productsContainerAdmin.js +++ b/imports/plugins/included/product-variant/containers/productsContainerAdmin.js @@ -9,7 +9,6 @@ import { Tracker } from "meteor/tracker"; import { Reaction } from "/client/api"; import { ITEMS_INCREMENT } from "/client/config/defaults"; import { ReactionProduct } from "/lib/api"; -import { applyProductRevision, resubscribeAfterCloning } from "/lib/api/products"; import { Products, Tags, Shops } from "/lib/collections"; import ProductsComponent from "../components/products"; @@ -158,10 +157,6 @@ function composer(props, onData) { const queryParams = Object.assign({}, tags, Reaction.Router.current().query, shopIds); const productsSubscription = Meteor.subscribe("Products", scrollLimit, queryParams, sort, editMode); - if (resubscribeAfterCloning.get()) { - resubscribeAfterCloning.set(false); - productsSubscription.stop(); - } if (productsSubscription.ready()) { window.prerenderReady = true; @@ -180,12 +175,8 @@ function composer(props, onData) { shopId: { $in: activeShopsIds } }); - const productIds = []; - const products = productCursor.map((product) => { - productIds.push(product._id); - - return applyProductRevision(product); - }); + const products = productCursor.fetch(); + const productIds = productCursor.map((product) => product._id); const sortedProducts = ReactionProduct.sortProducts(products, currentTag); Session.set("productGrid/products", sortedProducts); From aae79a59d8bc3daddda299c225ca3d1c9bc09ac3 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:57:06 -0700 Subject: [PATCH 09/57] refactor: remove `applyProductRevision` --- .../templates/products/productSettings/productSettings.js | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js index 486a9bdc312..16d3cddc2d4 100644 --- a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js +++ b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js @@ -7,7 +7,6 @@ import Logger from "/client/modules/logger"; import { getPrimaryMediaForItem, ReactionProduct } from "/lib/api"; import { Products } from "/lib/collections"; import { isRevisionControlEnabled } from "/imports/plugins/core/revisions/lib/api"; -import { applyProductRevision } from "/lib/api/products"; function updateVariantProductField(variants, field, value) { return variants.map((variant) => Meteor.call("products/updateProductField", variant._id, field, value)); @@ -30,7 +29,7 @@ Template.productSettings.onCreated(function () { _id: { $in: productIds } - }).map((product) => applyProductRevision(product)); + }) this.state.set("productIds", productIds); this.state.set("products", products); From e3c75814fe78a9c8c6642bf029163e83ac3e8a63 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 10:57:12 -0700 Subject: [PATCH 10/57] refactor: remove `applyProductRevision` helper --- lib/api/products.js | 48 +++------------------------------------------ 1 file changed, 3 insertions(+), 45 deletions(-) diff --git a/lib/api/products.js b/lib/api/products.js index d4a77a7e57f..c920398e958 100644 --- a/lib/api/products.js +++ b/lib/api/products.js @@ -33,48 +33,6 @@ import { MetaData } from "/lib/api/router/metadata"; */ const ReactionProduct = new ReactiveDict("currentProduct"); -/** - * @name applyProductRevision - * @method - * @memberof ReactionProduct - * @summary Apply revision to product - * @example applyProductRevision(product) - * @param {Object} product product - * @return {Object|null} product or null, if no product found - */ -export function applyProductRevision(product) { - if (product) { - if (product.__revisions && product.__revisions.length) { - const cleanProduct = Object.assign({}, product); - delete cleanProduct.__revisions; - let revisedProduct; - // check for product revisions and set that as the current product - for (const revision of product.__revisions) { - if (!revision.parentDocument) { - revisedProduct = product.__revisions[0].documentData; - } - } - - // if there are no revision to product (image and/or tag only) just set the original product as the product - if (!revisedProduct) { - revisedProduct = cleanProduct; - } - - return Object.assign( - {}, - revisedProduct, - { - __published: cleanProduct, - __draft: product.__revisions[0] - } - ); - } - return product; - } - - return null; -} - /** * @name variantIsSelected * @method @@ -199,7 +157,7 @@ ReactionProduct.setProduct = (currentProductId, currentVariantId) => { // Update the meta data when a product is selected MetaData.init(Router.current()); - return applyProductRevision(product); + return product; }; /** @@ -244,7 +202,7 @@ ReactionProduct.selectedVariantId = () => { ReactionProduct.selectedVariant = function () { const id = ReactionProduct.selectedVariantId(); if (typeof id === "string") { - return applyProductRevision(Products.findOne(id)); + return Products.findOne(id); } return []; }; @@ -273,7 +231,7 @@ ReactionProduct.selectedTopVariant = function () { ReactionProduct.selectedProduct = function () { const id = ReactionProduct.selectedProductId(); if (typeof id === "string") { - return applyProductRevision(Products.findOne(id)); + return Products.findOne(id); } return undefined; }; From 146fcc3d7163064cad9c917988c1c50d447d7356 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Thu, 10 May 2018 15:58:58 -0700 Subject: [PATCH 11/57] fix: fetch products --- .../templates/products/productSettings/productSettings.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js index 16d3cddc2d4..514d4af1124 100644 --- a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js +++ b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js @@ -29,7 +29,7 @@ Template.productSettings.onCreated(function () { _id: { $in: productIds } - }) + }).fetch(); this.state.set("productIds", productIds); this.state.set("products", products); From ebde6976b7bee5f765c5f3a2946857329a7a7c01 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:15:25 -0700 Subject: [PATCH 12/57] refactor: remove `isRevisionControlEnabled` stub --- imports/plugins/core/catalog/server/methods/catalog.app-test.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.app-test.js b/imports/plugins/core/catalog/server/methods/catalog.app-test.js index 7dbbce8cfe1..aa84ddc57eb 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.app-test.js +++ b/imports/plugins/core/catalog/server/methods/catalog.app-test.js @@ -9,7 +9,6 @@ import { Reaction } from "/server/api"; import * as Collections from "/lib/collections"; import Fixtures from "/server/imports/fixtures"; import { PublicationCollector } from "meteor/johanbrook:publication-collector"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; import { publishProductToCatalog } from "./catalog"; Fixtures(); @@ -21,7 +20,6 @@ describe("Catalog", function () { beforeEach(function () { createActiveShop({ _id: shopId }); sandbox = sinon.sandbox.create(); - sandbox.stub(RevisionApi, "isRevisionControlEnabled", () => true); }); afterEach(function () { From 0ce83cef870bd9dfa66b7e32dff645e505cec6b2 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:15:37 -0700 Subject: [PATCH 13/57] refactor: remove `isRevisionControlEnabled` stub --- .../publications/collections/product-publications.app-test.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/server/publications/collections/product-publications.app-test.js b/server/publications/collections/product-publications.app-test.js index 8321a8021b4..3a6780e0130 100644 --- a/server/publications/collections/product-publications.app-test.js +++ b/server/publications/collections/product-publications.app-test.js @@ -9,7 +9,6 @@ import { Reaction } from "/server/api"; import * as Collections from "/lib/collections"; import Fixtures from "/server/imports/fixtures"; import { PublicationCollector } from "meteor/johanbrook:publication-collector"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; Fixtures(); @@ -21,7 +20,6 @@ describe("Publication", function () { Collections.Shops.remove({}); createActiveShop({ _id: shopId }); sandbox = sinon.sandbox.create(); - sandbox.stub(RevisionApi, "isRevisionControlEnabled", () => true); }); afterEach(function () { From 678c131a8de99d89f78733d4086837cc46fa0381 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:15:50 -0700 Subject: [PATCH 14/57] refactor: remove `isRevisionControlEnabled` stub --- server/methods/catalog.app-test.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/server/methods/catalog.app-test.js b/server/methods/catalog.app-test.js index 0dcde14c0b1..dc3b96a08cf 100644 --- a/server/methods/catalog.app-test.js +++ b/server/methods/catalog.app-test.js @@ -12,7 +12,6 @@ import { sinon } from "meteor/practicalmeteor:sinon"; import { Roles } from "meteor/alanning:roles"; import { addProduct, addProductSingleVariant } from "/server/imports/fixtures/products"; import Fixtures from "/server/imports/fixtures"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; Fixtures(); @@ -43,7 +42,6 @@ describe("core product methods", function () { beforeEach(function () { sandbox = sinon.sandbox.create(); - sandbox.stub(RevisionApi, "isRevisionControlEnabled", () => true); Revisions.remove({}); }); From 593b3e9e1f18ce970be02a72aa14c24a3ccfbd76 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:16:01 -0700 Subject: [PATCH 15/57] refactor: remove `isRevisionControlEnabled` stub --- .../included/inventory/server/methods/inventory.app-test.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/imports/plugins/included/inventory/server/methods/inventory.app-test.js b/imports/plugins/included/inventory/server/methods/inventory.app-test.js index 91f56bdb3bf..98cdde81a95 100644 --- a/imports/plugins/included/inventory/server/methods/inventory.app-test.js +++ b/imports/plugins/included/inventory/server/methods/inventory.app-test.js @@ -8,7 +8,6 @@ import { expect } from "meteor/practicalmeteor:chai"; import { sinon } from "meteor/practicalmeteor:sinon"; import { addProduct } from "/server/imports/fixtures/products"; import Fixtures from "/server/imports/fixtures"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api/revisions"; Fixtures(); @@ -41,7 +40,6 @@ describe("inventory method", function () { beforeEach(function () { sandbox = sinon.sandbox.create(); - sandbox.stub(RevisionApi, "isRevisionControlEnabled", () => true); // again hack. w/o this we can't remove products from previous spec. Inventory.remove({}); // Empty Inventory }); From a0ffc6e1792da4151ee76a5af8fb7b25afcf8281 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:17:40 -0700 Subject: [PATCH 16/57] refactor: remove `isRevisionControlEnabled` Default isEnabled to true --- imports/plugins/core/dashboard/client/components/toolbar.js | 3 ++- .../core/dashboard/client/containers/toolbarContainer.js | 2 -- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/imports/plugins/core/dashboard/client/components/toolbar.js b/imports/plugins/core/dashboard/client/components/toolbar.js index 8983333e70b..2579c046a7f 100644 --- a/imports/plugins/core/dashboard/client/components/toolbar.js +++ b/imports/plugins/core/dashboard/client/components/toolbar.js @@ -35,7 +35,8 @@ class PublishControls extends Component { } static defaultProps = { - showViewAsControls: true + showViewAsControls: true, + isEnabled: true } componentDidMount() { diff --git a/imports/plugins/core/dashboard/client/containers/toolbarContainer.js b/imports/plugins/core/dashboard/client/containers/toolbarContainer.js index 72d5b12b406..4e89ce0e2ae 100644 --- a/imports/plugins/core/dashboard/client/containers/toolbarContainer.js +++ b/imports/plugins/core/dashboard/client/containers/toolbarContainer.js @@ -5,7 +5,6 @@ import { composeWithTracker } from "@reactioncommerce/reaction-components"; import { Reaction, i18next } from "/client/api"; import { Tags, Shops } from "/lib/collections"; import { AdminContextProvider } from "/imports/plugins/core/ui/client/providers"; -import { isRevisionControlEnabled } from "/imports/plugins/core/revisions/lib/api"; const handleAddProduct = () => { Reaction.setUserPreferences("reaction-dashboard", "viewAs", "administrator"); @@ -81,7 +80,6 @@ function composer(props, onData) { packageButtons, dashboardHeaderTemplate: props.data.dashboardHeader, isPreview: Reaction.isPreview(), - isEnabled: isRevisionControlEnabled(), isActionViewAtRootView: Reaction.isActionViewAtRootView(), actionViewIsOpen: Reaction.isActionViewOpen(), hasCreateProductAccess: Reaction.hasPermission("createProduct", Meteor.userId(), Reaction.getShopId()), From f2de5c1955266db758a9e20f62e2dbadaf0c6322 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:18:05 -0700 Subject: [PATCH 17/57] refactor: remove `isRevisionControlEnabled` Remove methods to apply revisions to media --- .../core/ui/client/containers/mediaGallery.js | 41 +------------------ 1 file changed, 1 insertion(+), 40 deletions(-) diff --git a/imports/plugins/core/ui/client/containers/mediaGallery.js b/imports/plugins/core/ui/client/containers/mediaGallery.js index 4d093e83ffd..3bf40a84c27 100644 --- a/imports/plugins/core/ui/client/containers/mediaGallery.js +++ b/imports/plugins/core/ui/client/containers/mediaGallery.js @@ -10,8 +10,6 @@ import { Meteor } from "meteor/meteor"; import MediaGallery from "../components/media/mediaGallery"; import { Logger, Reaction } from "/client/api"; import { ReactionProduct } from "/lib/api"; -import { Revisions } from "/lib/collections"; -import { isRevisionControlEnabled } from "/imports/plugins/core/revisions/lib/api"; import { Media } from "/imports/plugins/core/files/client"; const wrapComponent = (Comp) => ( @@ -213,18 +211,6 @@ const wrapComponent = (Comp) => ( } ); -function fetchMediaRevisions() { - const productId = ReactionProduct.selectedProductId(); - const mediaRevisions = Revisions.find({ - "parentDocument": productId, - "documentType": "image", - "workflow.status": { - $nin: ["revision/published"] - } - }).fetch(); - return mediaRevisions; -} - // resort the media in function sortMedia(media) { const sortedMedia = _.sortBy(media, (m) => { @@ -237,35 +223,10 @@ function sortMedia(media) { return sortedMedia; } -// Search through revisions and if we find one for the image, stick it on the object -function appendRevisionsToMedia(props, media) { - if (!isRevisionControlEnabled() || !Reaction.hasPermission(props.permission || ["createProduct"])) { - return media; - } - const mediaRevisions = fetchMediaRevisions(); - const newMedia = []; - for (const image of media) { - image.revision = undefined; - for (const revision of mediaRevisions) { - if (revision.documentId === image._id) { - image.revision = revision; - image.metadata.priority = revision.documentData.priority; - } - } - newMedia.push(image); - } - return sortMedia(newMedia); -} - function composer(props, onData) { - let media; let editable; const viewAs = Reaction.getUserPreferences("reaction-dashboard", "viewAs", "administrator"); - if (props.media) { - media = appendRevisionsToMedia(props, props.media); - } - if (viewAs === "customer") { editable = false; } else { @@ -274,7 +235,7 @@ function composer(props, onData) { onData(null, { editable, - media + media: sortMedia(props.media) }); } From 820444ee1c19172d6f7029d48e628e6ce6aa041f Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 11 May 2018 09:19:29 -0700 Subject: [PATCH 18/57] refactor: remove `isRevisionControlEnabled` conditional - Remove `isRevisionControlEnabled` conditional, keeping the contents of the block. - Remove the old publish logic --- .../productSettings/productSettings.js | 35 +++++++------------ 1 file changed, 12 insertions(+), 23 deletions(-) diff --git a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js index 514d4af1124..5afe32a9b7d 100644 --- a/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js +++ b/imports/plugins/included/product-variant/client/templates/products/productSettings/productSettings.js @@ -6,7 +6,6 @@ import { Reaction } from "/client/api"; import Logger from "/client/modules/logger"; import { getPrimaryMediaForItem, ReactionProduct } from "/lib/api"; import { Products } from "/lib/collections"; -import { isRevisionControlEnabled } from "/imports/plugins/core/revisions/lib/api"; function updateVariantProductField(variants, field, value) { return variants.map((variant) => Meteor.call("products/updateProductField", variant._id, field, value)); @@ -121,28 +120,18 @@ Template.productSettings.events({ const instance = Template.instance(); const products = instance.state.get("products") || []; - if (isRevisionControlEnabled()) { - for (const product of products) { - // Update the visibility using the first selected product to determine the proper - // visibility toggle. This is to ensure that all selected products will become visible or not visible - // at the same time so it's not confusing. - Meteor.call("products/updateProductField", product._id, "isVisible", !products[0].isVisible); - // update the variants visibility - const variants = Products.find({ - ancestors: { - $in: [product._id] - } - }); - updateVariantProductField(variants, "isVisible", !products[0].isVisible); - } - } else { - // The legacy behavior will bulk toggle visibilty of each product seperatly. - // - // Example: - // If you selected 10 products, and 5 were visible and 5 were not visible, and then - // clicked the visibility button, 5 products would switched from not visible to visible, and the other 5 - // would be swiched from visible to not visible. - ReactionProduct.publishProduct(products); + for (const product of products) { + // Update the visibility using the first selected product to determine the proper + // visibility toggle. This is to ensure that all selected products will become visible or not visible + // at the same time so it's not confusing. + Meteor.call("products/updateProductField", product._id, "isVisible", !products[0].isVisible); + // update the variants visibility + const variants = Products.find({ + ancestors: { + $in: [product._id] + } + }); + updateVariantProductField(variants, "isVisible", !products[0].isVisible); } }, "click [data-event-action=cloneProduct]"() { From 193f166d6fdaf717aa142a3717944f1bd2e7ca4c Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 14 May 2018 16:14:55 -0700 Subject: [PATCH 19/57] refactor: remove dependency on revision control system --- imports/plugins/core/files/server/methods.js | 131 ++++--------------- 1 file changed, 29 insertions(+), 102 deletions(-) diff --git a/imports/plugins/core/files/server/methods.js b/imports/plugins/core/files/server/methods.js index 52d54cb37c7..af58d436f65 100644 --- a/imports/plugins/core/files/server/methods.js +++ b/imports/plugins/core/files/server/methods.js @@ -1,9 +1,7 @@ import { Meteor } from "meteor/meteor"; import { check } from "meteor/check"; -import { Hooks, Reaction } from "/server/api"; -import { MediaRecords, Revisions } from "/lib/collections"; -import { Media } from "/imports/plugins/core/files/server"; -import { RevisionApi } from "/imports/plugins/core/revisions/lib/api"; +import { Reaction } from "/server/api"; +import { MediaRecords } from "/lib/collections"; /** * Media-related Meteor methods @@ -13,7 +11,7 @@ import { RevisionApi } from "/imports/plugins/core/revisions/lib/api"; /** * @method updateMediaMetadata * @memberof Media/Methods - * @summary updates media record in revision control. + * @summary updates media record control. * @param {String} fileRecordId - _id of updated file record. * @param {Object} metadata - metadata from updated media file. * @return {Boolean} @@ -22,95 +20,35 @@ import { RevisionApi } from "/imports/plugins/core/revisions/lib/api"; async function updateMediaMetadata(fileRecordId, metadata) { check(fileRecordId, String); check(metadata, Object); - if (RevisionApi.isRevisionControlEnabled()) { - if (metadata.productId) { - const existingRevision = Revisions.findOne({ - "documentId": fileRecordId, - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }); - if (existingRevision) { - const updatedMetadata = Object.assign({}, existingRevision.documentData, metadata); - // Special case where if we have both added and reordered images before publishing we don't want to overwrite - // the workflow status since it would be "unpublished" - if (existingRevision.documentData.workflow === "published" || existingRevision.changeType === "insert") { - updatedMetadata.workflow = "published"; - } - Revisions.update({ _id: existingRevision._id }, { - $set: { - documentData: updatedMetadata - } - }); - Hooks.Events.run("afterRevisionsUpdate", Meteor.userId(), { - ...existingRevision, - documentData: updatedMetadata - }); - } else { - Revisions.insert({ - documentId: fileRecordId, - documentData: metadata, - documentType: "image", - parentDocument: metadata.productId, - changeType: "update", - workflow: { - status: "revision/update" - } - }); - } - return false; + const result = MediaRecords.update({ + _id: fileRecordId + }, { + $set: { + metadata } - } - // for non-product images, just ignore and keep on moving - return true; + }); + + return result === 1; } /** * @name media/insert * @method * @memberof Media/Methods - * @summary insert a new media record and add it to revision control. + * @summary insert a new media record. * @param {Object} fileRecord - document from file collection upload. * @return {String} - _id of the new inserted media record. */ export async function insertMedia(fileRecord) { check(fileRecord, Object); - const mediaRecordId = await MediaRecords.insert(fileRecord); - - if (RevisionApi.isRevisionControlEnabled() && fileRecord.metadata.workflow !== "published") { - if (fileRecord.metadata.productId) { - const revisionMetadata = Object.assign({}, fileRecord.metadata); - revisionMetadata.workflow = "published"; - Revisions.insert({ - documentId: mediaRecordId, - documentData: revisionMetadata, - documentType: "image", - parentDocument: fileRecord.metadata.productId, - changeType: "insert", - workflow: { - status: "revision/update" - } - }); - MediaRecords.update({ - _id: mediaRecordId - }, { - $set: { - "metadata.workflow": "unpublished" - } - }); - } else { - MediaRecords.update({ - _id: mediaRecordId - }, { - $set: { - "metadata.workflow": "published" - } - }); + const mediaRecordId = await MediaRecords.insert({ + ...fileRecord, + metadata: { + ...fileRecord.metadata, + workflow: "published" } - } + }); return mediaRecordId; } @@ -119,33 +57,22 @@ export async function insertMedia(fileRecord) { * @name media/remove * @method * @memberof Media/Methods - * @summary removes media file and updates record in revision control. + * @summary unpublished media file by updating it's workflow * @param {String} fileRecordId - _id of file record to be deleted. * @return {Boolean} */ export async function removeMedia(fileRecordId) { check(fileRecordId, String); - const { metadata } = MediaRecords.findOne({ _id: fileRecordId }); - if (RevisionApi.isRevisionControlEnabled() && metadata.workflow && metadata.workflow === "unpublished") { - Revisions.remove({ - documentId: fileRecordId - }); - Media.remove(fileRecordId); - return true; - } else if (metadata.productId) { - Revisions.insert({ - documentId: fileRecordId, - documentData: metadata, - documentType: "image", - parentDocument: metadata.productId, - changeType: "remove", - workflow: { - status: "revision/update" - } - }); - return true; - } - return false; + + const result = MediaRecords.update({ + _id: fileRecordId + }, { + $set: { + "metadata.workflow": "archived" + } + }); + + return result === 1; } /** From baaca842a6ba2f98bf17b0acdeb4a24288982e0c Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:11:52 -0700 Subject: [PATCH 20/57] refactor: remove revision control hooks --- server/imports/fixtures/products.js | 11 ++--------- 1 file changed, 2 insertions(+), 9 deletions(-) diff --git a/server/imports/fixtures/products.js b/server/imports/fixtures/products.js index 34af01077fa..6ed16b16c76 100755 --- a/server/imports/fixtures/products.js +++ b/server/imports/fixtures/products.js @@ -3,7 +3,6 @@ import _ from "lodash"; import { Factory } from "meteor/dburles:factory"; import { Products, Tags } from "/lib/collections"; import { getShop } from "./shops"; -import { Hooks } from "/server/api"; /** * @method metaField @@ -98,14 +97,10 @@ export function productVariant(options = {}) { */ export function addProduct(options = {}) { const product = Factory.create("product", options); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", product); // top level variant const variant = Factory.create("variant", Object.assign({}, productVariant(options), { ancestors: [product._id] })); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", variant); - const variant2 = Factory.create("variant", Object.assign({}, productVariant(options), { ancestors: [product._id, variant._id] })); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", variant2); - const variant3 = Factory.create("variant", Object.assign({}, productVariant(options), { ancestors: [product._id, variant._id] })); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", variant3); + Factory.create("variant", Object.assign({}, productVariant(options), { ancestors: [product._id, variant._id] })); + Factory.create("variant", Object.assign({}, productVariant(options), { ancestors: [product._id, variant._id] })); return product; } @@ -118,10 +113,8 @@ export function addProduct(options = {}) { */ export function addProductSingleVariant() { const product = Factory.create("product"); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", product); // top level variant const variant = Factory.create("variant", Object.assign({}, productVariant(), { ancestors: [product._id] })); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", variant); return { product, variant }; } From 2f45c0b092718438267b6e2c50bf93769ddfd265 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:12:15 -0700 Subject: [PATCH 21/57] refactor: remove revision control hooks --- server/methods/catalog.js | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-) diff --git a/server/methods/catalog.js b/server/methods/catalog.js index 0ac6119fe41..5356ec18a39 100644 --- a/server/methods/catalog.js +++ b/server/methods/catalog.js @@ -497,7 +497,6 @@ Meteor.methods({ let newId; try { - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", clone); newId = Products.insert(clone, { validate: false }); const newProduct = Products.findOne(newId); Hooks.Events.run("afterInsertCatalogProduct", newProduct); @@ -572,8 +571,6 @@ Meteor.methods({ const _id = Products.insert(assembledVariant); Hooks.Events.run("afterInsertCatalogProduct", assembledVariant); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", Products.findOne({ _id })); - Logger.debug(`products/createVariant: created variant: ${newVariantId} for ${parentId}`); return newVariantId; @@ -785,7 +782,6 @@ Meteor.methods({ newProduct._id ); } - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", newProduct); result = Products.insert(newProduct, { validate: false }); Hooks.Events.run("afterInsertCatalogProduct", newProduct); results.push(result); @@ -814,7 +810,6 @@ Meteor.methods({ delete newVariant.createdAt; delete newVariant.publishedAt; // TODO can variant have this param? - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", newVariant); result = Products.insert(newVariant, { validate: false }); Hooks.Events.run("afterInsertCatalogProduct", newVariant); copyMedia(productNewId, variant._id, variantNewId); @@ -847,27 +842,19 @@ Meteor.methods({ throw new Meteor.Error("invalid-parameter", "Product should have a valid shopId"); } - // Create product revision - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", product); - return Products.insert(product); } const newSimpleProduct = createProduct(); - // Create simple product revision - Hooks.Events.run("afterInsertCatalogProductInsertRevision", newSimpleProduct); - - const newVariant = createProduct({ + // Create Variant + createProduct({ ancestors: [newSimpleProduct._id], price: 0.00, title: "", type: "variant" // needed for multi-schema }); - // Create variant revision - Hooks.Events.run("afterInsertCatalogProductInsertRevision", newVariant); - return newSimpleProduct._id; }, From 972b9a548b741d3316edd149a02e66e69a174f10 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:38:17 -0700 Subject: [PATCH 22/57] refactor: use standard catalog api --- server/methods/catalog.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/methods/catalog.js b/server/methods/catalog.js index 5356ec18a39..e399359d9b2 100644 --- a/server/methods/catalog.js +++ b/server/methods/catalog.js @@ -4,7 +4,7 @@ import { check, Match } from "meteor/check"; import { EJSON } from "meteor/ejson"; import { Meteor } from "meteor/meteor"; import { ReactionProduct } from "/lib/api"; -import { ProductRevision as Catalog } from "/imports/plugins/core/revisions/server/hooks"; +import Catalog from "/lib/api/catalog"; import { Hooks, Logger, Reaction } from "/server/api"; import { MediaRecords, Products, Revisions, Tags } from "/lib/collections"; import { Media } from "/imports/plugins/core/files/server"; From 0efddf83b9492bec861b433a7b77f8d710f19b3a Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:38:26 -0700 Subject: [PATCH 23/57] refactor: use standard catalog api --- imports/plugins/core/catalog/server/methods/catalog.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index f258bea0e14..11d9687a8ce 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -3,7 +3,7 @@ import { check, Match } from "meteor/check"; import { Products, Catalog as CatalogCollection } from "/lib/collections"; import { Logger, Reaction } from "/server/api"; import { Media } from "/imports/plugins/core/files/server"; -import { ProductRevision as Catalog } from "/imports/plugins/core/revisions/server/hooks"; +import Catalog from "/lib/api"; /** * @method isSoldOut From 0c710bb93ab75603e2a46063fb5b988d51d30ffc Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:45:25 -0700 Subject: [PATCH 24/57] refactor: don't depend on the result of the `beforeUpdateCatalogProduct` hook --- server/methods/catalog.js | 14 ++++---------- 1 file changed, 4 insertions(+), 10 deletions(-) diff --git a/server/methods/catalog.js b/server/methods/catalog.js index e399359d9b2..b49a0eda863 100644 --- a/server/methods/catalog.js +++ b/server/methods/catalog.js @@ -373,23 +373,17 @@ function createProduct(props = null) { function updateCatalogProduct(userId, selector, modifier, validation) { const product = Products.findOne(selector); - const shouldUpdateProduct = Hooks.Events.run("beforeUpdateCatalogProduct", product, { + Hooks.Events.run("beforeUpdateCatalogProduct", product, { userId, modifier, validation }); - if (shouldUpdateProduct) { - const result = Products.update(selector, modifier, validation); + const result = Products.update(selector, modifier, validation); - Hooks.Events.run("afterUpdateCatalogProduct", product, { modifier }); + Hooks.Events.run("afterUpdateCatalogProduct", product, { modifier }); - return result; - } - - Logger.debug(`beforeUpdateCatalogProduct hook returned falsy, not updating catalog product`); - - return false; + return result; } From 3c374ab535f8154d5be666d07236cede66a14659 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 14:46:07 -0700 Subject: [PATCH 25/57] refactor: fix lint issue --- server/methods/catalog.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/server/methods/catalog.js b/server/methods/catalog.js index b49a0eda863..567a1f448f2 100644 --- a/server/methods/catalog.js +++ b/server/methods/catalog.js @@ -562,7 +562,7 @@ Meteor.methods({ } Hooks.Events.run("beforeInsertCatalogProduct", assembledVariant); - const _id = Products.insert(assembledVariant); + Products.insert(assembledVariant); Hooks.Events.run("afterInsertCatalogProduct", assembledVariant); Logger.debug(`products/createVariant: created variant: ${newVariantId} for ${parentId}`); From 6aa5e3b1f2ef0d74227bb5a997180d00962cb96e Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:27:08 -0700 Subject: [PATCH 26/57] refactor: update tests to not depend on revision control Remove tests related only to revision control features. --- server/methods/catalog.app-test.js | 505 ++--------------------------- 1 file changed, 27 insertions(+), 478 deletions(-) diff --git a/server/methods/catalog.app-test.js b/server/methods/catalog.app-test.js index dc3b96a08cf..5d984aa8e53 100644 --- a/server/methods/catalog.app-test.js +++ b/server/methods/catalog.app-test.js @@ -6,7 +6,7 @@ import { Meteor } from "meteor/meteor"; import { check, Match } from "meteor/check"; import { Factory } from "meteor/dburles:factory"; import { Reaction } from "/server/api"; -import { Products, Revisions, Tags } from "/lib/collections"; +import { Products, Tags } from "/lib/collections"; import { expect } from "meteor/practicalmeteor:chai"; import { sinon } from "meteor/practicalmeteor:sinon"; import { Roles } from "meteor/alanning:roles"; @@ -42,7 +42,6 @@ describe("core product methods", function () { beforeEach(function () { sandbox = sinon.sandbox.create(); - Revisions.remove({}); }); afterEach(function () { @@ -164,7 +163,7 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not update individual variant by admin passing in full object", function (done) { + it("should update individual variant by admin passing in full object", function (done) { sandbox.stub(Reaction, "hasPermission", () => true); const product = addProduct(); let variant = Products.findOne({ ancestors: [product._id] }); @@ -172,55 +171,11 @@ describe("core product methods", function () { variant["price"] = 7; Meteor.call("products/updateVariant", variant); variant = Products.findOne({ ancestors: [product._id] }); - expect(variant.price).to.not.equal(7); - expect(variant.title).to.not.equal("Updated Title"); - - return done(); - }); - - it("should update individual variant revision by admin passing in full object", function (done) { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.find({ ancestors: [product._id] }).fetch()[0]; - variant["title"] = "Updated Title"; - variant["price"] = 7; - Meteor.call("products/updateVariant", variant); - const variantRevision = Revisions.find({ documentId: variant._id }).fetch()[0]; - expect(variantRevision.documentData.price).to.equal(7); - expect(variantRevision.documentData.title).to.equal("Updated Title"); + expect(variant.price).to.equal(7); + expect(variant.title).to.equal("Updated Title"); return done(); }); - - it("should not update individual variant by admin passing in partial object", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.findOne({ ancestors: [product._id] }); - Meteor.call("products/updateVariant", { - _id: variant._id, - title: "Updated Title", - price: 7 - }); - const updatedVariant = Products.findOne(variant._id); - expect(updatedVariant.price).to.not.equal(7); - expect(updatedVariant.title).to.not.equal("Updated Title"); - expect(updatedVariant.optionTitle).to.equal(variant.optionTitle); - }); - - it("should update individual variant revision by admin passing in partial object", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.find({ ancestors: [product._id] }).fetch()[0]; - Meteor.call("products/updateVariant", { - _id: variant._id, - title: "Updated Title", - price: 7 - }); - const updatedVariantRevision = Revisions.findOne({ documentId: variant._id }); - expect(updatedVariantRevision.documentData.price).to.equal(7); - expect(updatedVariantRevision.documentData.title).to.equal("Updated Title"); - expect(updatedVariantRevision.documentData.optionTitle).to.equal(variant.optionTitle); - }); }); describe("products/deleteVariant", function () { @@ -233,38 +188,16 @@ describe("core product methods", function () { expect(removeProductSpy).to.not.have.been.called; }); - it("should not mark top-level variant as deleted", function () { + it("should mark top-level variant as deleted", function () { sandbox.stub(Reaction, "hasPermission", () => true); const product = addProduct(); let variant = Products.findOne({ ancestors: [product._id] }); expect(variant.isDeleted).to.equal(false); Meteor.call("products/deleteVariant", variant._id); variant = Products.findOne(variant._id); - expect(variant.isDeleted).to.not.equal(true); + expect(variant.isDeleted).to.equal(true); }); - it("should mark top-level variant revision as deleted", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.findOne({ ancestors: [product._id] }); - expect(variant.isDeleted).to.equal(false); - Meteor.call("products/deleteVariant", variant._id); - const variantRevision = Revisions.findOne({ documentId: variant._id }); - expect(variantRevision.documentData.isDeleted).to.equal(true); - }); - - it("should publish top-level variant as deleted", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.findOne({ ancestors: [product._id] }); - expect(variant.isDeleted).to.equal(false); - Meteor.call("products/deleteVariant", variant._id); - Meteor.call("revisions/publish", variant._id); - const publishedProduct = Products.findOne(variant._id); - expect(publishedProduct.isDeleted).to.equal(true); - }); - - it("should mark all child variants (options) as deleted if top-level variant deleted", function () { sandbox.stub(Reaction, "hasPermission", () => true); const product = addProduct(); @@ -433,28 +366,11 @@ describe("core product methods", function () { expect(removeProductSpy).to.not.have.been.called; }); - it("should not mark product as deleted by admin", function () { + it("should mark product as deleted by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); Meteor.call("products/archiveProduct", product._id); product = Products.findOne(product._id); - expect(product.isDeleted).to.equal(false); - }); - - it("should mark product revision as deleted by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - Meteor.call("products/archiveProduct", product._id); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.isDeleted).to.equal(true); - }); - - it("should publish product revision marked as deleted by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/archiveProduct", product._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); expect(product.isDeleted).to.equal(true); }); }); @@ -471,56 +387,20 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not update product field by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "Updated Title"); - product = Products.findOne(product._id); - expect(product.title).to.not.equal("Updated Title"); - }); - - it("should update product revision field by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "Updated Title"); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.title).to.equal("Updated Title"); - }); - - it("should publish changes to product field by admin", function () { + it("should update product field by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); Meteor.call("products/updateProductField", product._id, "title", "Updated Title"); - Meteor.call("revisions/publish", product._id); product = Products.findOne(product._id); expect(product.title).to.equal("Updated Title"); }); - it("should not update variant fields", function () { + it("should update variant fields", function () { sandbox.stub(Reaction, "hasPermission", () => true); const product = addProduct(); let variant = Products.findOne({ ancestors: [product._id] }); Meteor.call("products/updateProductField", variant._id, "title", "Updated Title"); variant = Products.findOne(variant._id); - expect(variant.title).to.not.equal("Updated Title"); - }); - - it("should update variant revision fields", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const variant = Products.findOne({ ancestors: [product._id] }); - Meteor.call("products/updateProductField", variant._id, "title", "Updated Title"); - const variantRevision = Revisions.findOne({ documentId: variant._id }); - expect(variantRevision.documentData.title).to.equal("Updated Title"); - }); - - it("should publish update for variant fields", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - let variant = Products.findOne({ ancestors: [product._id] }); - Meteor.call("products/updateProductField", variant._id, "title", "Updated Title"); - Meteor.call("revisions/publish", product._id); - variant = Products.findOne(variant._id); expect(variant.title).to.equal("Updated Title"); }); }); @@ -540,7 +420,7 @@ describe("core product methods", function () { expect(insertTagsSpy).to.not.have.been.called; }); - it("should not new tag when passed tag name and null ID by admin", function () { + it("should create new tag when passed tag name and null ID by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); const tagName = "Product Tag"; @@ -549,59 +429,10 @@ describe("core product methods", function () { const tag = Tags.findOne({ name: tagName }); expect(tag.slug).to.equal(Reaction.getSlug(tagName)); product = Products.findOne(product._id); - expect(product.hashtags).to.not.contain(tag._id); - }); - - it("should add new tag to product revision when passed tag name and null ID by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const tagName = "Product Tag"; - expect(Tags.findOne({ name: tagName })).to.be.undefined; - Meteor.call("products/updateProductTags", product._id, tagName, null); - const tag = Tags.findOne({ name: tagName }); - expect(tag.slug).to.equal(Reaction.getSlug(tagName)); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.hashtags).to.contain(tag._id); - }); - - it("should publish new product tag when passed tag name and null ID by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const tagName = "Product Tag"; - expect(Tags.findOne({ name: tagName })).to.be.undefined; - Meteor.call("products/updateProductTags", product._id, tagName, null); - const tag = Tags.findOne({ name: tagName }); - expect(tag.slug).to.equal(Reaction.getSlug(tagName)); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); expect(product.hashtags).to.contain(tag._id); }); - it("should not add existing tag when passed existing tag and tag._id by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const tag = Factory.create("tag"); - expect(Tags.find().count()).to.equal(1); - expect(product.hashtags).to.not.contain(tag._id); - Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); - expect(Tags.find().count()).to.equal(1); - product = Products.findOne(product._id); - expect(product.hashtags).to.not.contain(tag._id); - }); - - it("should add existing tag to product revision when passed existing tag and tag._id by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const tag = Factory.create("tag"); - expect(Tags.find().count()).to.equal(1); - expect(product.hashtags).to.not.contain(tag._id); - Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); - expect(Tags.find().count()).to.equal(1); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.hashtags).to.contain(tag._id); - }); - - it("should publish existing tag for product when passed existing tag and tag._id by admin", function () { + it("should add existing tag when passed existing tag and tag._id by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); const tag = Factory.create("tag"); @@ -609,7 +440,6 @@ describe("core product methods", function () { expect(product.hashtags).to.not.contain(tag._id); Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); expect(Tags.find().count()).to.equal(1); - Meteor.call("revisions/publish", product._id); product = Products.findOne(product._id); expect(product.hashtags).to.contain(tag._id); }); @@ -631,70 +461,23 @@ describe("core product methods", function () { expect(removeTagsSpy).to.not.have.been.called; }); - it("should not remove product tag by admin", function () { + it("should remove product tag by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); const tag = Factory.create("tag"); - // Update product tags and publish so the original prodcut will have the tags + // Update product tags and publish so the original product will have the tags Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); - Meteor.call("revisions/publish", product._id); product = Products.findOne(product._id); expect(product.hashtags).to.contain(tag._id); expect(Tags.find().count()).to.equal(1); - // Remove the tag from the published prouct and ensure it didn't succeed. + // Remove the tag from the published product and ensure it didn't succeed. // Revision control should stop the published product from being changed. Meteor.call("products/removeProductTag", product._id, tag._id); product = Products.findOne(product._id); - expect(product.hashtags).to.contain(tag._id); - expect(Tags.find().count()).to.equal(1); - }); - - it("should remove tag in product revision by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const tag = Factory.create("tag"); - - // Update product tags and publish so the original prodcut will have the tags - Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.hashtags).to.contain(tag._id); - expect(Tags.find().count()).to.equal(1); - - // Remove the tag from the published prouct and ensure it changed in the revision. - Meteor.call("products/removeProductTag", product._id, tag._id); - const productRevision = Revisions.findOne({ - "documentId": product._id, - "workflow.status": { $nin: ["revision/published"] } - }); - expect(productRevision.documentData.hashtags).to.not.contain(tag._id); - expect(Tags.find().count()).to.equal(1); - }); - - it("should publish remove product tag by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - - // Update product tags and publish so the original prodcut will have the tags - const tag = Factory.create("tag"); - Meteor.call("products/updateProductTags", product._id, tag.name, tag._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.hashtags).to.contain(tag._id); - expect(Tags.find().count()).to.equal(1); - - // Remove the tag from the published prouct which should create a revision. - // Then publish that revision and ensure that it published product changed. - Meteor.call("products/removeProductTag", product._id, tag._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - const tags = Tags.find(); expect(product.hashtags).to.not.contain(tag._id); - expect(tags.count()).to.equal(1); - // Tag should not be deleted, it should just be removed from the product - expect(tags.fetch()[0].isDeleted).to.equal(false); + expect(Tags.find().count()).to.equal(0); }); }); @@ -709,70 +492,13 @@ describe("core product methods", function () { expect(productUpdateSpy).to.not.have.been.called; }); - it("should not set handle for product by admin", function () { + it("should set handle for product by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); - const productHandle = product.handle; Meteor.call("products/updateProductField", product._id, "title", "new product name"); Meteor.call("products/setHandle", product._id); product = Products.findOne(product._id); - expect(product.handle).to.equal(productHandle); - }); - - it("should set handle correctly on product revision", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - const revision = Revisions.findOne({ documentId: product._id }); - expect(revision.documentData.handle).to.not.equal("new-second-product-name"); - }); - - it("should not set handle on published product", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - product = Products.findOne(product._id); - expect(product.handle).to.not.equal("new-second-product-name"); - }); - - it("should publish handle correctly", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.handle).to.not.equal("new-second-product-name"); - }); - - it("unpublished products with the same title should not receive correct handle", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - product = Products.findOne(product._id); - expect(product.handle).to.not.equal("new-second-product-name-copy"); - }); - - it("products with the same title should receive correct handle on revision", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.handle).to.not.equal("new-second-product-name-copy"); - }); - - it("products with the same title should receive correct handle when published", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateProductField", product._id, "title", "new second product name"); - Meteor.call("products/setHandle", product._id); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.handle).to.not.equal("new-second-product-name-copy"); + expect(product.handle).to.equal(product._id); }); }); @@ -792,30 +518,11 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not set handle tag for product by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const tag = Factory.create("tag"); - Meteor.call("products/setHandleTag", product._id, tag._id); - product = Products.findOne(product._id); - expect(product.handle).to.not.equal(tag.slug); - }); - - it("should set handle tag for product revision by admin", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const tag = Factory.create("tag"); - Meteor.call("products/setHandleTag", product._id, tag._id); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.handle).to.equal(tag.slug); - }); - - it("should publish set handle tag for product by admin", function () { + it("should set handle tag for product by admin", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); const tag = Factory.create("tag"); Meteor.call("products/setHandleTag", product._id, tag._id); - Meteor.call("revisions/publish", product._id); product = Products.findOne(product._id); expect(product.handle).to.equal(tag.slug); }); @@ -838,7 +545,7 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not update product position by admin", function (done) { + it("should update product position by admin", function (done) { sandbox.stub(Reaction, "hasPermission", () => true); const product = addProduct(); const tag = Factory.create("tag"); @@ -852,46 +559,7 @@ describe("core product methods", function () { product._id, position, tag.slug )).to.not.throw(Meteor.Error, /Access Denied/); const updatedProduct = Products.findOne(product._id); - expect(updatedProduct.positions).to.be.undefined; - - return done(); - }); - - it("should update product revision position by admin", function (done) { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const tag = Factory.create("tag"); - const position = { - position: 0, - weight: 0, - updatedAt: new Date() - }; - expect(() => Meteor.call( - "products/updateProductPosition", - product._id, position, tag.slug - )).to.not.throw(Meteor.Error, /Access Denied/); - const updatedProductRevision = Revisions.findOne({ documentId: product._id }); - expect(updatedProductRevision.documentData.positions[tag.slug].position).to.equal(0); - - return done(); - }); - - it("should publish product position by admin", function (done) { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - const tag = Factory.create("tag"); - const position = { - position: 0, - weight: 0, - updatedAt: new Date() - }; - expect(() => Meteor.call( - "products/updateProductPosition", - product._id, position, tag.slug - )).to.not.throw(Meteor.Error, /Access Denied/); - Meteor.call("revisions/publish", product._id); - const updatedProduct = Products.findOne(product._id); - expect(updatedProduct.positions[tag.slug].position).to.equal(0); + expect(updatedProduct.positions).to.be.defined; return done(); }); @@ -908,49 +576,7 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not update variants' position", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const { variant: variant1 } = addProductSingleVariant(); - const { variant: variant2 } = addProductSingleVariant(); - const { variant: variant3 } = addProductSingleVariant(); - - expect(variant1.index).to.be.undefined; - expect(variant2.index).to.be.undefined; - expect(variant3.index).to.be.undefined; - - Meteor.call("products/updateVariantsPosition", [ - variant2._id, variant3._id, variant1._id - ]); - const modifiedVariant1 = Products.findOne(variant1._id); - const modifiedVariant2 = Products.findOne(variant2._id); - const modifiedVariant3 = Products.findOne(variant3._id); - expect(modifiedVariant1.index).to.be.undefined; - expect(modifiedVariant2.index).to.be.undefined; - expect(modifiedVariant3.index).to.be.undefined; - }); - - it("should update variants' revision position", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const { variant: variant1 } = addProductSingleVariant(); - const { variant: variant2 } = addProductSingleVariant(); - const { variant: variant3 } = addProductSingleVariant(); - - expect(variant1.index).to.be.undefined; - expect(variant2.index).to.be.undefined; - expect(variant3.index).to.be.undefined; - - Meteor.call("products/updateVariantsPosition", [ - variant2._id, variant3._id, variant1._id - ]); - const modifiedVariantRevision1 = Revisions.findOne({ documentId: variant1._id }); - const modifiedVariantRevision2 = Revisions.findOne({ documentId: variant2._id }); - const modifiedVariantRevision3 = Revisions.findOne({ documentId: variant3._id }); - expect(modifiedVariantRevision1.documentData.index).to.equal(2); - expect(modifiedVariantRevision2.documentData.index).to.equal(0); - expect(modifiedVariantRevision3.documentData.index).to.equal(1); - }); - - it("should publish variants' revision position", function () { + it("should update variants' position", function () { sandbox.stub(Reaction, "hasPermission", () => true); const { variant: variant1 } = addProductSingleVariant(); const { variant: variant2 } = addProductSingleVariant(); @@ -963,15 +589,12 @@ describe("core product methods", function () { Meteor.call("products/updateVariantsPosition", [ variant2._id, variant3._id, variant1._id ]); - Meteor.call("revisions/publish", [ - variant1._id, variant2._id, variant3._id - ]); const modifiedVariant1 = Products.findOne(variant1._id); const modifiedVariant2 = Products.findOne(variant2._id); const modifiedVariant3 = Products.findOne(variant3._id); - expect(modifiedVariant1.index).to.equal(2); - expect(modifiedVariant2.index).to.equal(0); - expect(modifiedVariant3.index).to.equal(1); + expect(modifiedVariant1.index).to.be(2); + expect(modifiedVariant2.index).to.be(0); + expect(modifiedVariant3.index).to.be(1); }); }); @@ -987,7 +610,7 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should not add meta fields by admin", function (done) { + it("should add meta fields by admin", function (done) { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); Meteor.call("products/updateMetaFields", product._id, { @@ -995,36 +618,7 @@ describe("core product methods", function () { value: "Spandex" }); product = Products.findOne(product._id); - expect(product.metafields.length).to.be.equal(0); - - return done(); - }); - - it("should add meta fields to product revision by admin", function (done) { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - Meteor.call("products/updateMetaFields", product._id, { - key: "Material", - value: "Spandex" - }); - const productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.metafields[0].key).to.equal("Material"); - expect(productRevision.documentData.metafields[0].value).to.equal("Spandex"); - - return done(); - }); - - it("should publish add meta fields by admin", function (done) { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - Meteor.call("products/updateMetaFields", product._id, { - key: "Material", - value: "Spandex" - }); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.metafields[0].key).to.equal("Material"); - expect(product.metafields[0].value).to.equal("Spandex"); + expect(product.metafields.length).to.be.equal(1); return done(); }); @@ -1039,60 +633,15 @@ describe("core product methods", function () { expect(updateProductSpy).to.not.have.been.called; }); - it("should let admin publish product changes", function () { + it("should let admin toggle product visibility", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); const { isVisible } = product; expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Access Denied/); - Meteor.call("revisions/publish", product._id); product = Products.findOne(product._id); - // We switch the visible state in `products/publishProdct` for revisions expect(product.isVisible).to.equal(!isVisible); }); - it("should not let admin toggle product visibility", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const { isVisible } = product; - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Access Denied/); - product = Products.findOne(product._id); - expect(product.isVisible).to.equal(isVisible); - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Bad Request/); - product = Products.findOne(product._id); - expect(product.isVisible).to.equal(isVisible); - }); - - it("should let admin toggle product revision visibility", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - const product = addProduct(); - let productRevision = Revisions.findOne({ documentId: product._id }); - const { isVisible } = productRevision.documentData; - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Access Denied/); - productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.isVisible).to.equal(!isVisible); - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Bad Request/); - productRevision = Revisions.findOne({ documentId: product._id }); - expect(productRevision.documentData.isVisible).to.equal(!isVisible); - }); - - it("should publish admin toggle product visibility", function () { - sandbox.stub(Reaction, "hasPermission", () => true); - let product = addProduct(); - const { isVisible } = product; // false - - // Toggle visible - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Access Denied/); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.isVisible).to.equal(!isVisible); - - // Toggle not visible - expect(() => Meteor.call("products/publishProduct", product._id)).to.not.throw(Meteor.Error, /Bad Request/); - Meteor.call("revisions/publish", product._id); - product = Products.findOne(product._id); - expect(product.isVisible).to.equal(isVisible); - }); - it("should not publish product when missing title", function () { sandbox.stub(Reaction, "hasPermission", () => true); let product = addProduct(); From 98dacee7bc2e5c782ed95044c71fc129a4ccc0cd Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:30:00 -0700 Subject: [PATCH 27/57] refactor: remove revision subscription --- .../client/containers/publishContainer.js | 43 +++---------------- 1 file changed, 6 insertions(+), 37 deletions(-) diff --git a/imports/plugins/core/catalog/client/containers/publishContainer.js b/imports/plugins/core/catalog/client/containers/publishContainer.js index e640e41083a..4a61099579c 100644 --- a/imports/plugins/core/catalog/client/containers/publishContainer.js +++ b/imports/plugins/core/catalog/client/containers/publishContainer.js @@ -2,7 +2,6 @@ import React, { Component } from "react"; import PropTypes from "prop-types"; import { composeWithTracker } from "@reactioncommerce/reaction-components"; import PublishControls from "../components/publishControls"; -import { Revisions } from "/lib/collections"; import { Meteor } from "meteor/meteor"; import TranslationProvider from "/imports/plugins/core/ui/client/providers/translationProvider"; import { Reaction, i18next } from "/client/api"; @@ -91,43 +90,13 @@ function composer(props, onData) { const viewAs = Reaction.getUserPreferences("reaction-dashboard", "viewAs", "administrator"); if (Array.isArray(props.documentIds) && props.documentIds.length) { - const subscription = Meteor.subscribe("ProductRevisions", props.documentIds); - - if (subscription.ready()) { - const revisions = Revisions.find({ - "$or": [ - { - documentId: { - $in: props.documentIds - } - }, - { - "documentData.ancestors": { - $in: props.documentIds - } - }, - { - parentDocument: { - $in: props.documentIds - } - } - ], - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }).fetch(); - - onData(null, { - documentIds: props.documentIds, - documents: props.documents, - revisions, - isPreview: viewAs === "customer" - }); + onData(null, { + documentIds: props.documentIds, + documents: props.documents, + isPreview: viewAs === "customer" + }); - return; - } + return; } onData(null, { From 20adfa7279b80bfaf56df7abfe5e60868327397d Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:31:14 -0700 Subject: [PATCH 28/57] refactor: remove revision publication --- server/publications/collections/revisions.js | 42 -------------------- 1 file changed, 42 deletions(-) delete mode 100644 server/publications/collections/revisions.js diff --git a/server/publications/collections/revisions.js b/server/publications/collections/revisions.js deleted file mode 100644 index 011afb94943..00000000000 --- a/server/publications/collections/revisions.js +++ /dev/null @@ -1,42 +0,0 @@ -import { Meteor } from "meteor/meteor"; -import { check, Match } from "meteor/check"; -import { Roles } from "meteor/alanning:roles"; -import { Revisions } from "/lib/collections"; -import { Reaction } from "/server/api"; - -/** - * accounts - */ - -Meteor.publish("Revisions", function (documentIds) { - check(documentIds, Match.OneOf(String, Array)); - - // we could additionally make checks of useId defined, but this could lead to - // situation when user will may not have time to get an account - if (this.userId === null) { - return this.ready(); - } - const shopId = Reaction.getShopId(); - if (!shopId) { - return this.ready(); - } - - if (Roles.userIsInRole(this.userId, ["admin", "owner"])) { - if (Array.isArray(documentIds)) { - return Revisions.find({ - // shopId, - documentId: { - $in: documentIds - } - }); - } - - // global admin can get all accounts - return Revisions.find({ - // shopId, - documentId: documentIds - }); - } - // regular users should get just their account - return this.ready(); -}); From 7497ca1eeb922b1ed0b063d30168b9341958ce43 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:39:29 -0700 Subject: [PATCH 29/57] breaking: remove revision control package --- .../revisions/client/components/settings.js | 45 -- .../revisions/client/components/simpleDiff.js | 86 ---- .../client/containers/settingsContainer.js | 70 --- .../plugins/core/revisions/client/index.js | 2 - .../revisions/client/templates/settings.html | 5 - .../revisions/client/templates/settings.js | 10 - imports/plugins/core/revisions/index.js | 1 - .../plugins/core/revisions/lib/api/index.js | 1 - .../core/revisions/lib/api/revisions.js | 32 -- imports/plugins/core/revisions/register.js | 21 - .../core/revisions/server/functions.js | 468 ------------------ .../plugins/core/revisions/server/hooks.js | 253 ---------- .../core/revisions/server/i18n/ar.json | 22 - .../core/revisions/server/i18n/bg.json | 22 - .../core/revisions/server/i18n/cs.json | 22 - .../core/revisions/server/i18n/de.json | 22 - .../core/revisions/server/i18n/el.json | 22 - .../core/revisions/server/i18n/en.json | 22 - .../core/revisions/server/i18n/es.json | 22 - .../core/revisions/server/i18n/fr.json | 22 - .../core/revisions/server/i18n/he.json | 5 - .../core/revisions/server/i18n/hr.json | 22 - .../core/revisions/server/i18n/hu.json | 22 - .../core/revisions/server/i18n/index.js | 32 -- .../core/revisions/server/i18n/it.json | 22 - .../core/revisions/server/i18n/my.json | 22 - .../core/revisions/server/i18n/nb.json | 5 - .../core/revisions/server/i18n/nl.json | 22 - .../core/revisions/server/i18n/pl.json | 22 - .../core/revisions/server/i18n/pt.json | 22 - .../core/revisions/server/i18n/ro.json | 22 - .../core/revisions/server/i18n/ru.json | 22 - .../core/revisions/server/i18n/sl.json | 22 - .../core/revisions/server/i18n/sv.json | 22 - .../core/revisions/server/i18n/tr.json | 22 - .../core/revisions/server/i18n/vi.json | 22 - .../core/revisions/server/i18n/zh.json | 22 - .../plugins/core/revisions/server/index.js | 4 - .../plugins/core/revisions/server/methods.js | 216 -------- .../core/revisions/server/publications.js | 47 -- 40 files changed, 1787 deletions(-) delete mode 100644 imports/plugins/core/revisions/client/components/settings.js delete mode 100644 imports/plugins/core/revisions/client/components/simpleDiff.js delete mode 100644 imports/plugins/core/revisions/client/containers/settingsContainer.js delete mode 100644 imports/plugins/core/revisions/client/index.js delete mode 100644 imports/plugins/core/revisions/client/templates/settings.html delete mode 100644 imports/plugins/core/revisions/client/templates/settings.js delete mode 100644 imports/plugins/core/revisions/index.js delete mode 100644 imports/plugins/core/revisions/lib/api/index.js delete mode 100644 imports/plugins/core/revisions/lib/api/revisions.js delete mode 100644 imports/plugins/core/revisions/register.js delete mode 100644 imports/plugins/core/revisions/server/functions.js delete mode 100644 imports/plugins/core/revisions/server/hooks.js delete mode 100644 imports/plugins/core/revisions/server/i18n/ar.json delete mode 100644 imports/plugins/core/revisions/server/i18n/bg.json delete mode 100644 imports/plugins/core/revisions/server/i18n/cs.json delete mode 100644 imports/plugins/core/revisions/server/i18n/de.json delete mode 100644 imports/plugins/core/revisions/server/i18n/el.json delete mode 100644 imports/plugins/core/revisions/server/i18n/en.json delete mode 100644 imports/plugins/core/revisions/server/i18n/es.json delete mode 100644 imports/plugins/core/revisions/server/i18n/fr.json delete mode 100644 imports/plugins/core/revisions/server/i18n/he.json delete mode 100644 imports/plugins/core/revisions/server/i18n/hr.json delete mode 100644 imports/plugins/core/revisions/server/i18n/hu.json delete mode 100644 imports/plugins/core/revisions/server/i18n/index.js delete mode 100644 imports/plugins/core/revisions/server/i18n/it.json delete mode 100644 imports/plugins/core/revisions/server/i18n/my.json delete mode 100644 imports/plugins/core/revisions/server/i18n/nb.json delete mode 100644 imports/plugins/core/revisions/server/i18n/nl.json delete mode 100644 imports/plugins/core/revisions/server/i18n/pl.json delete mode 100644 imports/plugins/core/revisions/server/i18n/pt.json delete mode 100644 imports/plugins/core/revisions/server/i18n/ro.json delete mode 100644 imports/plugins/core/revisions/server/i18n/ru.json delete mode 100644 imports/plugins/core/revisions/server/i18n/sl.json delete mode 100644 imports/plugins/core/revisions/server/i18n/sv.json delete mode 100644 imports/plugins/core/revisions/server/i18n/tr.json delete mode 100644 imports/plugins/core/revisions/server/i18n/vi.json delete mode 100644 imports/plugins/core/revisions/server/i18n/zh.json delete mode 100644 imports/plugins/core/revisions/server/index.js delete mode 100644 imports/plugins/core/revisions/server/methods.js delete mode 100644 imports/plugins/core/revisions/server/publications.js diff --git a/imports/plugins/core/revisions/client/components/settings.js b/imports/plugins/core/revisions/client/components/settings.js deleted file mode 100644 index 9b6f7c4a11a..00000000000 --- a/imports/plugins/core/revisions/client/components/settings.js +++ /dev/null @@ -1,45 +0,0 @@ -import React, { Component } from "react"; -import PropTypes from "prop-types"; -import { Translation } from "/imports/plugins/core/ui/client/components"; - - -class RevisionControlSettings extends Component { - get settings() { - return this.props.settings; - } - - render() { - let message; - - if (this.settings.general.enabled) { - message = ( - - ); - } else { - message = ( - - ); - } - - return ( -
-

{message}

-
- ); - } -} - -RevisionControlSettings.propTypes = { - checked: PropTypes.bool, - label: PropTypes.string, - onUpdateSettings: PropTypes.func, - settings: PropTypes.object -}; - -export default RevisionControlSettings; diff --git a/imports/plugins/core/revisions/client/components/simpleDiff.js b/imports/plugins/core/revisions/client/components/simpleDiff.js deleted file mode 100644 index d4d2275a534..00000000000 --- a/imports/plugins/core/revisions/client/components/simpleDiff.js +++ /dev/null @@ -1,86 +0,0 @@ -import React, { Component } from "react"; -import PropTypes from "prop-types"; - -class SimpleDiff extends Component { - renderDiff() { - const { diff } = this.props; - - return diff.map((change, index) => { - const rightHandSide = change.rhs && change.rhs.toString(); - const leftHandSide = change.lhs && change.lhs.toString(); - - switch (change.kind) { - // Array change - case "A": - return ( - - - {leftHandSide} - {rightHandSide} - - ); - - // Added property / element - case "N": - return ( - - - {leftHandSide} - {rightHandSide} - - ); - - // Edited property or element - case "E": - return ( - - - {leftHandSide} - {rightHandSide} - - ); - - // Removed property / element - case "D": - return ( - - - {leftHandSide} - {rightHandSide} - - ); - default: - return null; - } - }); - } - - render() { - return ( -
- - - - - - - - - {this.renderDiff()} - -
- {"Current"}{"Change"}
-
- ); - } -} - -SimpleDiff.defaultProps = { - diff: [] -}; - -SimpleDiff.propTypes = { - diff: PropTypes.arrayOf(PropTypes.object) -}; - -export default SimpleDiff; diff --git a/imports/plugins/core/revisions/client/containers/settingsContainer.js b/imports/plugins/core/revisions/client/containers/settingsContainer.js deleted file mode 100644 index 01a39387281..00000000000 --- a/imports/plugins/core/revisions/client/containers/settingsContainer.js +++ /dev/null @@ -1,70 +0,0 @@ -import React, { Component } from "react"; -import PropTypes from "prop-types"; -import { composeWithTracker } from "@reactioncommerce/reaction-components"; -import { Meteor } from "meteor/meteor"; -import SettingsComponent from "../components/settings"; -import { Packages } from "/lib/collections"; - -class RevisionSettingsContainer extends Component { - constructor(props) { - super(props); - - this.state = { - settings: this.props.packageInfo.settings - }; - } - - componentWillReceiveProps(nextProps) { - this.setState({ - settings: nextProps.packageInfo.settings - }); - } - - get settings() { - return this.state.settings; - } - - handleUpdateSettings = (settings) => { - this.setState({ settings }, () => { - Meteor.call("revisions/settings/update", settings); - }); - } - - /** - * Publish container is a stateless container component connected to Meteor data source. - * @return {PropTypes.node} react node - */ - render() { - return ( -
- -
- ); - } -} - -RevisionSettingsContainer.propTypes = { - packageInfo: PropTypes.object -}; - -export function handlePublishClick(revisions) { - if (Array.isArray(revisions)) { - const documentIds = revisions.map((revision) => revision.documentId); - Meteor.call("revisions/publish", documentIds); - } -} - -function composer(props, onData) { - const packageInfo = Packages.findOne({ - name: "reaction-revisions" - }); - - onData(null, { - packageInfo - }); -} - -export default composeWithTracker(composer)(RevisionSettingsContainer); diff --git a/imports/plugins/core/revisions/client/index.js b/imports/plugins/core/revisions/client/index.js deleted file mode 100644 index de2ea13734f..00000000000 --- a/imports/plugins/core/revisions/client/index.js +++ /dev/null @@ -1,2 +0,0 @@ -import "./templates/settings.html"; -import "./templates/settings.js"; diff --git a/imports/plugins/core/revisions/client/templates/settings.html b/imports/plugins/core/revisions/client/templates/settings.html deleted file mode 100644 index 03253ad97cd..00000000000 --- a/imports/plugins/core/revisions/client/templates/settings.html +++ /dev/null @@ -1,5 +0,0 @@ - diff --git a/imports/plugins/core/revisions/client/templates/settings.js b/imports/plugins/core/revisions/client/templates/settings.js deleted file mode 100644 index b12d8df528c..00000000000 --- a/imports/plugins/core/revisions/client/templates/settings.js +++ /dev/null @@ -1,10 +0,0 @@ -import { Template } from "meteor/templating"; -import SearchContainer from "../containers/settingsContainer.js"; - -Template.revisionControlSettings.helpers({ - SearchContainerComponent() { - return { - component: SearchContainer - }; - } -}); diff --git a/imports/plugins/core/revisions/index.js b/imports/plugins/core/revisions/index.js deleted file mode 100644 index d0eb62211f5..00000000000 --- a/imports/plugins/core/revisions/index.js +++ /dev/null @@ -1 +0,0 @@ -export { default as PublishContainer } from "./client/containers/publishContainer"; diff --git a/imports/plugins/core/revisions/lib/api/index.js b/imports/plugins/core/revisions/lib/api/index.js deleted file mode 100644 index 4442f1f0bed..00000000000 --- a/imports/plugins/core/revisions/lib/api/index.js +++ /dev/null @@ -1 +0,0 @@ -export * from "./revisions"; diff --git a/imports/plugins/core/revisions/lib/api/revisions.js b/imports/plugins/core/revisions/lib/api/revisions.js deleted file mode 100644 index b72ddb46af1..00000000000 --- a/imports/plugins/core/revisions/lib/api/revisions.js +++ /dev/null @@ -1,32 +0,0 @@ -import { Packages } from "/lib/collections"; -import { Reaction } from "/lib/api"; - -export function getPackageSettings() { - const shopId = Reaction.getPrimaryShopId(); - - const packageInfo = Packages.findOne({ - name: "reaction-revisions", - shopId - }); - - if (packageInfo && packageInfo.enabled && packageInfo.settings) { - return packageInfo.settings; - } - - return null; -} - -export function isRevisionControlEnabled() { - const settings = getPackageSettings(); - - if (settings && settings.general && typeof settings.general.enabled === "boolean") { - return settings.general.enabled; - } - - return false; -} - -export const RevisionApi = { - isRevisionControlEnabled, - getPackageSettings -}; diff --git a/imports/plugins/core/revisions/register.js b/imports/plugins/core/revisions/register.js deleted file mode 100644 index fa545f380bd..00000000000 --- a/imports/plugins/core/revisions/register.js +++ /dev/null @@ -1,21 +0,0 @@ -import { Reaction } from "/server/api"; - -Reaction.registerPackage({ - label: "Revisions", - name: "reaction-revisions", - autoEnable: true, - settings: { - general: { - enabled: true - } - }, - registry: [ - // Settings Panel in Catalog - { - label: "Product Revisions", - name: "catalog/settings/revisions/general", - provides: ["catalogSettings"], - template: "revisionControlSettings" - } - ] -}); diff --git a/imports/plugins/core/revisions/server/functions.js b/imports/plugins/core/revisions/server/functions.js deleted file mode 100644 index d6376ba6b38..00000000000 --- a/imports/plugins/core/revisions/server/functions.js +++ /dev/null @@ -1,468 +0,0 @@ - -import _ from "lodash"; -import { Meteor } from "meteor/meteor"; -import { Products, Revisions, Tags } from "/lib/collections"; -import { Hooks, Logger } from "/server/api"; -import { RevisionApi } from "../lib/api"; -import { ProductRevision } from "./hooks"; -import { getSlug } from "/lib/api"; - - -/** - * @name insertRevision - * @method - * @summary Inserts a new revision for a given product - * @param {Object} product - * @returns {undefined} - * @private - */ -export function insertRevision(product) { - if (RevisionApi.isRevisionControlEnabled() === false) { - return true; - } - - if (product.workflow && Array.isArray(product.workflow.workflow) && product.workflow.workflow.indexOf("imported") !== -1) { - // Mark imported products as published by default. - return true; - } - - const productRevision = Revisions.findOne({ - "documentId": product._id, - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }); - - // Prevent this product from being created if a parent product / variant ancestor is deleted. - // - // This will prevent cases where a parent variant has been deleted and a user tries to create a - // child variant. You cannot create the child variant because the parent will no longer exist when - // changes have been published; resulting in a broken inheritance and UI - const productHasAncestors = Array.isArray(product.ancestors); - - if (productHasAncestors) { - // Verify there are no deleted ancestors, - // Variants cannot be restored if their parent product / variant is deleted - const archivedCount = Revisions.find({ - "documentId": { $in: product.ancestors }, - "documentData.isDeleted": true, - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }).count(); - - if (archivedCount > 0) { - Logger.debug(`Cannot create product ${product._id} as a product/variant higher in it's ancestors tree is marked as 'isDeleted'.`); - throw new Meteor.Error("unable-to-create-variant", "Unable to create product variant"); - } - } - - - if (!productRevision) { - Logger.debug(`No revision found for product ${product._id}. Creating new revision`); - - Revisions.insert({ - documentId: product._id, - documentData: product - }); - } -} - -/** - * @name updateRevision - * @method - * @summary Update a product's revision - * @param {String} userId - * @param {Object} product - Product to update - * @param {Object} options - Options include userId, modifier and validation properties - * @returns {Boolean} true if underlying product should be updated, otherwise false. - * @private - */ -export function updateRevision(product, options = {}) { - if (RevisionApi.isRevisionControlEnabled() === false) { - return true; - } - - const { userId, modifier } = options; - - let productRevision = Revisions.findOne({ - "documentId": product._id, - "workflow.status": { - $nin: ["revision/published"] - } - }); - - // Prevent this product revision from being restored from isDeleted state if a product / variant - // ancestor is also deleted. - // - // This will prevent cases where a parent variant has been deleted and a user tries to restore a - // child variant. You cannot restore the child variant, because the parent will no longer exist when - // changes have been published; resulting in a broken inheritance and UI - const revisionHasAncestors = - productRevision && productRevision.documentData && Array.isArray(productRevision.documentData.ancestors); - const modifierContainsIsDeleted = modifier.$set && modifier.$set.isDeleted === false; - - if (revisionHasAncestors && modifierContainsIsDeleted) { - // Verify there are no deleted ancestors, - // Variants cannot be restored if their parent product / variant is deleted - const archivedCount = Revisions.find({ - "documentId": { $in: productRevision.documentData.ancestors }, - "documentData.isDeleted": true, - "workflow.status": { - $nin: ["revision/published"] - } - }).count(); - - if (archivedCount > 0) { - Logger.debug(`Cannot restore product ${ - product._id - } as a product/variant higher in it's ancestors tree is marked as 'isDeleted'.`); - throw new Meteor.Error("unable-to-delete-variant", "Unable to delete product variant"); - } - } - - - if (!productRevision) { - Logger.debug(`No revision found for product ${product._id}. Creating new revision`); - - // Create a new revision - Revisions.insert({ - documentId: product._id, - documentData: product - }); - - // Fetch newly created revision - productRevision = Revisions.findOne({ - documentId: product._id - }); - } - - // Create a new selector for the revision - // - // This is especially important since we may need to update some fields - // like metadata, and the selector is very important to that. - const revisionSelector = { - "documentId": product._id, - "workflow.status": { - $nin: ["revision/published"] - } - }; - - // Create a new modifier for the revision - const revisionModifier = { - $set: { - "workflow.status": "revision/update" - } - }; - - let publish = false; - if (Object.prototype.hasOwnProperty.call(options, "publish")) { - ({ publish } = options); - } - - if (publish === true || (product.workflow && product.workflow.status === "product/publish")) { - // Maybe mark the revision as published - - Logger.debug(`Publishing revision for product ${product._id}.`); - Revisions.update(revisionSelector, { - $set: { - "workflow.status": "revision/published" - } - }); - Hooks.Events.run("afterRevisionsUpdate", userId, { - ...productRevision, - workflow: { ...productRevision.workflow, status: "revisions/published" } - }); - return true; - } - - const hasAncestors = Array.isArray(product.ancestors) && product.ancestors.length > 0; - - for (const operation in modifier) { - if (Object.hasOwnProperty.call(modifier, operation)) { - if (!revisionModifier[operation]) { - revisionModifier[operation] = {}; - } - - for (const property in modifier[operation]) { - if ({}.hasOwnProperty.call(modifier[operation], property)) { - if (operation === "$set" && property === "metafields.$") { - // Special handling for meta fields with $ operator - // We need to update the selector otherwise the operation would completely fail. - // - // This does NOT apply to metafield.0, metafield.1, metafield.n operations - // where 0, 1, n represent an array index. - - // const originalSelector = options.selector; - revisionSelector["documentData.metafields"] = options.metafields; - revisionModifier.$set[`documentData.${property}`] = modifier.$set[property]; - } else if (operation === "$push" && property === "hashtags") { - if (!revisionModifier.$addToSet) { - revisionModifier.$addToSet = {}; - } - revisionModifier.$addToSet[`documentData.${property}`] = modifier.$push[property]; - } else if (operation === "$set" && property === "price" && hasAncestors) { - Revisions.update(revisionSelector, { - $set: { - "documentData.price": modifier.$set.price - } - }); - Hooks.Events.run("afterRevisionsUpdate", userId, { - ...productRevision, - documentData: { ...productRevision.documentData, price: modifier.$set.price } - }); - - const updateId = product.ancestors[0] || product._id; - const priceRange = ProductRevision.getProductPriceRange(updateId); - - Meteor.call("products/updateProductField", updateId, "price", priceRange); - } else if (operation === "$set" && property === "isVisible" && hasAncestors) { - Revisions.update(revisionSelector, { - $set: { - "documentData.isVisible": modifier.$set.isVisible - } - }); - Hooks.Events.run("afterRevisionsUpdate", userId, { - ...productRevision, - documentData: { ...productRevision.documentData, isVisible: modifier.$set.isVisible } - }); - - const updateId = product.ancestors[0] || product._id; - const priceRange = ProductRevision.getProductPriceRange(updateId); - - Meteor.call("products/updateProductField", updateId, "price", priceRange); - } else if ( - operation === "$set" && - (property === "title" || property === "handle") && - hasAncestors === false - ) { - // Special handling for product title and handle - // - // Summary: - // When a user updates the product title, if the handle matches the product id, - // then update the handle to be a slugified version of the title - // - // This block ensures that the handle is either a custom slug, slug of the title, or - // the _id of the product, but is never blank - - // New data - const newValue = modifier.$set[property]; - const newTitle = modifier.$set.title; - const newHandle = modifier.$set.handle; - - // Current revision data - const { documentId } = productRevision; - const slugDocId = getSlug(documentId); - const revisionTitle = productRevision.documentData.title; - const revisionHandle = productRevision.documentData.handle; - - // Checks - const hasNewHandle = _.isEmpty(newHandle) === false; - const hasExistingTitle = _.isEmpty(revisionTitle) === false; - const hasNewTitle = _.isEmpty(newTitle) === false; - const hasHandle = _.isEmpty(revisionHandle) === false; - const handleMatchesId = - revisionHandle === documentId || - revisionHandle === slugDocId || - newValue === documentId || - newValue === slugDocId; - - // Continue to set the title / handle as originally requested - // Handle will get changed if conditions are met in the below if block - revisionModifier.$set[`documentData.${property}`] = newValue; - - if ( - (handleMatchesId || hasHandle === false) && - (hasExistingTitle || hasNewTitle) && - hasNewHandle === false - ) { - // Set the handle to be the slug of the product.title - // when documentId (product._id) matches the handle, then handle is empty, and a title exists - revisionModifier.$set["documentData.handle"] = getSlug(newTitle || revisionTitle); - } else if (hasHandle === false && hasExistingTitle === false && hasNewHandle === false) { - // If the handle & title is empty, the handle becomes the product id - revisionModifier.$set["documentData.handle"] = documentId; - } else if (hasNewHandle === false && property === "handle") { - // If the handle is empty, the handle becomes the slugified product title, or document id if title does not exist. - // const newTitle = modifier.$set["title"]; - revisionModifier.$set["documentData.handle"] = hasExistingTitle - ? getSlug(newTitle || revisionTitle) - : documentId; - } - } else if (operation === "$unset" && property === "handle" && hasAncestors === false) { - // Special handling for product handle when it is going to be unset - // - // Summary: - // When a user updates the handle to a black string e.g. deletes all text in field in UI and saves, - // the handle will be adjusted so it will not be blank - const newValue = modifier.$unset[property]; - const revisionTitle = productRevision.documentData.title; - const hasExistingTitle = _.isEmpty(revisionTitle) === false; - - // If the new handle is going to be empty, the handle becomes the slugified product title, or document id if title does not exist. - if (_.isEmpty(newValue)) { - revisionModifier.$set["documentData.handle"] = hasExistingTitle - ? getSlug(revisionTitle) - : productRevision.documentId; - } - } else { - // Let everything else through - revisionModifier[operation][`documentData.${property}`] = modifier[operation][property]; - } - } - } - } - } - - Revisions.update(revisionSelector, revisionModifier); - const updatedRevision = Revisions.findOne({ documentId: product._id }); - Hooks.Events.run("afterRevisionsUpdate", userId, updatedRevision); - - Logger.debug(`Revision updated for product ${product._id}.`); - - if (modifier.$pull && modifier.$pull.hashtags) { - const tagId = modifier.$pull.hashtags; - - const productCount = Products.find({ - hashtags: tagId - }).count(); - - const relatedTagsCount = Tags.find({ - relatedTagIds: tagId - }).count(); - - if (productCount === 0 && relatedTagsCount === 0) { - // Mark tag as deleted - Tags.update( - { - _id: tagId - }, - { - $set: { - isDeleted: true - } - } - ); - } else { - Tags.update( - { - _id: tagId - }, - { - $set: { - isDeleted: false - } - } - ); - } - } - - // If we are using $set or $inc, and the fields are one of the ignoredFields, - // allow product to be updated without going through revision control - if ((modifier.$set || modifier.$inc) && !modifier.$pull && !modifier.$push) { - const newSet = {}; - const newInc = {}; - let hasIgnoredFields = false; - const ignoredFields = ["isLowQuantity", "isSoldOut", "inventoryQuantity"]; - - for (const field of ignoredFields) { - if (modifier.$set && ( - typeof modifier.$set[field] === "number" || - typeof modifier.$set[field] === "boolean" || - typeof modifier.$set[field] === "string" - )) { - newSet[field] = modifier.$set[field]; - hasIgnoredFields = true; - } - - if (modifier.$inc && ( - typeof modifier.$inc[field] === "number" || - typeof modifier.$inc[field] === "boolean" || - typeof modifier.$set[field] === "string" - )) { - newInc[field] = modifier.$inc[field]; - hasIgnoredFields = true; - } - } - if (_.isEmpty(newSet) === false) { - modifier.$set = newSet; - } - - if (_.isEmpty(newInc) === false) { - modifier.$inc = newInc; - } - - return hasIgnoredFields === true; - } - - // prevent the underlying document from being modified as it is in draft mode - return false; -} -/** - * @name markRevisionAsDeleted - * @method - * @summary Flag a product's revision as deleted - * @param {Object} product - The product whose revision will be flagged as deleted. - * @param {Object} options - Contains userId - * @returns {undefined} - * @private - */ -export function markRevisionAsDeleted(product, options) { - if (RevisionApi.isRevisionControlEnabled() === false) { - return true; - } - - const { userId } = options; - - let productRevision = Revisions.findOne({ - documentId: product._id - }); - - if (!productRevision) { - Logger.debug(`No revision found for product ${product._id}. Creating new revision`); - - Revisions.insert({ - documentId: product._id, - documentData: product - }); - productRevision = Revisions.findOne({ - documentId: product._id - }); - } - - // Set the revision as deleted "isDeleted: true" - Revisions.update({ - documentId: product._id - }, { - $set: { - "documentData.isDeleted": true, - "workflow.status": "revision/remove" - } - }); - Hooks.Events.run("afterRevisionsUpdate", userId, { - ...productRevision, - documentData: { ...productRevision.documentData, isDeleted: true }, - workflow: { ...productRevision.workflow, workflow: "revision/remove" } - }); - - Logger.debug(`Revision updated for product ${product._id}.`); - Logger.debug(`Product ${product._id} is now marked as deleted.`); - - // If the original product is deleted, and the user is trying to delete it again, - // then actually remove it completely. - // - // This acts like a trash. Where the product is sent to trash before it can actually - // be deleted permanently. - if (product.isDeleted === true) { - Logger.debug(`Allowing write to product ${product._id} for Collection.remove().`); - - return true; - } - - Logger.debug(`Preventing write to product ${product._id} for Collection.remove().`); - return false; -} diff --git a/imports/plugins/core/revisions/server/hooks.js b/imports/plugins/core/revisions/server/hooks.js deleted file mode 100644 index 9f598e37250..00000000000 --- a/imports/plugins/core/revisions/server/hooks.js +++ /dev/null @@ -1,253 +0,0 @@ -import _ from "lodash"; -import { diff } from "deep-diff"; -import { RevisionApi } from "../lib/api"; -import { insertRevision, updateRevision, markRevisionAsDeleted } from "./functions"; -import { Products, Revisions } from "/lib/collections"; -import { Hooks } from "/server/api"; -import { Media } from "/imports/plugins/core/files/server"; - -export const ProductRevision = { - getProductPriceRange(productId) { - const product = Products.findOne(productId); - if (!product) { - return { - range: "0", - min: 0, - max: 0 - }; - } - - const variants = this.getTopVariants(product._id); - if (variants.length > 0) { - const variantPrices = []; - variants.forEach((variant) => { - if (variant.isVisible === true) { - const range = this.getVariantPriceRange(variant._id); - if (typeof range === "string") { - const firstPrice = parseFloat(range.substr(0, range.indexOf(" "))); - const lastPrice = parseFloat(range.substr(range.lastIndexOf(" ") + 1)); - variantPrices.push(firstPrice, lastPrice); - } else { - variantPrices.push(range); - } - } else { - variantPrices.push(0, 0); - } - }); - const priceMin = _.min(variantPrices); - const priceMax = _.max(variantPrices); - let priceRange = `${priceMin.toFixed(2)} - ${priceMax.toFixed(2)}`; - // if we don't have a range - if (priceMin === priceMax) { - priceRange = priceMin.toFixed(2); - } - const priceObject = { - range: priceRange, - min: priceMin, - max: priceMax - }; - return priceObject; - } - - if (!product.price) { - return { - range: "0", - min: 0, - max: 0 - }; - } - - // if we have no variants subscribed to (client) - // we'll get the price object previously from the product - return product.price; - }, - - getVariantPriceRange(variantId) { - const children = this.getVariants(variantId); - const visibleChildren = children.filter((child) => child.isVisible && !child.isDeleted); - - switch (visibleChildren.length) { - case 0: { - const topVariant = this.getProduct(variantId); - // topVariant could be undefined when we removing last top variant - return topVariant && topVariant.price; - } - case 1: { - return visibleChildren[0].price; - } - default: { - let priceMin = Number.POSITIVE_INFINITY; - let priceMax = Number.NEGATIVE_INFINITY; - - visibleChildren.forEach((child) => { - if (child.price < priceMin) { - priceMin = child.price; - } - if (child.price > priceMax) { - priceMax = child.price; - } - }); - - if (priceMin === priceMax) { - // TODO check impact on i18n/formatPrice from moving return to string - return priceMin.toString(); - } - return `${priceMin} - ${priceMax}`; - } - } - }, - - findRevision({ documentId }) { - return Revisions.findOne({ - documentId, - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }); - }, - - getProduct(variantId) { - const product = Products.findOne(variantId); - const revision = this.findRevision({ - documentId: variantId - }); - - return (revision && revision.documentData) || product; - }, - - getTopVariants(id) { - const variants = []; - - Products.find({ - ancestors: [id], - type: "variant", - isDeleted: false - }).forEach((product) => { - const revision = this.findRevision({ - documentId: product._id - }); - - if (revision && revision.documentData.isVisible) { - variants.push(revision.documentData); - } else if (!revision && product.isVisible) { - variants.push(product); - } - - return variants; - }); - - return variants; - }, - - getVariants(id, type) { - const variants = []; - - Products.find({ - ancestors: { $in: [id] }, - type: type || "variant", - isDeleted: false - }).forEach((product) => { - const revision = this.findRevision({ - documentId: product._id - }); - - if (revision && revision.documentData.isVisible) { - variants.push(revision.documentData); - } else if (!revision && product.isVisible) { - variants.push(product); - } - }); - - return variants; - }, - - getVariantQuantity(variant) { - const options = this.getVariants(variant._id); - if (options && options.length) { - return options.reduce((sum, option) => - sum + option.inventoryQuantity || 0, 0); - } - return variant.inventoryQuantity || 0; - } -}; - -/** - * @summary Executes the provided function when beforeInsertCatalogProductInsertRevision - * hook is ran. The hook is ran before a product is inserted, and it will insert a - * corresponding revision for the provided product. - * @param {Function} Callback to execute - * @return {Object} product - the product in which the callback was called on. - * @private - */ -Hooks.Events.add("beforeInsertCatalogProductInsertRevision", (product) => { - insertRevision(product); - - return product; -}); - -/** - * @summary Executes the provided function when beforeInsertCatalogProductInsertRevision - * hook is ran. The hook is ran after a product is inserted, and it will insert a - * corresponding revision for the provided product. - * @param {Function} Callback to execute - * @return {Object} product - the product in which the callback was called on. - * @private - */ -Hooks.Events.add("afterInsertCatalogProductInsertRevision", (product) => { - insertRevision(product); - - return product; -}); - -/** - * @summary Executes the provided function when beforeUpdateCatalogProduct - * hook is ran. The hook is ran before a product is updated, and it will updated the - * corresponding revisions for the provided product. - * @param {Function} Callback to execute - * @return {Boolean} true|false - Used to determine whether the underlying product should be updated. - * @private - */ -Hooks.Events.add("beforeUpdateCatalogProduct", (product, options) => updateRevision(product, options)); - -/** - * @summary Executes the provided function when beforeRemoveCatalogProduct - * hook is ran. The hook is ran before a product or variant is archived, and it will updated the - * corresponding revisions for the provided product or variant. - * @param {Function} Callback to execute - * @return {Boolean} true|false - Used to determine whether the underlying product should be updated. - * @private - */ -Hooks.Events.add("beforeRemoveCatalogProduct", (product, options) => markRevisionAsDeleted(product, options)); - -Hooks.Events.add("afterRevisionsUpdate", (userId, revision) => { - if (RevisionApi.isRevisionControlEnabled() === false) { - return true; - } - let differences; - - - if (!revision.documentType || revision.documentType === "product") { - // Make diff - const product = Products.findOne({ - _id: revision.documentId - }); - differences = diff(product, revision.documentData); - } - - if (revision.documentType && revision.documentType === "image") { - const image = Promise.await(Media.findOne(revision.documentId, { raw: true })); - differences = image && diff(image.metadata, revision.documentData); - } - - Revisions.update({ - _id: revision._id - }, { - $set: { - diff: differences && differences.map((d) => Object.assign({}, d)) - } - }); -}, { - fetchPrevious: false -}); diff --git a/imports/plugins/core/revisions/server/i18n/ar.json b/imports/plugins/core/revisions/server/i18n/ar.json deleted file mode 100644 index fa66d8c3a7a..00000000000 --- a/imports/plugins/core/revisions/server/i18n/ar.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "ar", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "معاينة", - "revisionsLabel": "التنقيحات", - "revisionsTitle": "التنقيحات", - "revisionsDescription": "مراجعة مراقبة" - }, - "catalogSettings": { - "productRevisionsLabel": "مراجعات المنتج" - }, - "toolbar": { - "publishAll": "نشر جميع" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/bg.json b/imports/plugins/core/revisions/server/i18n/bg.json deleted file mode 100644 index 9e0fbcf8cdc..00000000000 --- a/imports/plugins/core/revisions/server/i18n/bg.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "bg", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "предварителен преглед", - "revisionsLabel": "ревизии", - "revisionsTitle": "ревизии", - "revisionsDescription": "контрол на контрол" - }, - "catalogSettings": { - "productRevisionsLabel": "ревизии на продукта" - }, - "toolbar": { - "publishAll": "публикува всички" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/cs.json b/imports/plugins/core/revisions/server/i18n/cs.json deleted file mode 100644 index 72230d99c70..00000000000 --- a/imports/plugins/core/revisions/server/i18n/cs.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "cs", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Náhled", - "revisionsLabel": "revize", - "revisionsTitle": "revize", - "revisionsDescription": "ovládání revize" - }, - "catalogSettings": { - "productRevisionsLabel": "Revize produktu" - }, - "toolbar": { - "publishAll": "publikovat vše" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/de.json b/imports/plugins/core/revisions/server/i18n/de.json deleted file mode 100644 index 777ea5115e5..00000000000 --- a/imports/plugins/core/revisions/server/i18n/de.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "de", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Vorschau", - "revisionsLabel": "Revisionen", - "revisionsTitle": "Revisionen", - "revisionsDescription": "Revisionskontrolle" - }, - "catalogSettings": { - "productRevisionsLabel": "Produkt Revisions" - }, - "toolbar": { - "publishAll": "veröffentlichen Alle" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/el.json b/imports/plugins/core/revisions/server/i18n/el.json deleted file mode 100644 index 016cffe5f80..00000000000 --- a/imports/plugins/core/revisions/server/i18n/el.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "el", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Πρεμιέρα", - "revisionsLabel": "αναθεωρήσεις", - "revisionsTitle": "αναθεωρήσεις", - "revisionsDescription": "έλεγχο αναθεώρηση" - }, - "catalogSettings": { - "productRevisionsLabel": "αναθεωρήσεις του προϊόντος" - }, - "toolbar": { - "publishAll": "Δημοσιεύστε Όλα" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/en.json b/imports/plugins/core/revisions/server/i18n/en.json deleted file mode 100644 index 4d97abd4707..00000000000 --- a/imports/plugins/core/revisions/server/i18n/en.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "en", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Preview", - "revisionsLabel": "Revisions", - "revisionsTitle": "Revisions", - "revisionsDescription": "Revision control" - }, - "catalogSettings": { - "productRevisionsLabel": "Product Revisions" - }, - "toolbar": { - "publishAll": "Publish All" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/es.json b/imports/plugins/core/revisions/server/i18n/es.json deleted file mode 100644 index 87b73d9a09e..00000000000 --- a/imports/plugins/core/revisions/server/i18n/es.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "es", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Preestreno", - "revisionsLabel": "Las revisiones", - "revisionsTitle": "Las revisiones", - "revisionsDescription": "Control de revisión" - }, - "catalogSettings": { - "productRevisionsLabel": "Las revisiones del producto" - }, - "toolbar": { - "publishAll": "publicar todo" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/fr.json b/imports/plugins/core/revisions/server/i18n/fr.json deleted file mode 100644 index 61f4afef428..00000000000 --- a/imports/plugins/core/revisions/server/i18n/fr.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "fr", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Aperçu", - "revisionsLabel": "Versions", - "revisionsTitle": "Versions", - "revisionsDescription": "Gestion de versions" - }, - "catalogSettings": { - "productRevisionsLabel": "Gestion de versions des produits" - }, - "toolbar": { - "publishAll": "Tout publier" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/he.json b/imports/plugins/core/revisions/server/i18n/he.json deleted file mode 100644 index 7a2cc9d0e73..00000000000 --- a/imports/plugins/core/revisions/server/i18n/he.json +++ /dev/null @@ -1,5 +0,0 @@ -[{ - "i18n": "he", - "ns": "reaction-revisions", - "translation": { } -}] diff --git a/imports/plugins/core/revisions/server/i18n/hr.json b/imports/plugins/core/revisions/server/i18n/hr.json deleted file mode 100644 index ce55ba26011..00000000000 --- a/imports/plugins/core/revisions/server/i18n/hr.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "hr", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "pregled", - "revisionsLabel": "Izmjene", - "revisionsTitle": "Izmjene", - "revisionsDescription": "kontrola Revizija" - }, - "catalogSettings": { - "productRevisionsLabel": "Izmjene proizvoda" - }, - "toolbar": { - "publishAll": "objaviti sve" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/hu.json b/imports/plugins/core/revisions/server/i18n/hu.json deleted file mode 100644 index 1357f81f0e3..00000000000 --- a/imports/plugins/core/revisions/server/i18n/hu.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "hu", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Előnézet", - "revisionsLabel": "Változatok", - "revisionsTitle": "Változatok", - "revisionsDescription": "Revision szabályozás" - }, - "catalogSettings": { - "productRevisionsLabel": "termék Változatok" - }, - "toolbar": { - "publishAll": "közzétenni minden" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/index.js b/imports/plugins/core/revisions/server/i18n/index.js deleted file mode 100644 index 3f6a8d87fb9..00000000000 --- a/imports/plugins/core/revisions/server/i18n/index.js +++ /dev/null @@ -1,32 +0,0 @@ -import { loadTranslations } from "/server/startup/i18n"; - -// import ar from "./ar.json"; -// import bg from "./bg.json"; -// import de from "./de.json"; -// import el from "./el.json"; -import en from "./en.json"; -// import es from "./es.json"; -// import fr from "./fr.json"; -// import he from "./he.json"; -// import hr from "./hr.json"; -// import it from "./it.json"; -// import my from "./my.json"; -// import nb from "./nb.json"; -// import nl from "./nl.json"; -// import pl from "./pl.json"; -// import pt from "./pt.json"; -// import ro from "./ro.json"; -// import ru from "./ru.json"; -// import sl from "./sl.json"; -// import sv from "./sv.json"; -// import tr from "./tr.json"; -// import vi from "./vi.json"; -// import zh from "./zh.json"; - -// -// we want all the files in individual -// imports for easier handling by -// automated translation software -// -loadTranslations([en]); -// loadTranslations([ar, bg, de, el, en, es, fr, he, hr, it, my, nb, nl, pl, pt, ro, ru, sl, sv, tr, vi, zh]); diff --git a/imports/plugins/core/revisions/server/i18n/it.json b/imports/plugins/core/revisions/server/i18n/it.json deleted file mode 100644 index f3e540553ba..00000000000 --- a/imports/plugins/core/revisions/server/i18n/it.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "it", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Anteprima", - "revisionsLabel": "revisioni", - "revisionsTitle": "revisioni", - "revisionsDescription": "controllo di revisione" - }, - "catalogSettings": { - "productRevisionsLabel": "Le revisioni del prodotto" - }, - "toolbar": { - "publishAll": "pubblicare Tutto" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/my.json b/imports/plugins/core/revisions/server/i18n/my.json deleted file mode 100644 index b67ca31ef7c..00000000000 --- a/imports/plugins/core/revisions/server/i18n/my.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "my", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "ကို preview", - "revisionsLabel": "တည်းဖြတ်မူများကို", - "revisionsTitle": "တည်းဖြတ်မူများကို", - "revisionsDescription": "တည်းဖြတ်မူထိန်းချုပ်မှု" - }, - "catalogSettings": { - "productRevisionsLabel": "ကုန်ပစ္စည်းပြင်ဆင်ချက်များကို" - }, - "toolbar": { - "publishAll": "အားလုံး Publish" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/nb.json b/imports/plugins/core/revisions/server/i18n/nb.json deleted file mode 100644 index 80dd19ca6f7..00000000000 --- a/imports/plugins/core/revisions/server/i18n/nb.json +++ /dev/null @@ -1,5 +0,0 @@ -[{ - "i18n": "nb", - "ns": "reaction-revisions", - "translation": { } -}] diff --git a/imports/plugins/core/revisions/server/i18n/nl.json b/imports/plugins/core/revisions/server/i18n/nl.json deleted file mode 100644 index be3191b745f..00000000000 --- a/imports/plugins/core/revisions/server/i18n/nl.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "nl", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Voorbeeld", - "revisionsLabel": "herzieningen", - "revisionsTitle": "herzieningen", - "revisionsDescription": "controle Revision" - }, - "catalogSettings": { - "productRevisionsLabel": "product revisies" - }, - "toolbar": { - "publishAll": "Alle publiceren" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/pl.json b/imports/plugins/core/revisions/server/i18n/pl.json deleted file mode 100644 index b0fadff8835..00000000000 --- a/imports/plugins/core/revisions/server/i18n/pl.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "pl", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Zapowiedź", - "revisionsLabel": "rewizje", - "revisionsTitle": "rewizje", - "revisionsDescription": "kontroli wersji" - }, - "catalogSettings": { - "productRevisionsLabel": "Wersje produktu" - }, - "toolbar": { - "publishAll": "publikuje wszystkie" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/pt.json b/imports/plugins/core/revisions/server/i18n/pt.json deleted file mode 100644 index 50d7723561b..00000000000 --- a/imports/plugins/core/revisions/server/i18n/pt.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "pt", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "visualização", - "revisionsLabel": "revisões", - "revisionsTitle": "revisões", - "revisionsDescription": "controle de revisão" - }, - "catalogSettings": { - "productRevisionsLabel": "As revisões de produtos" - }, - "toolbar": { - "publishAll": "publicar todos" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/ro.json b/imports/plugins/core/revisions/server/i18n/ro.json deleted file mode 100644 index 3f3be9ba368..00000000000 --- a/imports/plugins/core/revisions/server/i18n/ro.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "ro", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "previzualizare", - "revisionsLabel": "reviziile", - "revisionsTitle": "reviziile", - "revisionsDescription": "controlul revizuirii" - }, - "catalogSettings": { - "productRevisionsLabel": "Revizuiri produsului" - }, - "toolbar": { - "publishAll": "publicaţi toate" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/ru.json b/imports/plugins/core/revisions/server/i18n/ru.json deleted file mode 100644 index 6242c1d6dd0..00000000000 --- a/imports/plugins/core/revisions/server/i18n/ru.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "ru", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Предварительный просмотр", - "revisionsLabel": "Ревизии", - "revisionsTitle": "Ревизии", - "revisionsDescription": "контроль версий" - }, - "catalogSettings": { - "productRevisionsLabel": "Ревизии продукта" - }, - "toolbar": { - "publishAll": "Опубликовать все" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/sl.json b/imports/plugins/core/revisions/server/i18n/sl.json deleted file mode 100644 index c2ec0e0e7f2..00000000000 --- a/imports/plugins/core/revisions/server/i18n/sl.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "sl", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "predogled", - "revisionsLabel": "Revizije", - "revisionsTitle": "Revizije", - "revisionsDescription": "nadzor revizija" - }, - "catalogSettings": { - "productRevisionsLabel": "Revizije izdelka" - }, - "toolbar": { - "publishAll": "objavi Vse" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/sv.json b/imports/plugins/core/revisions/server/i18n/sv.json deleted file mode 100644 index 7bb54c470c7..00000000000 --- a/imports/plugins/core/revisions/server/i18n/sv.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "sv", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Förhandsvisning", - "revisionsLabel": "revideringar", - "revisionsTitle": "revideringar", - "revisionsDescription": "revisionskontroll" - }, - "catalogSettings": { - "productRevisionsLabel": "produkt~~POS=TRUNC Revideringar" - }, - "toolbar": { - "publishAll": "publicera All" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/tr.json b/imports/plugins/core/revisions/server/i18n/tr.json deleted file mode 100644 index e08af4a707e..00000000000 --- a/imports/plugins/core/revisions/server/i18n/tr.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "tr", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Önizleme", - "revisionsLabel": "Düzeltmeler", - "revisionsTitle": "Düzeltmeler", - "revisionsDescription": "Revizyon kontrolü" - }, - "catalogSettings": { - "productRevisionsLabel": "Ürün Düzeltmeler" - }, - "toolbar": { - "publishAll": "Tümünü Yayınla" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/vi.json b/imports/plugins/core/revisions/server/i18n/vi.json deleted file mode 100644 index 62efd5cb679..00000000000 --- a/imports/plugins/core/revisions/server/i18n/vi.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "vi", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "Xem trước", - "revisionsLabel": "Revisions", - "revisionsTitle": "Revisions", - "revisionsDescription": "kiểm soát sửa đổi" - }, - "catalogSettings": { - "productRevisionsLabel": "Sửa đổi sản phẩm" - }, - "toolbar": { - "publishAll": "Xuất bản Tất cả" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/i18n/zh.json b/imports/plugins/core/revisions/server/i18n/zh.json deleted file mode 100644 index 9cc0052a7a6..00000000000 --- a/imports/plugins/core/revisions/server/i18n/zh.json +++ /dev/null @@ -1,22 +0,0 @@ -[{ - "i18n": "zh", - "ns": "reaction-revisions", - "translation": { - "reaction-revisions": { - "admin": { - "dashboard": { - "preview": "预习", - "revisionsLabel": "修订", - "revisionsTitle": "修订", - "revisionsDescription": "版本控制" - }, - "catalogSettings": { - "productRevisionsLabel": "产品修订" - }, - "toolbar": { - "publishAll": "所有发布" - } - } - } - } -}] diff --git a/imports/plugins/core/revisions/server/index.js b/imports/plugins/core/revisions/server/index.js deleted file mode 100644 index 62d4d463737..00000000000 --- a/imports/plugins/core/revisions/server/index.js +++ /dev/null @@ -1,4 +0,0 @@ -import "./hooks"; -import "./methods"; -import "./i18n"; -import "./publications"; diff --git a/imports/plugins/core/revisions/server/methods.js b/imports/plugins/core/revisions/server/methods.js deleted file mode 100644 index 10d3f53cac6..00000000000 --- a/imports/plugins/core/revisions/server/methods.js +++ /dev/null @@ -1,216 +0,0 @@ -import { Meteor } from "meteor/meteor"; -import { check, Match } from "meteor/check"; -import { Products, MediaRecords, Revisions, Packages } from "/lib/collections"; -import { Hooks, Logger } from "/server/api"; - -function handleImageRevision(revision) { - let result = 0; - if (revision.changeType === "insert") { - result = MediaRecords.update({ - _id: revision.documentId - }, { - $set: { - metadata: { ...revision.documentData, workflow: "published" } - } - }); - } else if (revision.changeType === "remove") { - result = MediaRecords.update({ - _id: revision.documentId - }, { - $set: { - "metadata.workflow": "archived" - } - }); - } else if (revision.changeType === "update") { - result = MediaRecords.update({ - _id: revision.documentId - }, { - $set: { - metadata: { ...revision.documentData, workflow: "published" } - } - }); - Logger.debug(`setting metadata for ${revision.documentId} to ${JSON.stringify(revision.documentData, null, 4)}`); - } - // mark revision published whether we are publishing the image or not - Revisions.update({ - _id: revision._id - }, { - $set: { - "workflow.status": "revision/published" - } - }); - - return result; -} - -export function updateSettings(settings) { - check(settings, Object); - - Packages.update({ - name: "reaction-revisions" - }, { - $set: { - settings - } - }); -} - -/** - * @name publishCatalogProduct - * @method - * @summary Updates revision and publishes a product. - * - * @param {String} userId - currently logged in user - * @param {Object} selector - selector for product to update - * @param {Object} modifier - Object describing what parts of the document to update. - * @param {Object} validation - simple schema validation - * @return {String} _id of updated document - * @private - */ -function publishCatalogProduct(userId, selector, modifier, validation) { - const product = Products.findOne(selector); - const options = { - userId, - modifier, - validation, - publish: true - }; - - Hooks.Events.run("beforeUpdateCatalogProduct", product, options); - - const result = Products.update(selector, modifier, validation); - - Hooks.Events.run("afterUpdateCatalogProduct", product, options); - - // Records are not remove from the Products collection, they are only flagged as deleted. - // Run Hook to remove search record, if a product is being published as deleted - // Which is the equivalent to removing a product. - if (modifier.$set.isDeleted === true) { - Hooks.Events.run("afterRemoveProduct", product); - } - - return result; -} - -export function discardDrafts(documentIds) { - check(documentIds, Match.OneOf(String, Array)); - - let documentIdArray; - - if (Array.isArray(documentIds)) { - documentIdArray = documentIds; - } else { - documentIdArray = [documentIds]; - } - - const selector = { - "workflow.status": { - $nin: [ - "revision/published" - ] - }, - "$or": [ - { - documentId: { - $in: documentIdArray - } - }, - { - "documentData.ancestors": { - $in: documentIdArray - } - }, - { - parentDocument: { - $in: documentIds - } - } - ] - }; - - const result = Revisions.remove(selector); - - return result > 0; -} - -Meteor.methods({ - "revisions/settings/update": updateSettings, - "revisions/discard": discardDrafts, - "revisions/publish"(documentIds) { - check(documentIds, Match.OneOf(String, Array)); - - // Also publish variants if they have a draft - let revisions; - - if (Array.isArray(documentIds)) { - revisions = Revisions.find({ - "workflow.status": { - $nin: [ - "revision/published" - ] - }, - "$or": [ - { - documentId: { - $in: documentIds - } - }, - { - "documentData.ancestors": { - $in: documentIds - } - }, - { - parentDocument: { - $in: documentIds - } - } - ] - }).fetch(); - } else { - revisions = Revisions.find({ - "workflow.status": { - $nin: [ - "revision/published" - ] - }, - "$or": [ - { documentId: documentIds }, - { - "documentData.ancestors": { - $in: [documentIds] - } - } - ] - }).fetch(); - } - - let updatedDocuments = 0; - if (revisions) { - for (const revision of revisions) { - if (!revision.documentType || revision.documentType === "product") { - const res = publishCatalogProduct( - this.userId, - { - _id: revision.documentId - }, - { - $set: revision.documentData - } - ); - updatedDocuments += res; - } else if (revision.documentType === "image") { - updatedDocuments += handleImageRevision(revision); - } - } - } - - if (updatedDocuments > 0) { - return { - status: "success" - }; - } - - return false; - } -}); diff --git a/imports/plugins/core/revisions/server/publications.js b/imports/plugins/core/revisions/server/publications.js deleted file mode 100644 index 920769bf5a3..00000000000 --- a/imports/plugins/core/revisions/server/publications.js +++ /dev/null @@ -1,47 +0,0 @@ -import { Meteor } from "meteor/meteor"; -import { check } from "meteor/check"; -import { Roles } from "meteor/alanning:roles"; -import { Revisions } from "/lib/collections"; -import { Reaction } from "/server/api"; - -/** - * products publication - * @param {Number} productScrollLimit - optional, defaults to 24 - * @param {Array} shops - array of shopId to retrieve product from. - * @return {Object} return product cursor - */ -Meteor.publish("ProductRevisions", function (productIds) { - check(productIds, Array); - - const shop = Reaction.getShopId(); - // Authorized content curators fo the shop get special publication of the product - // all all relevant revisions all is one package - if (Roles.userIsInRole(this.userId, ["owner", "admin", "createProduct"], shop._id)) { - return Revisions.find({ - "$or": [ - { - documentId: { - $in: productIds - } - }, - { - "documentData.ancestors": { - $in: productIds - } - }, - { - parentDocument: { - $in: productIds - } - } - ], - "workflow.status": { - $nin: [ - "revision/published" - ] - } - }); - } - - return this.ready(); -}); From 1e13685f79fa17a5e04a84aa48e9b8b2bf18f0af Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:40:06 -0700 Subject: [PATCH 30/57] chore: add migration to remove revision registry entry --- .../server/migrations/25_remove_revision_control.js | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 imports/plugins/core/versions/server/migrations/25_remove_revision_control.js diff --git a/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js b/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js new file mode 100644 index 00000000000..26a8fcc3fbc --- /dev/null +++ b/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js @@ -0,0 +1,12 @@ +import { Migrations } from "meteor/percolate:migrations"; +import { Packages } from "/lib/collections"; + +// Migration file created for removing revision control package registry entry from all shops +Migrations.add({ + version: 25, + up() { + Packages.remove({ + name: "reaction-revisions" + }); + } +}); From 39cfb5dfc876152d0fa78eda1bad80e0835b77ed Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Tue, 15 May 2018 15:43:19 -0700 Subject: [PATCH 31/57] breaking: remove Revisions schema and collection --- lib/collections/collections.js | 9 ---- lib/collections/schemas/index.js | 1 - lib/collections/schemas/revisions.js | 80 ---------------------------- 3 files changed, 90 deletions(-) delete mode 100644 lib/collections/schemas/revisions.js diff --git a/lib/collections/collections.js b/lib/collections/collections.js index 3a7f2ae83e7..af4c8a0debe 100644 --- a/lib/collections/collections.js +++ b/lib/collections/collections.js @@ -141,15 +141,6 @@ export const Products = new Mongo.Collection("Products"); Products.attachSchema(Schemas.Product, { selector: { type: "simple" } }); Products.attachSchema(Schemas.ProductVariant, { selector: { type: "variant" } }); -/** - * @name Revisions - * @memberof Collections - * @type {MongoCollection} - */ -export const Revisions = new Mongo.Collection("Revisions"); - -Revisions.attachSchema(Schemas.Revisions); - /** * @name Shipping * @memberof Collections diff --git a/lib/collections/schemas/index.js b/lib/collections/schemas/index.js index 160941ba546..3d7b2328294 100644 --- a/lib/collections/schemas/index.js +++ b/lib/collections/schemas/index.js @@ -27,7 +27,6 @@ export * from "./orders"; export * from "./payments"; export * from "./products"; export * from "./registry"; -export * from "./revisions"; export * from "./shipping"; export * from "./shops"; export * from "./groups"; diff --git a/lib/collections/schemas/revisions.js b/lib/collections/schemas/revisions.js deleted file mode 100644 index db2498564fa..00000000000 --- a/lib/collections/schemas/revisions.js +++ /dev/null @@ -1,80 +0,0 @@ -import SimpleSchema from "simpl-schema"; -import { check } from "meteor/check"; -import { Tracker } from "meteor/tracker"; -import { registerSchema } from "@reactioncommerce/schemas"; -import { createdAtAutoValue, updatedAtAutoValue } from "./helpers"; -import { Workflow } from "./workflow"; - -/** - * @name Revisions - * @memberof Schemas - * @type {SimpleSchema} - * @property {String} _id Revision Id - * @property {Workflow} workflow required - * @property {String} documentId Reference Document Id - * @property {String} documentType Document Type, default value: `product`, allowed values: `product`, `image`, `tag` - * @property {String} parentDocument optional - * @property {"object"} documentData blackbox object - * @property {String} changeType optional, allowed values: `insert`, `update`, `remove` - * @property {Object[]} diff optional, blackbox - * @property {Date} createdAt required - * @property {Date} updatedAt optional - * @property {Date} publishAt optional - */ -export const Revisions = new SimpleSchema({ - "_id": { - type: String, - label: "Revision Id" - }, - "workflow": { - type: Workflow, - optional: false, - defaultValue: {} - }, - "documentId": { - type: String, - label: "Reference Document Id" - }, - "documentType": { - type: String, - label: "Document Type", - defaultValue: "product", - allowedValues: ["product", "image", "tag"] - }, - "parentDocument": { - type: String, - optional: true - }, - "documentData": { - type: "object", - blackbox: true - }, - "changeType": { - type: String, - optional: true, - allowedValues: ["insert", "update", "remove"] - }, - "diff": { - type: Array, - optional: true - }, - "diff.$": { - type: Object, - blackbox: true - }, - "createdAt": { - type: Date, - autoValue: createdAtAutoValue - }, - "updatedAt": { - type: Date, - autoValue: updatedAtAutoValue, - optional: true - }, - "publishAt": { - type: Date, - optional: true - } -}, { check, tracker: Tracker }); - -registerSchema("Revisions", Revisions); From e95780c1b1ebca9eb8e72bba4abd702f38ac3d84 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 10:08:18 -0700 Subject: [PATCH 32/57] refactor: check Products collection for isDeleted ancestors --- lib/api/products.js | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/lib/api/products.js b/lib/api/products.js index c920398e958..4eafeef5ca8 100644 --- a/lib/api/products.js +++ b/lib/api/products.js @@ -6,7 +6,7 @@ import { ReactiveDict } from "meteor/reactive-dict"; import { ReactiveVar } from "meteor/reactive-var"; import { Router } from "/imports/plugins/core/router/lib"; import { getCurrentTag, getShopName } from "/lib/api"; -import { Products, Revisions } from "/lib/collections"; +import { Products } from "/lib/collections"; import Catalog from "./catalog"; import { MetaData } from "/lib/api/router/metadata"; @@ -605,14 +605,9 @@ ReactionProduct.isAncestorDeleted = function (product, includeSelf) { // Verify there are no deleted ancestors, // Variants cannot be restored if their parent product / variant is deleted - const archivedCount = Revisions.find({ - "documentId": { $in: productIds }, - "documentData.isDeleted": true, - "workflow.status": { - $nin: [ - "revision/published" - ] - } + const archivedCount = Products.find({ + _id: { $in: productIds }, + isDeleted: true }).count(); if (archivedCount > 0) { From 0b4114ac5b6ce4b82a876c7d40578d440ced2d59 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 10:08:40 -0700 Subject: [PATCH 33/57] fix: import catalog directly --- imports/plugins/core/catalog/server/methods/catalog.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 11d9687a8ce..ce768bb6cc0 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -3,7 +3,7 @@ import { check, Match } from "meteor/check"; import { Products, Catalog as CatalogCollection } from "/lib/collections"; import { Logger, Reaction } from "/server/api"; import { Media } from "/imports/plugins/core/files/server"; -import Catalog from "/lib/api"; +import Catalog from "/lib/api/catalog"; /** * @method isSoldOut From ac095980912bb0a144a11fa0b0ce678c189a0b99 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 12:25:34 -0700 Subject: [PATCH 34/57] fix: set inventoryPolicy in state Set `inventoryPolicy` in state to fix an issue where the `Backorder` switch,would not change state to reflect the change in policy when clicked. --- .../plugins/included/product-variant/components/variantForm.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/included/product-variant/components/variantForm.js b/imports/plugins/included/product-variant/components/variantForm.js index 4e46afa9eb1..b1f1bf92471 100644 --- a/imports/plugins/included/product-variant/components/variantForm.js +++ b/imports/plugins/included/product-variant/components/variantForm.js @@ -173,13 +173,13 @@ class VariantForm extends Component { const inverseValue = !value; this.setState(({ variant }) => ({ + inventoryPolicy: inverseValue, variant: { ...variant, [field]: inverseValue } })); - this.handleFieldBlur(event, inverseValue, field); } From 0f1c7e00e97bfee6d503437e47433aa0d3de7006 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 15:18:13 -0700 Subject: [PATCH 35/57] docs: update summaries --- imports/plugins/core/files/server/methods.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/imports/plugins/core/files/server/methods.js b/imports/plugins/core/files/server/methods.js index af58d436f65..0dbd6b62cb5 100644 --- a/imports/plugins/core/files/server/methods.js +++ b/imports/plugins/core/files/server/methods.js @@ -11,7 +11,7 @@ import { MediaRecords } from "/lib/collections"; /** * @method updateMediaMetadata * @memberof Media/Methods - * @summary updates media record control. + * @summary Updates a media record. * @param {String} fileRecordId - _id of updated file record. * @param {Object} metadata - metadata from updated media file. * @return {Boolean} @@ -36,7 +36,7 @@ async function updateMediaMetadata(fileRecordId, metadata) { * @name media/insert * @method * @memberof Media/Methods - * @summary insert a new media record. + * @summary Insert a new media record. * @param {Object} fileRecord - document from file collection upload. * @return {String} - _id of the new inserted media record. */ @@ -57,7 +57,7 @@ export async function insertMedia(fileRecord) { * @name media/remove * @method * @memberof Media/Methods - * @summary unpublished media file by updating it's workflow + * @summary Unpublish a media record by updating it's workflow * @param {String} fileRecordId - _id of file record to be deleted. * @return {Boolean} */ From c5dde219cfa96ca1f28352325a4973d73e664c04 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 15:19:09 -0700 Subject: [PATCH 36/57] docs: update comment --- .../versions/server/migrations/25_remove_revision_control.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js b/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js index 26a8fcc3fbc..6f606421d2d 100644 --- a/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js +++ b/imports/plugins/core/versions/server/migrations/25_remove_revision_control.js @@ -1,7 +1,7 @@ import { Migrations } from "meteor/percolate:migrations"; import { Packages } from "/lib/collections"; -// Migration file created for removing revision control package registry entry from all shops +// Migration file created for removing the revision control package registry entry from all shops Migrations.add({ version: 25, up() { From 0f5fc54dcb9967e1c68e3d80a5a9cd5f5fc085a7 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Wed, 16 May 2018 15:19:32 -0700 Subject: [PATCH 37/57] docs: remove comma --- lib/api/products.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/api/products.js b/lib/api/products.js index 4eafeef5ca8..c3e40192a21 100644 --- a/lib/api/products.js +++ b/lib/api/products.js @@ -603,7 +603,7 @@ ReactionProduct.isAncestorDeleted = function (product, includeSelf) { productIds.push(product._id); } - // Verify there are no deleted ancestors, + // Verify there are no deleted ancestors // Variants cannot be restored if their parent product / variant is deleted const archivedCount = Products.find({ _id: { $in: productIds }, From cbff4ee7b8c1b0f3b068fbd6a9991ac2a9a5fb46 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 11:19:46 -0700 Subject: [PATCH 38/57] fix: conflict --- lib/api/catalog.js | 23 ++++++----------------- 1 file changed, 6 insertions(+), 17 deletions(-) diff --git a/lib/api/catalog.js b/lib/api/catalog.js index 46e65f2becf..30e2d0b126c 100644 --- a/lib/api/catalog.js +++ b/lib/api/catalog.js @@ -161,26 +161,15 @@ export default { }, /** -<<<<<<< HEAD - * @method getProduct - * @method - * @memberof ReactionProduct - * @summary Get product object. Could be useful for products and for top level variants - * @param {String} [id] - product _id - * @return {Object} Product data + * @method getProduct + * @method + * @memberof ReactionProduct + * @summary Get product object. Could be useful for products and for top level variants + * @param {String} [id] - product _id + * @return {Object} Product data */ getProduct(id) { return Products.findOne(id); -======= - * @method getPublishedOrRevision - * @memberof Catalog - * @description return top product revision if available - * @param {Object} product product or variant document - * @return {Object} product document - */ - getPublishedOrRevision(product) { - return applyProductRevision(product); ->>>>>>> release-1.12.0 }, /** From e5a5c957e336cc0bc803b707870797f41bca83d7 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 13:23:43 -0700 Subject: [PATCH 39/57] refactor: import helpers from catalog package --- imports/plugins/included/inventory/server/methods/inventory.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/included/inventory/server/methods/inventory.js b/imports/plugins/included/inventory/server/methods/inventory.js index 8c41e7209b4..bc049e059ac 100644 --- a/imports/plugins/included/inventory/server/methods/inventory.js +++ b/imports/plugins/included/inventory/server/methods/inventory.js @@ -2,7 +2,7 @@ import { Meteor } from "meteor/meteor"; import { Inventory, Products } from "/lib/collections"; import { Logger, Reaction } from "/server/api"; import rawCollections from "/imports/collections/rawCollections"; -import getVariants from "/imports/plugins/core/revisions/server/no-meteor/utils/getVariants"; +import getVariants from "/imports/plugins/core/catalog/server/no-meteor/utils/getVariants"; /** * @namespace Inventory/Methods From 40d38ea6a979b44ae6d59b62014861b78aa80f3f Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 13:23:51 -0700 Subject: [PATCH 40/57] refactor: import helpers from catalog package --- imports/plugins/core/catalog/server/methods/catalog.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 75e9e9fe9dc..0ac8f7e233f 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -8,8 +8,8 @@ import { Hooks, Logger, Reaction } from "/server/api"; import { MediaRecords, Products, Revisions, Tags } from "/lib/collections"; import { Media } from "/imports/plugins/core/files/server"; import rawCollections from "/imports/collections/rawCollections"; -import getProductPriceRange from "/imports/plugins/core/revisions/server/no-meteor/utils/getProductPriceRange"; -import getVariants from "/imports/plugins/core/revisions/server/no-meteor/utils/getVariants"; +import getProductPriceRange from "../no-meteor/utils/getProductPriceRange"; +import getVariants from "../no-meteor/utils/getVariants"; import isSoldOut from "../no-meteor/utils/isSoldOut"; import isLowQuantity from "../no-meteor/utils/isLowQuantity"; import isBackorder from "../no-meteor/utils/isBackorder"; From 4e31b5875e8c8e52d9120a99f6b9bae4b42500d4 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:15:18 -0700 Subject: [PATCH 41/57] test: fix broken assertions --- .../plugins/core/catalog/server/methods/catalog.app-test.js | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.app-test.js b/imports/plugins/core/catalog/server/methods/catalog.app-test.js index 5d984aa8e53..aeac0f0057b 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.app-test.js +++ b/imports/plugins/core/catalog/server/methods/catalog.app-test.js @@ -592,9 +592,9 @@ describe("core product methods", function () { const modifiedVariant1 = Products.findOne(variant1._id); const modifiedVariant2 = Products.findOne(variant2._id); const modifiedVariant3 = Products.findOne(variant3._id); - expect(modifiedVariant1.index).to.be(2); - expect(modifiedVariant2.index).to.be(0); - expect(modifiedVariant3.index).to.be(1); + expect(modifiedVariant1.index).to.be.equal(2); + expect(modifiedVariant2.index).to.be.equal(0); + expect(modifiedVariant3.index).to.be.equal(1); }); }); From 869d19f5acd01b2e77281ef814faa702a7f09d17 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:21:54 -0700 Subject: [PATCH 42/57] refactor: remove revision control --- .../core/catalog/server/methods/catalog.js | 75 ++++++++----------- 1 file changed, 32 insertions(+), 43 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 0ac8f7e233f..7c1b9eebc03 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -5,7 +5,7 @@ import { EJSON } from "meteor/ejson"; import { Meteor } from "meteor/meteor"; import { ReactionProduct } from "/lib/api"; import { Hooks, Logger, Reaction } from "/server/api"; -import { MediaRecords, Products, Revisions, Tags } from "/lib/collections"; +import { MediaRecords, Products, Tags } from "/lib/collections"; import { Media } from "/imports/plugins/core/files/server"; import rawCollections from "/imports/collections/rawCollections"; import getProductPriceRange from "../no-meteor/utils/getProductPriceRange"; @@ -189,7 +189,7 @@ function copyMedia(newId, variantOldId, variantNewId) { }) .then((fileRecords) => { fileRecords.forEach((fileRecord) => { - // Copy File and insert directly, bypasing revision control + // Copy File and insert fileRecord .fullClone({ productId: newId, @@ -259,7 +259,6 @@ function denormalize(id, field) { } } - // TODO: Determine if product revision needs to be updated as well. Products.update( id, { @@ -338,9 +337,7 @@ function createProduct(props = null) { /** * @function * @name updateCatalogProduct - * @summary Updates a product's revision and conditionally updates - * the underlying product. - * + * @summary Updates a product document. * @param {String} userId - currently logged in user * @param {Object} selector - selector for product to update * @param {Object} modifier - Object describing what parts of the document to update. @@ -350,23 +347,17 @@ function createProduct(props = null) { function updateCatalogProduct(userId, selector, modifier, validation) { const product = Products.findOne(selector); - const shouldUpdateProduct = Hooks.Events.run("beforeUpdateCatalogProduct", product, { + Hooks.Events.run("beforeUpdateCatalogProduct", product, { userId, modifier, validation }); - if (shouldUpdateProduct) { - const result = Products.update(selector, modifier, validation); - - Hooks.Events.run("afterUpdateCatalogProduct", product, { modifier }); - - return result; - } + const result = Products.update(selector, modifier, validation); - Logger.debug(`beforeUpdateCatalogProduct hook returned falsy, not updating catalog product`); + Hooks.Events.run("afterUpdateCatalogProduct", product, { modifier }); - return false; + return result; } Meteor.methods({ @@ -396,8 +387,7 @@ Meteor.methods({ } // Verify that this variant and any ancestors are not deleted. - // Child variants cannot be added if a parent product or product revision - // is marked as `{ isDeleted: true }` + // Child variants cannot be added if a parent product is marked as `{ isDeleted: true }` if (ReactionProduct.isAncestorDeleted(variant, true)) { throw new Meteor.Error("server-error", "Unable to create product variant"); } @@ -472,7 +462,6 @@ Meteor.methods({ let newId; try { - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", clone); newId = Products.insert(clone, { validate: false }); const newProduct = Products.findOne(newId); Hooks.Events.run("afterInsertCatalogProduct", newProduct); @@ -515,8 +504,7 @@ Meteor.methods({ const { ancestors } = product; // Verify that the parent variant and any ancestors are not deleted. - // Child variants cannot be added if a parent product or product revision - // is marked as `{ isDeleted: true }` + // Child variants cannot be added if a parent product is marked as `{ isDeleted: true }` if (ReactionProduct.isAncestorDeleted(product, true)) { throw new Meteor.Error("server-error", "Unable to create product variant"); } @@ -543,11 +531,9 @@ Meteor.methods({ } Hooks.Events.run("beforeInsertCatalogProduct", assembledVariant); - const _id = Products.insert(assembledVariant); + Products.insert(assembledVariant); Hooks.Events.run("afterInsertCatalogProduct", assembledVariant); - Hooks.Events.run("afterInsertCatalogProductInsertRevision", Products.findOne({ _id })); - Logger.debug(`products/createVariant: created variant: ${newVariantId} for ${parentId}`); return newVariantId; @@ -649,9 +635,16 @@ Meteor.methods({ // out if nothing to delete if (!Array.isArray(toDelete) || toDelete.length === 0) return false; - // Flag the variant and all its children as deleted in Revisions collection. + // Flag the variant and all its children as deleted. toDelete.forEach((product) => { Hooks.Events.run("beforeRemoveCatalogProduct", product, { userId: this.userId }); + Products.update({ + _id: product._id + }, { + $set: { + isDeleted: true + } + }); Hooks.Events.run("afterRemoveCatalogProduct", this.userId, product); }); @@ -760,7 +753,6 @@ Meteor.methods({ newProduct.title = createTitle(newProduct.title, newProduct._id); newProduct.handle = createHandle(Reaction.getSlug(newProduct.title), newProduct._id); } - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", newProduct); result = Products.insert(newProduct, { validate: false }); Hooks.Events.run("afterInsertCatalogProduct", newProduct); results.push(result); @@ -789,7 +781,6 @@ Meteor.methods({ delete newVariant.createdAt; delete newVariant.publishedAt; // TODO can variant have this param? - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", newVariant); result = Products.insert(newVariant, { validate: false }); Hooks.Events.run("afterInsertCatalogProduct", newVariant); copyMedia(productNewId, variant._id, variantNewId); @@ -822,27 +813,20 @@ Meteor.methods({ throw new Meteor.Error("invalid-parameter", "Product should have a valid shopId"); } - // Create product revision - Hooks.Events.run("beforeInsertCatalogProductInsertRevision", product); - return Products.insert(product); } + // Create a product const newSimpleProduct = createProduct(); - // Create simple product revision - Hooks.Events.run("afterInsertCatalogProductInsertRevision", newSimpleProduct); - - const newVariant = createProduct({ + // Create a product variant + createProduct({ ancestors: [newSimpleProduct._id], price: 0.0, title: "", type: "variant" // needed for multi-schema }); - // Create variant revision - Hooks.Events.run("afterInsertCatalogProductInsertRevision", newVariant); - return newSimpleProduct._id; }, @@ -902,18 +886,24 @@ Meteor.methods({ return ids; }); - // Flag the product and all its variants as deleted in the Revisions collection. + // Flag the product and all of it's variants as deleted. productsWithVariants.forEach((toArchiveProduct) => { Hooks.Events.run("beforeRemoveCatalogProduct", toArchiveProduct, { userId: this.userId }); - + Products.update({ + _id: toArchiveProduct._id + }, { + $set: { + isDeleted: true + } + }).count(); Hooks.Events.run("afterRemoveCatalogProduct", this.userId, toArchiveProduct); }); - const numFlaggedAsDeleted = Revisions.find({ - "documentId": { + const numFlaggedAsDeleted = Products.find({ + _id: { $in: ids }, - "documentData.isDeleted": true + isDeleted: true }).count(); if (numFlaggedAsDeleted > 0) { @@ -1017,7 +1007,6 @@ Meteor.methods({ } // If we get a result from the product update, - // meaning the update went past revision control, // denormalize and attach results to top-level product if (result === 1) { if (type === "variant" && toDenormalize.indexOf(field) >= 0) { From 07a7ca5d09ba7be4c95a76d0e46228212e289258 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:27:55 -0700 Subject: [PATCH 43/57] test: update test assertion result --- imports/plugins/core/catalog/server/methods/catalog.app-test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.app-test.js b/imports/plugins/core/catalog/server/methods/catalog.app-test.js index aeac0f0057b..9783739c076 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.app-test.js +++ b/imports/plugins/core/catalog/server/methods/catalog.app-test.js @@ -498,7 +498,7 @@ describe("core product methods", function () { Meteor.call("products/updateProductField", product._id, "title", "new product name"); Meteor.call("products/setHandle", product._id); product = Products.findOne(product._id); - expect(product.handle).to.equal(product._id); + expect(product.handle).to.equal("new product name"); }); }); From 4b01aa7e38e67df625990895c64b3ee7ac6577d1 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:36:05 -0700 Subject: [PATCH 44/57] fix: add type option to product update --- imports/plugins/core/catalog/server/methods/catalog.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 7c1b9eebc03..76064c16c90 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -644,6 +644,8 @@ Meteor.methods({ $set: { isDeleted: true } + }, { + type: product.type }); Hooks.Events.run("afterRemoveCatalogProduct", this.userId, product); }); From 36b714eb6762a2b0892bd9b18773ce8c6cf3204b Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:37:55 -0700 Subject: [PATCH 45/57] test: fix test that relied on revision control indirectly --- .../plugins/core/catalog/server/methods/catalog.app-test.js | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.app-test.js b/imports/plugins/core/catalog/server/methods/catalog.app-test.js index 9783739c076..69230dd2062 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.app-test.js +++ b/imports/plugins/core/catalog/server/methods/catalog.app-test.js @@ -472,12 +472,10 @@ describe("core product methods", function () { expect(product.hashtags).to.contain(tag._id); expect(Tags.find().count()).to.equal(1); - // Remove the tag from the published product and ensure it didn't succeed. - // Revision control should stop the published product from being changed. + // Remove the tag from the published product and ensure it succeed. Meteor.call("products/removeProductTag", product._id, tag._id); product = Products.findOne(product._id); expect(product.hashtags).to.not.contain(tag._id); - expect(Tags.find().count()).to.equal(0); }); }); From 4266a130b60137e3d0e3d11730dfe0e009a6dbef Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:39:17 -0700 Subject: [PATCH 46/57] test: fix assertion for product handle --- imports/plugins/core/catalog/server/methods/catalog.app-test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.app-test.js b/imports/plugins/core/catalog/server/methods/catalog.app-test.js index 69230dd2062..1e975f99cfc 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.app-test.js +++ b/imports/plugins/core/catalog/server/methods/catalog.app-test.js @@ -496,7 +496,7 @@ describe("core product methods", function () { Meteor.call("products/updateProductField", product._id, "title", "new product name"); Meteor.call("products/setHandle", product._id); product = Products.findOne(product._id); - expect(product.handle).to.equal("new product name"); + expect(product.handle).to.equal("new-product-name"); }); }); From 8997444b9a459ae0845c5a160c78a1f0899ce796 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:46:27 -0700 Subject: [PATCH 47/57] refactor: add revision control package removal migration --- imports/plugins/core/versions/server/migrations/index.js | 1 + 1 file changed, 1 insertion(+) diff --git a/imports/plugins/core/versions/server/migrations/index.js b/imports/plugins/core/versions/server/migrations/index.js index 26658655eb5..4ba42c448a0 100644 --- a/imports/plugins/core/versions/server/migrations/index.js +++ b/imports/plugins/core/versions/server/migrations/index.js @@ -22,3 +22,4 @@ import "./21_clean_cart_shipment_method"; import "./22_register_verify_account"; import "./23_drop_tempstore_collections"; import "./24_publish_all_existing_visible_products"; +import "./25_remove_revision_control"; From 7e0271c3a8d3de0ef33756258e3f88e809967571 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 14:47:15 -0700 Subject: [PATCH 48/57] fix: use toArchiveProduct as the string product id --- imports/plugins/core/catalog/server/methods/catalog.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 76064c16c90..1784849067b 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -892,7 +892,7 @@ Meteor.methods({ productsWithVariants.forEach((toArchiveProduct) => { Hooks.Events.run("beforeRemoveCatalogProduct", toArchiveProduct, { userId: this.userId }); Products.update({ - _id: toArchiveProduct._id + _id: toArchiveProduct }, { $set: { isDeleted: true From 82a02bac8e7d01188d76e38be306da911163cda1 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 15:04:40 -0700 Subject: [PATCH 49/57] test: add type to product update statements to fix broken tests --- imports/plugins/core/catalog/server/methods/catalog.js | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/imports/plugins/core/catalog/server/methods/catalog.js b/imports/plugins/core/catalog/server/methods/catalog.js index 1784849067b..e33d33da7db 100644 --- a/imports/plugins/core/catalog/server/methods/catalog.js +++ b/imports/plugins/core/catalog/server/methods/catalog.js @@ -639,13 +639,12 @@ Meteor.methods({ toDelete.forEach((product) => { Hooks.Events.run("beforeRemoveCatalogProduct", product, { userId: this.userId }); Products.update({ - _id: product._id + _id: product._id, + type: product.type }, { $set: { isDeleted: true } - }, { - type: product.type }); Hooks.Events.run("afterRemoveCatalogProduct", this.userId, product); }); @@ -892,12 +891,13 @@ Meteor.methods({ productsWithVariants.forEach((toArchiveProduct) => { Hooks.Events.run("beforeRemoveCatalogProduct", toArchiveProduct, { userId: this.userId }); Products.update({ - _id: toArchiveProduct + _id: toArchiveProduct._id, + type: toArchiveProduct.type }, { $set: { isDeleted: true } - }).count(); + }); Hooks.Events.run("afterRemoveCatalogProduct", this.userId, toArchiveProduct); }); From d49b6f04216b873208402ef0c91e9dc20fd8c1c5 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Fri, 18 May 2018 15:31:35 -0700 Subject: [PATCH 50/57] chore: update package lock file --- package-lock.json | 17 ++--------------- 1 file changed, 2 insertions(+), 15 deletions(-) diff --git a/package-lock.json b/package-lock.json index ac0cfe85b9d..f69a91f86a5 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8883,9 +8883,9 @@ "requires": { "inherits": "2.0.3", "isarray": "1.0.0", - "process-nextick-args": "2.0.0", + "process-nextick-args": "1.0.7", "safe-buffer": "5.1.1", - "string_decoder": "1.1.1", + "string_decoder": "1.0.3", "util-deprecate": "1.0.2" }, "dependencies": { @@ -8893,19 +8893,6 @@ "version": "2.0.3", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "process-nextick-args": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-2.0.0.tgz", - "integrity": "sha512-MtEC1TqN0EU5nephaJ4rAtThHtC86dNN9qCuEhtshvpVBkAW5ZO7BASN9REnF9eoXGcRub+pFuKEpOHE+HbEMw==" - }, - "string_decoder": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.1.1.tgz", - "integrity": "sha512-n/ShnvDi6FHbbVfviro+WojiFzv+s8MPMHBczVePfUpDJLwoLT0ht1l4YwBCbi8pJAveEEdnkHyPyTP/mzRfwg==", - "requires": { - "safe-buffer": "5.1.1" - } } } }, From 4dd5fea28351eca9cb2e10dd977a39ca94387725 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:01:52 -0700 Subject: [PATCH 51/57] refactor: remove revisions definition --- imports/collections/defineCollections.js | 1 - 1 file changed, 1 deletion(-) diff --git a/imports/collections/defineCollections.js b/imports/collections/defineCollections.js index 30f0436b920..0ac3982a0cb 100644 --- a/imports/collections/defineCollections.js +++ b/imports/collections/defineCollections.js @@ -22,7 +22,6 @@ export default function defineCollections(db, collections) { Orders: db.collection("Orders"), Packages: db.collection("Packages"), Products: db.collection("Products"), - Revisions: db.collection("Revisions"), roles: db.collection("roles"), SellerShops: db.collection("SellerShops"), Shipping: db.collection("Shipping"), From e3b27e7fcbcf614a6c78d0724ff4941390e81042 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:02:02 -0700 Subject: [PATCH 52/57] refactor: remove unused render function --- .../catalog/client/components/publishControls.js | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/imports/plugins/core/catalog/client/components/publishControls.js b/imports/plugins/core/catalog/client/components/publishControls.js index 39322a5cef3..19bd56c36b3 100644 --- a/imports/plugins/core/catalog/client/components/publishControls.js +++ b/imports/plugins/core/catalog/client/components/publishControls.js @@ -290,19 +290,6 @@ class PublishControls extends Component { return null; } - renderUndoButton() { - return ( - - ); - } - renderArchiveButton() { return ( Date: Mon, 21 May 2018 15:03:45 -0700 Subject: [PATCH 53/57] refactor: remove "discard" logic --- .../client/containers/publishContainer.js | 28 ++----------------- 1 file changed, 3 insertions(+), 25 deletions(-) diff --git a/imports/plugins/core/catalog/client/containers/publishContainer.js b/imports/plugins/core/catalog/client/containers/publishContainer.js index 4a61099579c..61fe55639fa 100644 --- a/imports/plugins/core/catalog/client/containers/publishContainer.js +++ b/imports/plugins/core/catalog/client/containers/publishContainer.js @@ -28,31 +28,9 @@ class PublishContainer extends Component { this.publishToCatalog("products", productIds); } - handlePublishActions = (event, action, documentIds) => { - switch (action) { - case "archive": - if (this.props.onAction) { - this.props.onAction(event, action, this.props.documentIds); - } - break; - case "discard": - Meteor.call("revisions/discard", documentIds, (error, result) => { - if (result === true) { - const message = i18next.t("revisions.changesDiscarded", { - defaultValue: "Changes discarded successfully" - }); - - Alerts.toast(message, "success"); - } else { - const message = i18next.t("revisions.noChangesDiscarded", { - defaultValue: "There are no changes to discard" - }); - - Alerts.toast(message, "warning"); - } - }); - break; - default: + handlePublishActions = (event, action) => { + if (action === "archive" && this.props.onAction) { + this.props.onAction(event, action, this.props.documentIds); } } From d5f96c311172b09d8366810e3ff9ac7966520d56 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:04:06 -0700 Subject: [PATCH 54/57] refactor: remove revisions prop --- .../core/catalog/client/containers/publishContainer.js | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/imports/plugins/core/catalog/client/containers/publishContainer.js b/imports/plugins/core/catalog/client/containers/publishContainer.js index 61fe55639fa..c9c1d21efc2 100644 --- a/imports/plugins/core/catalog/client/containers/publishContainer.js +++ b/imports/plugins/core/catalog/client/containers/publishContainer.js @@ -44,7 +44,6 @@ class PublishContainer extends Component { onPublishClick={this.handlePublishClick} onAction={this.handlePublishActions} onVisibilityChange={this.props.onVisibilityChange} - revisions={this.props.revisions} isPreview={this.props.isPreview} /> @@ -60,8 +59,7 @@ PublishContainer.propTypes = { onAction: PropTypes.func, onPublishSuccess: PropTypes.func, onVisibilityChange: PropTypes.func, - product: PropTypes.object, - revisions: PropTypes.arrayOf(PropTypes.object) + product: PropTypes.object }; function composer(props, onData) { From 7f35a3402d225cb6d4d49a0818799373244cfff1 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:07:04 -0700 Subject: [PATCH 55/57] refactor: remove unused render func --- .../client/components/publishControls.js | 47 ------------------- 1 file changed, 47 deletions(-) diff --git a/imports/plugins/core/catalog/client/components/publishControls.js b/imports/plugins/core/catalog/client/components/publishControls.js index 19bd56c36b3..0e977b59eae 100644 --- a/imports/plugins/core/catalog/client/components/publishControls.js +++ b/imports/plugins/core/catalog/client/components/publishControls.js @@ -4,10 +4,6 @@ import { Components } from "@reactioncommerce/reaction-components"; import { Button, FlatButton, - IconButton, - Divider, - DropDownMenu, - MenuItem, Switch, Icon } from "/imports/plugins/core/ui/client/components"; @@ -218,48 +214,6 @@ class PublishControls extends Component { ); } - renderMoreOptionsButton() { - return ( - } - handleMenuItemChange={this.handleAction} - > - - - - - - - - - - - ); - } - renderViewControls() { if (this.props.showViewAsControls) { let tooltip = "Private"; @@ -357,7 +311,6 @@ class PublishControls extends Component { {this.renderArchiveButton()} {this.renderViewControls()} {this.renderPublishButton()} - {/* this.renderMoreOptionsButton() */} ); } From 746ec219903758e71b04151e2bc4da32e18744c4 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:17:03 -0700 Subject: [PATCH 56/57] refactor: remove revision logic for the edit button --- .../plugins/core/ui/client/containers/edit.js | 41 +------------------ 1 file changed, 1 insertion(+), 40 deletions(-) diff --git a/imports/plugins/core/ui/client/containers/edit.js b/imports/plugins/core/ui/client/containers/edit.js index 547b8294813..0d2357806c8 100644 --- a/imports/plugins/core/ui/client/containers/edit.js +++ b/imports/plugins/core/ui/client/containers/edit.js @@ -65,47 +65,8 @@ class EditContainer extends Component { renderEditButton() { let status; let tooltip; - let hasChange = false; - - if (this.props.data.__draft && this.props.field) { - const draft = this.props.data.__draft; - - if (Array.isArray(draft.diff)) { - for (const diff of draft.diff) { - let hasChangedField = false; - - if (Array.isArray(this.props.field)) { - if (this.props.field.indexOf(diff.path[0]) >= 0) { - hasChangedField = true; - } - } else if (typeof this.props.field === "string" && this.props.field === diff.path[0]) { - hasChangedField = true; - } - - if (hasChangedField) { - status = "warning"; - - tooltip = ( - - - - ); - - hasChange = true; - } - } - } - } else if (this.props.data.__draft) { - status = "warning"; - - tooltip = ( - - - - ); - } - if (this.props.autoHideEditButton && hasChange === false) { + if (this.props.autoHideEditButton) { return null; } From 0e1421e6758feebc7366ca7a0034c74de9b4f909 Mon Sep 17 00:00:00 2001 From: Mike Murray Date: Mon, 21 May 2018 15:21:36 -0700 Subject: [PATCH 57/57] refactor: remove revision translations --- private/data/i18n/ar.json | 14 -------------- private/data/i18n/bg.json | 14 -------------- private/data/i18n/cs.json | 14 -------------- private/data/i18n/de.json | 14 -------------- private/data/i18n/el.json | 14 -------------- private/data/i18n/en.json | 14 -------------- private/data/i18n/es.json | 14 -------------- private/data/i18n/fr.json | 14 -------------- private/data/i18n/he.json | 14 -------------- private/data/i18n/hr.json | 14 -------------- private/data/i18n/hu.json | 14 -------------- private/data/i18n/it.json | 14 -------------- private/data/i18n/my.json | 14 -------------- private/data/i18n/nl.json | 14 -------------- private/data/i18n/pl.json | 14 -------------- private/data/i18n/pt.json | 14 -------------- private/data/i18n/ro.json | 14 -------------- private/data/i18n/ru.json | 14 -------------- private/data/i18n/sl.json | 14 -------------- private/data/i18n/sv.json | 14 -------------- private/data/i18n/tr.json | 14 -------------- private/data/i18n/vi.json | 14 -------------- private/data/i18n/zh.json | 14 -------------- 23 files changed, 322 deletions(-) diff --git a/private/data/i18n/ar.json b/private/data/i18n/ar.json index b5997c3ef92..5720bf9a9e7 100644 --- a/private/data/i18n/ar.json +++ b/private/data/i18n/ar.json @@ -513,20 +513,6 @@ "isCommercial": "هذه عناوين تجارية" } }, - "revisions": { - "isDisabled": ".مراجعة المراقبة غير مفعل .أي تغيير سوف يتم نشره فوراً", - "isEnabled": "يتم تمكين مراجعة مراقبة للمنتجات. سوف يحتاج أي تغييرات على أن تنشر قبل أن يكون مرئيا للعملاء.", - "unpublishedChanges": "تغييرات غير منشورة", - "publishChanges": "تغييرات النشر", - "showChanges": "إظهار التغييرات", - "hideChanges": "إخفاء التغييرات", - "discardChanges": "التراجع عن التغييرات ", - "changedPublished": "تم نشر التغييرات بنجاح", - "changesDiscarded": "تم التراجع عن التغييرات بنجاح ", - "noChanges": "لا يوجد تغييرات", - "noChangesPublished": ".لا يوجد تغييرات لنشرها", - "noChangesDiscarded": "لايوجد تغييرات للتراجع عنها " - }, "address": { "country": "البلد", "fullName": "الأسم كامل", diff --git a/private/data/i18n/bg.json b/private/data/i18n/bg.json index e326d60c6ce..ac4566b42f8 100644 --- a/private/data/i18n/bg.json +++ b/private/data/i18n/bg.json @@ -513,20 +513,6 @@ "isCommercial": "Това е търговски адрес." } }, - "revisions": { - "isDisabled": "контрол на контрол е забранено. Всички промени ще бъдат публикувани веднага.", - "isEnabled": "контрол на контрол е активиран за продукти. ще се нуждае от никакви промени, за да бъдат публикувани преди да бъдат видими за клиентите.", - "unpublishedChanges": "Непубликувани промени", - "publishChanges": "Публикуване на промените", - "showChanges": "Показване на промените", - "hideChanges": "Скриване на промените", - "discardChanges": "Отхвърлите промените", - "changedPublished": "Промени публикувани успешно", - "changesDiscarded": "Промени изхвърли успешно", - "noChanges": "Няма промени", - "noChangesPublished": "Няма промени за публикуване", - "noChangesDiscarded": "Няма промени, за да изхвърли" - }, "address": { "country": "Държава", "fullName": "Пълно име", diff --git a/private/data/i18n/cs.json b/private/data/i18n/cs.json index 9635919d934..2e967bbcf81 100644 --- a/private/data/i18n/cs.json +++ b/private/data/i18n/cs.json @@ -513,20 +513,6 @@ "isCommercial": "Jedná se o obchodní adresu." } }, - "revisions": { - "isDisabled": "Ovládání revize je zakázáno. Jakékoli změny budou zveřejněny okamžitě.", - "isEnabled": "Ovládání revize je povoleno za produkty. bude muset případné změny, které mají být zveřejněny dříve, než jsou viditelné pro zákazníky.", - "unpublishedChanges": "nepublikované Změny", - "publishChanges": "Publish changes", - "showChanges": "Zobrazit změny", - "hideChanges": "skrýt Změny", - "discardChanges": "Zrušit změny", - "changedPublished": "Změny úspěšně publikován", - "changesDiscarded": "Změny úspěšně zlikvidovat", - "noChanges": "Žádné změny", - "noChangesPublished": "Nejsou žádné změny publikovat", - "noChangesDiscarded": "Nejsou žádné změny k vyhazování" - }, "address": { "country": "Země", "fullName": "Celé jméno", diff --git a/private/data/i18n/de.json b/private/data/i18n/de.json index 33320f8aabb..4d831df918d 100644 --- a/private/data/i18n/de.json +++ b/private/data/i18n/de.json @@ -513,20 +513,6 @@ "isCommercial": "This is a commercial address." } }, - "revisions": { - "isDisabled": "Die Revisionsverwaltung ist deaktiviert. Jegliche Änderungen werden sofort veröffentlicht.", - "isEnabled": "Revisionskontrolle für Produkte aktiviert. Alle Änderungen werden müssen, bevor sie an den Kunden sichtbar veröffentlicht.", - "unpublishedChanges": "Unveröffentlichte Änderungen", - "publishChanges": "Änderungen veröffentlichen", - "showChanges": "Änderungen anzeigen", - "hideChanges": "Änderungen verbergen", - "discardChanges": "Änderungen verwerfen", - "changedPublished": "Die Änderungen wurden erfolgreich veröffentlicht", - "changesDiscarded": "Änderungen erfolgreich verworfen", - "noChanges": "Keine Änderungen", - "noChangesPublished": "Es gibt keine Änderungen zu veröffentlichen", - "noChangesDiscarded": "Keine zu verwerfenden Änderungen gefunden" - }, "address": { "country": "Land", "fullName": "Vor- und Zuname", diff --git a/private/data/i18n/el.json b/private/data/i18n/el.json index 797072181fc..48bf2a57dd1 100644 --- a/private/data/i18n/el.json +++ b/private/data/i18n/el.json @@ -513,20 +513,6 @@ "isCommercial": "Είναι εμπορική διεύθυνση;" } }, - "revisions": { - "isDisabled": "έλεγχος αναθεώρηση είναι απενεργοποιημένη. Οποιεσδήποτε αλλαγές θα δημοσιεύονται αμέσως.", - "isEnabled": "ελέγχου αναθεώρησης είναι ενεργοποιημένη για Προϊόντα. Οποιεσδήποτε αλλαγές θα πρέπει να δημοσιεύονται πριν να είναι ορατή στους πελάτες.", - "unpublishedChanges": "Ανέκδοτες Αλλαγές", - "publishChanges": "Δημοσίευση αλλαγών", - "showChanges": "Εμφάνιση αλλαγών", - "hideChanges": "Απόκρυψη αλλαγών", - "discardChanges": "Απορρίψετε τις αλλαγές", - "changedPublished": "Αλλαγές που δημοσιεύθηκε με επιτυχία", - "changesDiscarded": "Αλλαγές απορρίφθηκε με επιτυχία", - "noChanges": "Χωρίς αλλαγές", - "noChangesPublished": "Δεν υπάρχουν αλλαγές να δημοσιεύσει", - "noChangesDiscarded": "Δεν υπάρχουν αλλαγές για να απορρίψετε" - }, "address": { "country": "Χώρα", "fullName": "Ονοματεπώνυμο", diff --git a/private/data/i18n/en.json b/private/data/i18n/en.json index 7e2dc283599..60848154620 100644 --- a/private/data/i18n/en.json +++ b/private/data/i18n/en.json @@ -526,20 +526,6 @@ "isCommercial": "This is a commercial address." } }, - "revisions": { - "isDisabled": "Revision control is disabled. Any changes will be published immediately.", - "isEnabled": "Revision control is enabled for products. Any changes will be need to be published before being visible to customers.", - "unpublishedChanges": "Unpublished changes", - "publishChanges": "Publish changes", - "showChanges": "Show changes", - "hideChanges": "Hide changes", - "discardChanges": "Discard changes", - "changedPublished": "Changes published successfully", - "changesDiscarded": "Changes discarded successfully", - "noChanges": "No changes", - "noChangesPublished": "There are no changes to publish", - "noChangesDiscarded": "There are no changes to discard" - }, "address": { "country": "Country", "fullName": "Full name", diff --git a/private/data/i18n/es.json b/private/data/i18n/es.json index 4e2812e6f77..20a05158a49 100644 --- a/private/data/i18n/es.json +++ b/private/data/i18n/es.json @@ -513,20 +513,6 @@ "isCommercial": "Esta es una dirección comercial" } }, - "revisions": { - "isDisabled": "El control de revisión está deshabilitado Todos los cambios se publicarán de imediato.", - "isEnabled": "Revisión de control está habilitada para los productos. Se necesitan cualquier cambio que se publicará antes de ser visibles para los clientes.", - "unpublishedChanges": "Cambios sin publicar", - "publishChanges": "Publicar cambios", - "showChanges": "Mostrar cambios", - "hideChanges": "Ocultar cambios", - "discardChanges": "Descartar cambios", - "changedPublished": "Cambios publicados correctamente", - "changesDiscarded": "Los cambios se han descartado", - "noChanges": "Sin cambios", - "noChangesPublished": "No hay cambios para publicar", - "noChangesDiscarded": "No hay cambios que descartar" - }, "address": { "country": "País", "fullName": "Nombre completo", diff --git a/private/data/i18n/fr.json b/private/data/i18n/fr.json index 8a871906296..2810b3c178a 100644 --- a/private/data/i18n/fr.json +++ b/private/data/i18n/fr.json @@ -513,20 +513,6 @@ "isCommercial": "Il s'agit d'une adresse commerciale." } }, - "revisions": { - "isDisabled": "La gestion de versions est désactivée. Toute modification sera immédiatement publiée.", - "isEnabled": "La gestion de versions est activée pour les produits. Toute modification devra être publiée avant d'être visible pour les clients.", - "unpublishedChanges": "Modifications non publiées", - "publishChanges": "Publier les modifications", - "showChanges": "Afficher les modifications", - "hideChanges": "Masquer les modifications", - "discardChanges": "Annuler les modifications", - "changedPublished": "Les modifications ont été publiées avec succès", - "changesDiscarded": "Modifications annulées avec succès", - "noChanges": "Aucune modification", - "noChangesPublished": "Aucune modification à publier", - "noChangesDiscarded": "Aucune modification à annuler" - }, "address": { "country": "Pays", "fullName": "Nom complet", diff --git a/private/data/i18n/he.json b/private/data/i18n/he.json index ff4fec442f1..6618b3fc71c 100644 --- a/private/data/i18n/he.json +++ b/private/data/i18n/he.json @@ -444,20 +444,6 @@ "isCommercial": "האם זו כתובת מסחרית?" } }, - "revisions": { - "isDisabled": "ניהול הגרסאות מושבת. כל השינויים יפורסמו באופן מידי.", - "isEnabled": "ניהול גרסאות מופעל עבור המוצרים. יש לפרסם את כל השינויים לפני שיהפכו להיות גלויים עבור הלקוחות.", - "unpublishedChanges": "שינויים שלא פורסמו", - "publishChanges": "פרסם שינויים", - "showChanges": "הצג שינויים", - "hideChanges": "הסתר שינויים", - "discardChanges": "בטל שינויים", - "changedPublished": "השינויים פורסמו בהצלחה", - "changesDiscarded": "השינויים בוטלו בהצלחה", - "noChanges": "אין שינויים", - "noChangesPublished": "אין שינויים לפרסום", - "noChangesDiscarded": "אין שינויים הניתנים לביטול" - }, "address": { "country": "ארץ", "fullName": "שם פרטי ומשפחה", diff --git a/private/data/i18n/hr.json b/private/data/i18n/hr.json index 43e29a01740..6a3d3d7c810 100644 --- a/private/data/i18n/hr.json +++ b/private/data/i18n/hr.json @@ -513,20 +513,6 @@ "isCommercial": "Ovo je adresa tvrtke." } }, - "revisions": { - "isDisabled": "kontrola Revizija je onemogućen. Sve promjene bit će odmah objavljena.", - "isEnabled": "kontrola Revizija je omogućena za proizvode. Sve promjene bit će morati biti objavljena prije nego što je vidljivo na kupce.", - "unpublishedChanges": "Neobjavljena Promjene", - "publishChanges": "Objavi promjene", - "showChanges": "Prikaži promjene", - "hideChanges": "Sakrij promjene", - "discardChanges": "Odbaciti promjene", - "changedPublished": "Promjene objavljeno uspješno", - "changesDiscarded": "Promjene uspješno odbačena", - "noChanges": "Nema promjena", - "noChangesPublished": "Nema promjena za objavu", - "noChangesDiscarded": "Nema promjena za odbacivanje" - }, "address": { "country": "Država", "fullName": "Puno ime", diff --git a/private/data/i18n/hu.json b/private/data/i18n/hu.json index c33995fadea..20a5be666e5 100644 --- a/private/data/i18n/hu.json +++ b/private/data/i18n/hu.json @@ -513,20 +513,6 @@ "isCommercial": "Céges cím." } }, - "revisions": { - "isDisabled": "Revision szabályozás ki van kapcsolva. A módosításokat haladéktalanul közzé kell tenni.", - "isEnabled": "Revision szabályozás engedélyezve a termékek. A módosításokat közzé kell tenni, mielőtt láthatóvá az ügyfelek számára.", - "unpublishedChanges": "közzétett módosítások", - "publishChanges": "Módosítások közzététele", - "showChanges": "Változások megjelenítése", - "hideChanges": "Változások elrejtése", - "discardChanges": "Módosítások elvetése", - "changedPublished": "Változások közzététele sikeresen", - "changesDiscarded": "Változások sikeresen elvetve", - "noChanges": "Nincs változás", - "noChangesPublished": "Nincs változás közzétételére", - "noChangesDiscarded": "Nincs változás megválni" - }, "address": { "country": "Ország", "fullName": "Teljes név", diff --git a/private/data/i18n/it.json b/private/data/i18n/it.json index 4c3ec615128..a4ff374dcec 100644 --- a/private/data/i18n/it.json +++ b/private/data/i18n/it.json @@ -513,20 +513,6 @@ "isCommercial": "Questo è un indirizzo commerciale." } }, - "revisions": { - "isDisabled": "controllo di revisione è disabilitato. Eventuali modifiche saranno pubblicate immediatamente.", - "isEnabled": "controllo di revisione è abilitato per i prodotti. saranno bisogno di alcuna modifica per essere pubblicato prima di essere visibile ai clienti.", - "unpublishedChanges": "Modifiche non pubblicati", - "publishChanges": "Pubblica modifiche", - "showChanges": "Mostra modifiche", - "hideChanges": "Nascondi le modifiche", - "discardChanges": "Non salvare le modifiche", - "changedPublished": "Modifiche pubblicato con successo", - "changesDiscarded": "Modifiche scartato con successo", - "noChanges": "Nessun cambiamento", - "noChangesPublished": "Non ci sono modifiche da pubblicare", - "noChangesDiscarded": "Non ci sono modifiche da scartare" - }, "address": { "country": "Nazione", "fullName": "Nome e cognome", diff --git a/private/data/i18n/my.json b/private/data/i18n/my.json index 436585cfb6a..d65f08776f6 100644 --- a/private/data/i18n/my.json +++ b/private/data/i18n/my.json @@ -513,20 +513,6 @@ "isCommercial": "ဒါကစီးပွားဖြစ်လိပ်စာဖြစ်ပါတယ်။" } }, - "revisions": { - "isDisabled": "တည်းဖြတ်မူထိန်းချုပ်မှုကိုပိတ်ထားသည်။ မဆိုအပြောင်းအလဲများချက်ချင်းပုံနှိပ်ထုတ်ဝေပါလိမ့်မည်။", - "isEnabled": "တည်းဖြတ်မူထိန်းချုပ်မှုထုတ်ကုန်များအတွက် enabled ဖြစ်ပါတယ်။ မဆိုစသောအပြောင်းအလဲဖောက်သည်မြင်နိုင်ဖြစ်ခြင်းမီကထုတ်ဝေသောခံရဖို့လိုအပ်ပါလိမ့်မည်။", - "unpublishedChanges": "အတည်မပြုရသေးသောအပြောင်းအလဲများ", - "publishChanges": "အပြောင်းအလဲများ Publish", - "showChanges": "အပြောင်းအလဲများ show ကို", - "hideChanges": "အပြောင်းအလဲများဝှက်ရန်", - "discardChanges": "စွန့်ပစ်အပြောင်းအလဲများ", - "changedPublished": "အောင်မြင်စွာပုံနှိပ်ထုတ်ဝေအပြောင်းအလဲများ", - "changesDiscarded": "အောင်မြင်စွာလွှင့်ပစ်အပြောင်းအလဲများ", - "noChanges": "အဘယ်သူမျှမအပြောင်းအလဲများ", - "noChangesPublished": "ထုတ်ဝေဖို့မအပြောင်းအလဲများရှိပါသည်", - "noChangesDiscarded": "ဖယ်ရန်မအပြောင်းအလဲများရှိပါသည်" - }, "address": { "country": "ပြည်", "fullName": "နာမည်အပြည့်အစုံ", diff --git a/private/data/i18n/nl.json b/private/data/i18n/nl.json index 3fc2d72ea49..2acae4c84f7 100644 --- a/private/data/i18n/nl.json +++ b/private/data/i18n/nl.json @@ -513,20 +513,6 @@ "isCommercial": "Dit is een zakelijk adres." } }, - "revisions": { - "isDisabled": "Revisie controle is uitgeschakeld. Eventuele wijzigingen zullen onmiddellijk worden gepubliceerd.", - "isEnabled": "Revisie controle is ingeschakeld voor producten. Eventuele wijzigingen zullen nodig hebben voordat ze zichtbaar zijn voor klanten om te worden gepubliceerd.", - "unpublishedChanges": "ongepubliceerde Wijzigingen", - "publishChanges": "Wijzigingen publiceren", - "showChanges": "Wijzigingen weergeven", - "hideChanges": "verbergen Wijzigingen", - "discardChanges": "Veranderingen ongedaan maken", - "changedPublished": "Wijzigingen met succes gepubliceerd", - "changesDiscarded": "Wijzigingen met succes verwijderd", - "noChanges": "Geen veranderingen", - "noChangesPublished": "Er zijn geen wijzigingen te publiceren", - "noChangesDiscarded": "Er zijn geen wijzigingen te ontdoen" - }, "address": { "country": "Land", "fullName": "Volledige naam", diff --git a/private/data/i18n/pl.json b/private/data/i18n/pl.json index 56f99b88f14..05ca212569f 100644 --- a/private/data/i18n/pl.json +++ b/private/data/i18n/pl.json @@ -513,20 +513,6 @@ "isCommercial": "Adres firmowy." } }, - "revisions": { - "isDisabled": "kontrola wersji jest wyłączona. Wszelkie zmiany będą publikowane natychmiast.", - "isEnabled": "kontrola wersji jest włączona dla Produktów. Wszelkie zmiany muszą być opublikowane, zanim będą widoczne dla klientów.", - "unpublishedChanges": "Niepublikowane Zmiany", - "publishChanges": "Opublikuj zmiany", - "showChanges": "Pokaż zmiany", - "hideChanges": "Schowaj Zmiany", - "discardChanges": "Odrzucać zmiany", - "changedPublished": "Zmiany opublikowane powodzeniem", - "changesDiscarded": "Zmiany odrzucone powodzeniem", - "noChanges": "Bez zmian", - "noChangesPublished": "Brak zmiany publikuj", - "noChangesDiscarded": "Brak zmiany, aby odrzucić" - }, "address": { "country": "Kraj", "fullName": "Pełne imię i nazwisko", diff --git a/private/data/i18n/pt.json b/private/data/i18n/pt.json index 5f699af6586..d461be7156f 100644 --- a/private/data/i18n/pt.json +++ b/private/data/i18n/pt.json @@ -513,20 +513,6 @@ "isCommercial": "Trata-se de um endereço comercial." } }, - "revisions": { - "isDisabled": "O controlo da revisão está desativado. As alterações serão publicadas de imediato.", - "isEnabled": "controle de revisão está habilitado para os produtos. será preciso qualquer alteração a ser publicado antes de ser visível para os clientes.", - "unpublishedChanges": "Alterações não publicadas", - "publishChanges": "Publicar alterações", - "showChanges": "Mostrar alterações", - "hideChanges": "Ocultar alterações", - "discardChanges": "Eliminar alterações", - "changedPublished": "Alterações publicadas com sucesso", - "changesDiscarded": "Alterações eliminadas com sucesso", - "noChanges": "Sem alterações", - "noChangesPublished": "Não há alterações para publicar", - "noChangesDiscarded": "Não há alterações para eliminar" - }, "address": { "country": "País", "fullName": "Nome completo", diff --git a/private/data/i18n/ro.json b/private/data/i18n/ro.json index 4f2b610f977..e853fedc10d 100644 --- a/private/data/i18n/ro.json +++ b/private/data/i18n/ro.json @@ -513,20 +513,6 @@ "isCommercial": "Aceasta este o adresă comercială." } }, - "revisions": { - "isDisabled": "Opțiunea „Revision control” este dezactivată. Orice schimbare va fi imediat publicată.", - "isEnabled": "Controlul revizie este activat pentru produse. Toate modificările vor fi trebui să fie publicate înainte de a fi vizibile pentru clienți.", - "unpublishedChanges": "Schimbări nepublicate", - "publishChanges": "Publicare schimbări", - "showChanges": "Expunere schimbări", - "hideChanges": "Ascundere modificări", - "discardChanges": "Eliminare schimbări", - "changedPublished": "Schimbările au fost publicate cu succes.", - "changesDiscarded": "Schimbări eliminate cu succes", - "noChanges": "Nicio schimbare", - "noChangesPublished": "Nu există modificări pentru publicare", - "noChangesDiscarded": "Nu există nicio schimbare de eliminat" - }, "address": { "country": "Țară", "fullName": "Numele complet", diff --git a/private/data/i18n/ru.json b/private/data/i18n/ru.json index c0894cdb71a..8cf085c8b1d 100644 --- a/private/data/i18n/ru.json +++ b/private/data/i18n/ru.json @@ -513,20 +513,6 @@ "isCommercial": "Это юридический адрес" } }, - "revisions": { - "isDisabled": "Управление версиями отключено. Любые изменения будут немедленно опубликованы.", - "isEnabled": "Контроль версий включена для продуктов. Любые изменения будут должны быть опубликованы до быть видимым для клиентов.", - "unpublishedChanges": "Неопубликованные изменения", - "publishChanges": "Опубликовать изменения", - "showChanges": "Отобразить изменения", - "hideChanges": "Скрыть изменения", - "discardChanges": "Отменить изменения", - "changedPublished": "Изменения успешно опубликованы", - "changesDiscarded": "Изменения успешно отменены", - "noChanges": "Изменений нет", - "noChangesPublished": "Нет изменений для публикации", - "noChangesDiscarded": "Отсутствуют изменения для отмены" - }, "address": { "country": "Страна", "fullName": "Ф.И.О.", diff --git a/private/data/i18n/sl.json b/private/data/i18n/sl.json index a8f36ddafb4..24c746d1a7c 100644 --- a/private/data/i18n/sl.json +++ b/private/data/i18n/sl.json @@ -513,20 +513,6 @@ "isCommercial": "To je komercialna naslov." } }, - "revisions": { - "isDisabled": "Nadzor Revizija je onemogočeno. Vse spremembe bodo objavljene takoj.", - "isEnabled": "Nadzor Revizija je omogočen za izdelke. Vse spremembe bo treba objaviti, preden se vidno strankam.", - "unpublishedChanges": "neobjavljene spremembe", - "publishChanges": "objavi spremembe", - "showChanges": "prikaži spremembe", - "hideChanges": "Skrij spremembe", - "discardChanges": "Zavreči spremembe", - "changedPublished": "Spremembe so bile uspešno objavljeno", - "changesDiscarded": "Spremembe uspešno zavreči", - "noChanges": "ni spremembe", - "noChangesPublished": "Ni spremembe objavijo", - "noChangesDiscarded": "Ni sprememb za zavržke" - }, "address": { "country": "Država", "fullName": "Polno ime", diff --git a/private/data/i18n/sv.json b/private/data/i18n/sv.json index 412408846fa..5b2c4680ab9 100644 --- a/private/data/i18n/sv.json +++ b/private/data/i18n/sv.json @@ -513,20 +513,6 @@ "isCommercial": "Detta är en kommersiell adress." } }, - "revisions": { - "isDisabled": "Versionskontroll är inaktiverad. Eventuella ändringar kommer att publiceras omedelbart.", - "isEnabled": "Versionskontroll har aktiverats för produkter. Eventuella ändringar kommer att behöva publiceras innan de blir synliga för kunderna.", - "unpublishedChanges": "Avpublicera ändringar", - "publishChanges": "publicera ändringar", - "showChanges": "visa ändringar", - "hideChanges": "Göm ändringar", - "discardChanges": "Ignorera ändringar", - "changedPublished": "Ändringarna publicerades", - "changesDiscarded": "Ändringarna kastades bort", - "noChanges": "Inga förändringar", - "noChangesPublished": "Det finns inga ändringar att publicera", - "noChangesDiscarded": "Det finns inga ändringar att avbryta" - }, "address": { "country": "Land", "fullName": "Fullständigt namn", diff --git a/private/data/i18n/tr.json b/private/data/i18n/tr.json index b7e4bd67307..57ab200c640 100644 --- a/private/data/i18n/tr.json +++ b/private/data/i18n/tr.json @@ -513,20 +513,6 @@ "isCommercial": "Bu ticari bir adres." } }, - "revisions": { - "isDisabled": "Revizyon kontrolü devre dışı bırakılır. Herhangi bir değişiklik derhal yayınlanacaktır.", - "isEnabled": "Revizyon kontrol Ürünleri etkindir. Herhangi bir değişiklik müşterilere görünür olmak önce yayınlanmış gerekir edilecektir.", - "unpublishedChanges": "yayınlanmamış değişiklikler", - "publishChanges": "Değişiklikleri Yayınla", - "showChanges": "Değişiklikleri göster", - "hideChanges": "gizle değişiklikler", - "discardChanges": "Değişiklikleri gözardı et", - "changedPublished": "Değişiklikler başarıyla yayınlandı", - "changesDiscarded": "Değişiklikler başarıyla atılır", - "noChanges": "Değişiklik yok", - "noChangesPublished": "yayımlamak için herhangi bir değişiklik bulunmamaktadır", - "noChangesDiscarded": "atmak için herhangi bir değişiklik bulunmamaktadır" - }, "address": { "country": "Ülke", "fullName": "Ad Saoyad", diff --git a/private/data/i18n/vi.json b/private/data/i18n/vi.json index 0e30397153b..6f9b9cadd46 100644 --- a/private/data/i18n/vi.json +++ b/private/data/i18n/vi.json @@ -513,20 +513,6 @@ "isCommercial": "Đây là địa chỉ thương mại." } }, - "revisions": { - "isDisabled": "kiểm soát sửa đổi được vô hiệu hóa. Mọi thay đổi sẽ được công bố ngay lập tức.", - "isEnabled": "kiểm soát sửa đổi được kích hoạt cho sản phẩm. Mọi thay đổi sẽ cần phải được công bố trước khi được rõ cho khách hàng.", - "unpublishedChanges": "Thay đổi chưa được công bố", - "publishChanges": "Xuất bản thay đổi", - "showChanges": "Hiện Thay đổi", - "hideChanges": "Ẩn Thay đổi", - "discardChanges": "Loại bỏ những thay đổi", - "changedPublished": "Thay đổi đăng thành công", - "changesDiscarded": "Thay đổi loại bỏ thành công", - "noChanges": "Không thay đổi", - "noChangesPublished": "Không có thay đổi để xuất bản", - "noChangesDiscarded": "Không có thay đổi để loại bỏ" - }, "address": { "country": "Quốc gia", "fullName": "Họ và tên", diff --git a/private/data/i18n/zh.json b/private/data/i18n/zh.json index d6e80393b39..54f6e8e96df 100644 --- a/private/data/i18n/zh.json +++ b/private/data/i18n/zh.json @@ -513,20 +513,6 @@ "isCommercial": "这是商业地址。" } }, - "revisions": { - "isDisabled": "版本控制已禁用。将立即发布任何更改。", - "isEnabled": "版本控制产品启用。任何更改都将是需要看到客户之前公布。", - "unpublishedChanges": "未发布更改", - "publishChanges": "发布更改", - "showChanges": "显示更改", - "hideChanges": "隐藏更改", - "discardChanges": "放弃更改", - "changedPublished": "更改已成功发布", - "changesDiscarded": "成功放弃更改", - "noChanges": "无更改", - "noChangesPublished": "没有要发布的更改", - "noChangesDiscarded": "没有需要放弃的更改" - }, "address": { "country": "国家", "fullName": "姓名",