From af4c81387ec4d7b5fc225c19441fb0c637920510 Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Wed, 3 May 2017 15:35:48 +0200 Subject: [PATCH 1/9] Framework: Add react-codemod dependency --- npm-shrinkwrap.json | 824 +++++++++++++++++++++++++++++++++++++++++--- package.json | 1 + 2 files changed, 783 insertions(+), 42 deletions(-) diff --git a/npm-shrinkwrap.json b/npm-shrinkwrap.json index 08fdb354480fc..e42a6e015078e 100644 --- a/npm-shrinkwrap.json +++ b/npm-shrinkwrap.json @@ -84,9 +84,17 @@ "ansi-styles": { "version": "2.2.1" }, + "ansicolors": { + "version": "0.2.1", + "dev": true + }, "anymatch": { "version": "1.3.0" }, + "append-transform": { + "version": "0.4.0", + "dev": true + }, "aproba": { "version": "1.1.1" }, @@ -265,6 +273,10 @@ "babel-helpers": { "version": "6.24.1" }, + "babel-jest": { + "version": "15.0.0", + "dev": true + }, "babel-loader": { "version": "6.2.4" }, @@ -293,6 +305,14 @@ "version": "1.0.1", "dev": true }, + "babel-plugin-istanbul": { + "version": "2.0.3", + "dev": true + }, + "babel-plugin-jest-hoist": { + "version": "15.0.0", + "dev": true + }, "babel-plugin-jscript": { "version": "1.0.4", "dev": true @@ -452,6 +472,14 @@ "babel-plugin-transform-es2015-unicode-regex": { "version": "6.24.1" }, + "babel-plugin-transform-es3-member-expression-literals": { + "version": "6.22.0", + "dev": true + }, + "babel-plugin-transform-es3-property-literals": { + "version": "6.22.0", + "dev": true + }, "babel-plugin-transform-exponentiation-operator": { "version": "6.24.1" }, @@ -494,6 +522,14 @@ "babel-preset-es2015": { "version": "6.9.0" }, + "babel-preset-fbjs": { + "version": "1.0.0", + "dev": true + }, + "babel-preset-jest": { + "version": "15.0.0", + "dev": true + }, "babel-preset-stage-1": { "version": "6.24.1", "dev": true, @@ -573,6 +609,10 @@ "version": "0.5.3", "dev": true }, + "beeper": { + "version": "1.1.1", + "dev": true + }, "benchmark": { "version": "1.0.0" }, @@ -652,6 +692,16 @@ "browser-filesaver": { "version": "1.1.0" }, + "browser-resolve": { + "version": "1.11.2", + "dev": true, + "dependencies": { + "resolve": { + "version": "1.1.7", + "dev": true + } + } + }, "browser-stdout": { "version": "1.3.0", "dev": true @@ -662,6 +712,10 @@ "browserslist": { "version": "1.3.6" }, + "bser": { + "version": "1.0.2", + "dev": true + }, "buffer": { "version": "4.9.1" }, @@ -705,6 +759,10 @@ "caniuse-db": { "version": "1.0.30000666" }, + "cardinal": { + "version": "1.0.0", + "dev": true + }, "caseless": { "version": "0.12.0" }, @@ -765,6 +823,10 @@ "chrono-node": { "version": "1.3.1" }, + "ci-info": { + "version": "1.0.0", + "dev": true + }, "circular-json": { "version": "0.3.1", "dev": true @@ -787,6 +849,26 @@ "version": "1.0.2", "dev": true }, + "cli-table": { + "version": "0.3.1", + "dev": true, + "dependencies": { + "colors": { + "version": "1.0.3", + "dev": true + } + } + }, + "cli-usage": { + "version": "0.1.4", + "dev": true, + "dependencies": { + "marked": { + "version": "0.3.6", + "dev": true + } + } + }, "cli-width": { "version": "2.1.0", "dev": true @@ -807,6 +889,10 @@ "version": "1.0.0", "dev": true }, + "clone-stats": { + "version": "0.0.1", + "dev": true + }, "co": { "version": "4.6.0" }, @@ -943,6 +1029,10 @@ "content-type": { "version": "1.0.2" }, + "content-type-parser": { + "version": "1.0.1", + "dev": true + }, "convert-source-map": { "version": "1.5.0" }, @@ -995,7 +1085,7 @@ "version": "1.6.1" }, "cross-spawn": { - "version": "4.0.2", + "version": "3.0.1", "dev": true }, "cross-spawn-async": { @@ -1057,6 +1147,10 @@ "date-now": { "version": "0.1.4" }, + "dateformat": { + "version": "2.0.0", + "dev": true + }, "debug": { "version": "2.2.0" }, @@ -1088,6 +1182,10 @@ "version": "0.1.3", "dev": true }, + "default-require-extensions": { + "version": "1.0.0", + "dev": true + }, "defaults-deep": { "version": "0.2.3", "dev": true, @@ -1643,6 +1741,10 @@ "events": { "version": "1.0.2" }, + "exec-sh": { + "version": "0.2.0", + "dev": true + }, "execall": { "version": "1.0.0", "dev": true @@ -1703,6 +1805,20 @@ } } }, + "fancy-log": { + "version": "1.3.0", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + } + } + }, "fast-future": { "version": "1.0.2" }, @@ -1716,6 +1832,10 @@ "fastparse": { "version": "1.1.1" }, + "fb-watchman": { + "version": "1.9.2", + "dev": true + }, "fbemitter": { "version": "2.1.1" }, @@ -1727,6 +1847,28 @@ } } }, + "fbjs-scripts": { + "version": "0.7.1", + "dev": true, + "dependencies": { + "core-js": { + "version": "1.2.7", + "dev": true + }, + "readable-stream": { + "version": "2.2.9", + "dev": true + }, + "string_decoder": { + "version": "1.0.0", + "dev": true + }, + "through2": { + "version": "2.0.3", + "dev": true + } + } + }, "figures": { "version": "1.7.0", "dev": true, @@ -1744,6 +1886,16 @@ "filename-regex": { "version": "2.0.1" }, + "fileset": { + "version": "2.0.3", + "dev": true, + "dependencies": { + "minimatch": { + "version": "3.0.4", + "dev": true + } + } + }, "filesize": { "version": "3.2.1" }, @@ -1941,6 +2093,10 @@ } } }, + "glogg": { + "version": "1.0.0", + "dev": true + }, "good-listener": { "version": "1.2.2" }, @@ -1967,10 +2123,58 @@ "version": "1.9.2", "dev": true }, + "growly": { + "version": "1.3.0", + "dev": true + }, + "gulp-util": { + "version": "3.0.8", + "dev": true, + "dependencies": { + "minimist": { + "version": "1.2.0", + "dev": true + }, + "object-assign": { + "version": "3.0.0", + "dev": true + }, + "readable-stream": { + "version": "2.2.9", + "dev": true + }, + "string_decoder": { + "version": "1.0.0", + "dev": true + }, + "through2": { + "version": "2.0.3", + "dev": true + } + } + }, + "gulplog": { + "version": "1.0.0", + "dev": true + }, "gzip-size": { "version": "3.0.0", "dev": true }, + "handlebars": { + "version": "4.0.8", + "dev": true, + "dependencies": { + "async": { + "version": "1.5.2", + "dev": true + }, + "source-map": { + "version": "0.4.4", + "dev": true + } + } + }, "har-schema": { "version": "1.0.5" }, @@ -2012,6 +2216,10 @@ "has-flag": { "version": "1.0.0" }, + "has-gulplog": { + "version": "0.1.0", + "dev": true + }, "has-unicode": { "version": "2.0.1" }, @@ -2037,6 +2245,10 @@ "version": "1.0.0", "dev": true }, + "html-encoding-sniffer": { + "version": "1.0.1", + "dev": true + }, "html-loader": { "version": "0.4.0", "dependencies": { @@ -2203,6 +2415,10 @@ "version": "1.1.3", "dev": true }, + "is-ci": { + "version": "1.0.10", + "dev": true + }, "is-date-object": { "version": "1.0.1", "dev": true @@ -2342,6 +2558,90 @@ "isstream": { "version": "0.1.2" }, + "istanbul": { + "version": "0.4.5", + "dev": true, + "dependencies": { + "abbrev": { + "version": "1.0.9", + "dev": true + }, + "async": { + "version": "1.5.2", + "dev": true + }, + "esprima": { + "version": "2.7.3", + "dev": true + }, + "glob": { + "version": "5.0.15", + "dev": true + }, + "resolve": { + "version": "1.1.7", + "dev": true + }, + "wordwrap": { + "version": "1.0.0", + "dev": true + } + } + }, + "istanbul-api": { + "version": "1.1.8", + "dev": true, + "dependencies": { + "async": { + "version": "2.4.0", + "dev": true + } + } + }, + "istanbul-lib-coverage": { + "version": "1.1.0", + "dev": true + }, + "istanbul-lib-hook": { + "version": "1.0.6", + "dev": true + }, + "istanbul-lib-instrument": { + "version": "1.7.1", + "dev": true, + "dependencies": { + "semver": { + "version": "5.3.0", + "dev": true + } + } + }, + "istanbul-lib-report": { + "version": "1.1.0", + "dev": true + }, + "istanbul-lib-source-maps": { + "version": "1.2.0", + "dev": true, + "dependencies": { + "debug": { + "version": "2.6.6", + "dev": true + }, + "ms": { + "version": "0.7.3", + "dev": true + }, + "source-map": { + "version": "0.5.6", + "dev": true + } + } + }, + "istanbul-reports": { + "version": "1.1.0", + "dev": true + }, "jade": { "version": "1.11.0", "from": "git://github.com/pugjs/jade.git#29784fd1ec6043397f4b43d45b4ee9e25177b940", @@ -2363,44 +2663,224 @@ } } }, - "jade-error": { - "version": "1.2.0" - }, - "jade-filters": { - "version": "1.1.0" + "jade-error": { + "version": "1.2.0" + }, + "jade-filters": { + "version": "1.1.0" + }, + "jade-lexer": { + "version": "0.0.9", + "dependencies": { + "acorn": { + "version": "2.7.0" + }, + "is-expression": { + "version": "1.0.2" + } + } + }, + "jade-linker": { + "version": "0.0.3" + }, + "jade-load": { + "version": "0.0.4" + }, + "jade-parser": { + "version": "0.0.9" + }, + "jade-runtime": { + "version": "2.0.0" + }, + "jade-strip-comments": { + "version": "1.0.0" + }, + "jade-walk": { + "version": "0.0.3" + }, + "jed": { + "version": "1.0.2" + }, + "jest": { + "version": "17.0.3", + "dev": true, + "dependencies": { + "callsites": { + "version": "2.0.0", + "dev": true + }, + "camelcase": { + "version": "3.0.0", + "dev": true + }, + "chalk": { + "version": "1.1.3", + "dev": true + }, + "cliui": { + "version": "3.2.0", + "dev": true + }, + "jest-cli": { + "version": "17.0.3", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + }, + "yargs": { + "version": "6.6.0", + "dev": true + } + } + }, + "jest-changed-files": { + "version": "17.0.2", + "dev": true + }, + "jest-config": { + "version": "17.0.3", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + } + } + }, + "jest-diff": { + "version": "17.0.3", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "diff": { + "version": "3.2.0", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + } + } + }, + "jest-environment-jsdom": { + "version": "17.0.2", + "dev": true + }, + "jest-environment-node": { + "version": "17.0.2", + "dev": true + }, + "jest-file-exists": { + "version": "17.0.0", + "dev": true + }, + "jest-haste-map": { + "version": "17.0.3", + "dev": true + }, + "jest-jasmine2": { + "version": "17.0.3", + "dev": true + }, + "jest-matcher-utils": { + "version": "17.0.3", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + } + } + }, + "jest-matchers": { + "version": "17.0.3", + "dev": true + }, + "jest-mock": { + "version": "17.0.2", + "dev": true + }, + "jest-resolve": { + "version": "17.0.3", + "dev": true + }, + "jest-resolve-dependencies": { + "version": "17.0.3", + "dev": true + }, + "jest-runtime": { + "version": "17.0.3", + "dev": true, + "dependencies": { + "babel-jest": { + "version": "17.0.2", + "dev": true + }, + "babel-plugin-jest-hoist": { + "version": "17.0.2", + "dev": true + }, + "babel-preset-jest": { + "version": "17.0.2", + "dev": true + }, + "camelcase": { + "version": "3.0.0", + "dev": true + }, + "chalk": { + "version": "1.1.3", + "dev": true + }, + "cliui": { + "version": "3.2.0", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + }, + "yargs": { + "version": "6.6.0", + "dev": true + } + } + }, + "jest-snapshot": { + "version": "17.0.3", + "dev": true }, - "jade-lexer": { - "version": "0.0.9", + "jest-util": { + "version": "17.0.2", + "dev": true, "dependencies": { - "acorn": { - "version": "2.7.0" + "chalk": { + "version": "1.1.3", + "dev": true }, - "is-expression": { - "version": "1.0.2" + "diff": { + "version": "3.2.0", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true } } }, - "jade-linker": { - "version": "0.0.3" - }, - "jade-load": { - "version": "0.0.4" - }, - "jade-parser": { - "version": "0.0.9" - }, - "jade-runtime": { - "version": "2.0.0" - }, - "jade-strip-comments": { - "version": "1.0.0" - }, - "jade-walk": { - "version": "0.0.3" - }, - "jed": { - "version": "1.0.2" - }, "jquery": { "version": "1.11.3" }, @@ -2491,15 +2971,11 @@ } }, "jsdom": { - "version": "9.4.1", + "version": "9.12.0", "dev": true, "dependencies": { "acorn": { - "version": "2.7.0", - "dev": true - }, - "acorn-globals": { - "version": "1.0.9", + "version": "4.0.11", "dev": true } } @@ -2668,10 +3144,22 @@ "lodash-es": { "version": "4.17.4" }, + "lodash._arraycopy": { + "version": "3.0.0", + "dev": true + }, + "lodash._arrayeach": { + "version": "3.0.0", + "dev": true + }, "lodash._baseassign": { "version": "3.2.0", "dev": true }, + "lodash._baseclone": { + "version": "3.3.0", + "dev": true + }, "lodash._basecopy": { "version": "3.0.1", "dev": true @@ -2680,6 +3168,22 @@ "version": "3.0.3", "dev": true }, + "lodash._basefor": { + "version": "3.0.3", + "dev": true + }, + "lodash._basetostring": { + "version": "3.0.1", + "dev": true + }, + "lodash._basevalues": { + "version": "3.0.0", + "dev": true + }, + "lodash._bindcallback": { + "version": "3.0.1", + "dev": true + }, "lodash._getnative": { "version": "3.9.1", "dev": true @@ -2688,13 +3192,37 @@ "version": "3.0.9", "dev": true }, + "lodash._reescape": { + "version": "3.0.0", + "dev": true + }, + "lodash._reevaluate": { + "version": "3.0.0", + "dev": true + }, + "lodash._reinterpolate": { + "version": "3.0.0", + "dev": true + }, + "lodash._root": { + "version": "3.0.1", + "dev": true + }, "lodash.assign": { "version": "4.2.0" }, + "lodash.clonedeep": { + "version": "3.0.2", + "dev": true + }, "lodash.create": { "version": "3.1.1", "dev": true }, + "lodash.escape": { + "version": "3.2.0", + "dev": true + }, "lodash.flatten": { "version": "4.4.0" }, @@ -2717,6 +3245,18 @@ "version": "4.6.0", "dev": true }, + "lodash.restparam": { + "version": "3.6.1", + "dev": true + }, + "lodash.template": { + "version": "3.6.2", + "dev": true + }, + "lodash.templatesettings": { + "version": "3.1.1", + "dev": true + }, "log-symbols": { "version": "1.0.2", "dev": true @@ -2753,12 +3293,30 @@ "lunr": { "version": "0.5.7" }, + "makeerror": { + "version": "1.0.11", + "dev": true + }, "map-obj": { "version": "1.0.1" }, "marked": { "version": "0.3.5" }, + "marked-terminal": { + "version": "1.7.0", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + } + } + }, "md5": { "version": "2.2.1", "dev": true @@ -2789,6 +3347,10 @@ } } }, + "merge": { + "version": "1.2.0", + "dev": true + }, "merge-descriptors": { "version": "1.0.0" }, @@ -2894,6 +3456,10 @@ } } }, + "multipipe": { + "version": "0.1.2", + "dev": true + }, "mute-stream": { "version": "0.0.5", "dev": true @@ -2946,6 +3512,10 @@ } } }, + "node-emoji": { + "version": "1.5.1", + "dev": true + }, "node-fetch": { "version": "1.6.3" }, @@ -2960,9 +3530,23 @@ } } }, + "node-int64": { + "version": "0.4.0", + "dev": true + }, "node-libs-browser": { "version": "0.6.0" }, + "node-notifier": { + "version": "4.6.1", + "dev": true, + "dependencies": { + "minimist": { + "version": "1.2.0", + "dev": true + } + } + }, "node-sass": { "version": "3.7.0", "dependencies": { @@ -3194,6 +3778,10 @@ "pascal-case": { "version": "1.1.2" }, + "path": { + "version": "0.12.7", + "dev": true + }, "path-browserify": { "version": "0.0.0" }, @@ -3318,6 +3906,10 @@ "preserve": { "version": "0.2.0" }, + "pretty-format": { + "version": "4.2.3", + "dev": true + }, "prismjs": { "version": "1.6.0" }, @@ -3427,6 +4019,42 @@ "react-click-outside": { "version": "2.1.0" }, + "react-codemod": { + "version": "4.0.0", + "from": "git://github.com/reactjs/react-codemod.git#d6563d988c1dbc4a94d4c67f4eb85ab12f2f70ea", + "resolved": "git://github.com/reactjs/react-codemod.git#d6563d988c1dbc4a94d4c67f4eb85ab12f2f70ea", + "dev": true, + "dependencies": { + "chalk": { + "version": "1.1.3", + "dev": true + }, + "doctrine": { + "version": "1.5.0", + "dev": true + }, + "eslint": { + "version": "2.13.1", + "dev": true + }, + "file-entry-cache": { + "version": "1.3.1", + "dev": true + }, + "strip-json-comments": { + "version": "1.0.4", + "dev": true + }, + "supports-color": { + "version": "2.0.0", + "dev": true + }, + "user-home": { + "version": "2.0.0", + "dev": true + } + } + }, "react-day-picker": { "version": "2.4.1" }, @@ -3481,9 +4109,29 @@ "version": "0.2.0", "dev": true, "dependencies": { + "acorn": { + "version": "2.7.0", + "dev": true + }, + "acorn-globals": { + "version": "1.0.9", + "dev": true + }, + "jsdom": { + "version": "9.4.1", + "dev": true + }, "lodash.assign": { "version": "4.1.0", "dev": true + }, + "webidl-conversions": { + "version": "3.0.1", + "dev": true + }, + "whatwg-url": { + "version": "3.1.0", + "dev": true } } }, @@ -3559,6 +4207,16 @@ "redent": { "version": "1.0.0" }, + "redeyed": { + "version": "1.0.1", + "dev": true, + "dependencies": { + "esprima": { + "version": "3.0.0", + "dev": true + } + } + }, "reduce-component": { "version": "1.0.1" }, @@ -3666,6 +4324,10 @@ "repeating": { "version": "2.0.1" }, + "replace-ext": { + "version": "0.0.1", + "dev": true + }, "request": { "version": "2.81.0", "dependencies": { @@ -3790,6 +4452,20 @@ "version": "1.1.2", "dev": true }, + "sane": { + "version": "1.4.1", + "dev": true, + "dependencies": { + "minimatch": { + "version": "3.0.4", + "dev": true + }, + "minimist": { + "version": "1.2.0", + "dev": true + } + } + }, "sanitize-html": { "version": "1.11.1" }, @@ -3925,6 +4601,10 @@ "version": "0.6.1", "dev": true }, + "shellwords": { + "version": "0.1.0", + "dev": true + }, "sigmund": { "version": "1.0.1", "dev": true @@ -4038,6 +4718,10 @@ } } }, + "sparkles": { + "version": "1.0.0", + "dev": true + }, "spdx-correct": { "version": "1.0.2" }, @@ -4106,6 +4790,10 @@ "string-width": { "version": "1.0.2" }, + "string.prototype.codepointat": { + "version": "0.2.0", + "dev": true + }, "stringify-object": { "version": "2.4.0", "dev": true @@ -4298,10 +4986,18 @@ } } }, + "test-exclude": { + "version": "2.1.3", + "dev": true + }, "text-table": { "version": "0.2.0", "dev": true }, + "throat": { + "version": "3.0.0", + "dev": true + }, "through": { "version": "2.3.8" }, @@ -4316,6 +5012,10 @@ } } }, + "time-stamp": { + "version": "1.0.1", + "dev": true + }, "timed-out": { "version": "2.0.0", "dev": true @@ -4335,6 +5035,10 @@ "title-case-minors": { "version": "0.0.2" }, + "tmpl": { + "version": "1.0.4", + "dev": true + }, "to-array": { "version": "0.1.4" }, @@ -4541,6 +5245,10 @@ "verror": { "version": "1.3.6" }, + "vinyl": { + "version": "0.5.3", + "dev": true + }, "vm-browserify": { "version": "0.0.4" }, @@ -4550,11 +5258,19 @@ "walk": { "version": "2.3.4" }, + "walker": { + "version": "1.0.7", + "dev": true + }, + "watch": { + "version": "0.10.0", + "dev": true + }, "watchpack": { "version": "0.2.9" }, "webidl-conversions": { - "version": "3.0.1", + "version": "4.0.1", "dev": true }, "webpack": { @@ -4740,6 +5456,10 @@ "version": "0.3.1", "dev": true }, + "cross-spawn": { + "version": "4.0.2", + "dev": true + }, "debug": { "version": "2.3.3", "dev": true @@ -4863,12 +5583,28 @@ "wemoji": { "version": "0.1.9" }, + "whatwg-encoding": { + "version": "1.0.1", + "dev": true, + "dependencies": { + "iconv-lite": { + "version": "0.4.13", + "dev": true + } + } + }, "whatwg-fetch": { "version": "2.0.3" }, "whatwg-url": { - "version": "3.1.0", - "dev": true + "version": "4.7.1", + "dev": true, + "dependencies": { + "webidl-conversions": { + "version": "3.0.1", + "dev": true + } + } }, "which": { "version": "1.2.14" @@ -4888,6 +5624,10 @@ "wordwrap": { "version": "0.0.2" }, + "worker-farm": { + "version": "1.3.1", + "dev": true + }, "wp-error": { "version": "1.3.0" }, diff --git a/package.json b/package.json index 70aecc42e147c..5094f2c4d6e28 100644 --- a/package.json +++ b/package.json @@ -184,6 +184,7 @@ "nock": "8.0.0", "nodemon": "1.4.1", "react-addons-test-utils": "15.4.0", + "react-codemod": "github:reactjs/react-codemod", "react-hot-loader": "1.3.0", "react-test-env": "0.2.0", "readline-sync": "1.4.5", From e12107c19b8780b74a5fd2544edfec9e56ee4f03 Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Wed, 3 May 2017 15:36:11 +0200 Subject: [PATCH 2/9] Framework: Add i18n-translate codemod --- bin/codemods/i18n-translate | 42 ++++++++++++++++++++++ bin/codemods/i18n-translate-to-localize.js | 31 ++++++++++++++++ 2 files changed, 73 insertions(+) create mode 100755 bin/codemods/i18n-translate create mode 100644 bin/codemods/i18n-translate-to-localize.js diff --git a/bin/codemods/i18n-translate b/bin/codemods/i18n-translate new file mode 100755 index 0000000000000..f0d7408b34eaa --- /dev/null +++ b/bin/codemods/i18n-translate @@ -0,0 +1,42 @@ +#!/usr/bin/env node + +/* + This codemod converts `this.translate` to `this.props.translate`, and wraps the corresponding + React.createClass instance with a `localize()` higher-order component. + + How to use: + ./bin/codemods/i18n-translate path-to-transform/ +*/ + +/** + * External dependencies + */ +const path = require( 'path' ); +const child_process = require( 'child_process' ); + +/** + * Internal dependencies + */ +const config = require( './config' ); +const helpers = require( './helpers' ); + +const args = process.argv.slice( 2 ); +if ( args.length === 0 ) { + process.stdout.write( 'No files to transform\n' ); + process.exit( 0 ); +} + +const binArgs = [ + // jscodeshift options + '--transform=bin/codemods/i18n-translate-to-localize.js', + ...config.jscodeshiftArgs, + + // Recast options via 5to6 + ...config.recastArgs, + + // Transform target + args[ 0 ], +]; +const binPath = path.join( '.', 'node_modules', '.bin', 'jscodeshift' ); +const jscodeshift = child_process.spawn( binPath, binArgs ); +helpers.bindEvents( jscodeshift ); diff --git a/bin/codemods/i18n-translate-to-localize.js b/bin/codemods/i18n-translate-to-localize.js new file mode 100644 index 0000000000000..8a1d2d3fe860b --- /dev/null +++ b/bin/codemods/i18n-translate-to-localize.js @@ -0,0 +1,31 @@ +export default function transformer(file, api) { + const j = api.jscodeshift; + const ReactUtils = require('react-codemod/transforms/utils/ReactUtils')(j); + const root = j(file.source); + + const createClassesInstances = ReactUtils.findAllReactCreateClassCalls( root ); + + createClassesInstances.forEach( createClassInstance => { + const thisTranslateInstances = j(createClassInstance).find(j.MemberExpression, { + object: { type: 'ThisExpression'}, + property: { + type: 'Identifier', + name: 'translate' + } + }); + thisTranslateInstances.replaceWith( () => ( + j.memberExpression( + j.memberExpression( + j.thisExpression(), + j.identifier('props') + ), + j.identifier('translate') + ) + ) ); + } ); + + return root + .toSource({ + useTabs: true + }); +} From d0debc04785858e7c4b9af1ebc7d84691343256e Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Wed, 3 May 2017 15:50:27 +0200 Subject: [PATCH 3/9] Wrap in localize --- bin/codemods/i18n-translate-to-localize.js | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/bin/codemods/i18n-translate-to-localize.js b/bin/codemods/i18n-translate-to-localize.js index 8a1d2d3fe860b..f5dfaf345aa07 100644 --- a/bin/codemods/i18n-translate-to-localize.js +++ b/bin/codemods/i18n-translate-to-localize.js @@ -22,6 +22,14 @@ export default function transformer(file, api) { j.identifier('translate') ) ) ); + if (thisTranslateInstances.size()) { + j(createClassInstance).replaceWith( () => ( + j.callExpression( + j.identifier('localize'), + [ createClassInstance.value ] + ) + )); + } } ); return root From 2b4c83a60e19ca8848fefd54f9b3bc04e5e4a0ea Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Thu, 4 May 2017 12:44:47 +0200 Subject: [PATCH 4/9] Rename codemod and script --- bin/codemods/{i18n-translate => i18n-mixin} | 4 ++-- ...18n-translate-to-localize.js => i18n-mixin-to-localize.js} | 0 2 files changed, 2 insertions(+), 2 deletions(-) rename bin/codemods/{i18n-translate => i18n-mixin} (89%) rename bin/codemods/{i18n-translate-to-localize.js => i18n-mixin-to-localize.js} (100%) diff --git a/bin/codemods/i18n-translate b/bin/codemods/i18n-mixin similarity index 89% rename from bin/codemods/i18n-translate rename to bin/codemods/i18n-mixin index f0d7408b34eaa..7de3160857e78 100755 --- a/bin/codemods/i18n-translate +++ b/bin/codemods/i18n-mixin @@ -5,7 +5,7 @@ React.createClass instance with a `localize()` higher-order component. How to use: - ./bin/codemods/i18n-translate path-to-transform/ + ./bin/codemods/i18n-mixin path-to-transform/ */ /** @@ -28,7 +28,7 @@ if ( args.length === 0 ) { const binArgs = [ // jscodeshift options - '--transform=bin/codemods/i18n-translate-to-localize.js', + '--transform=bin/codemods/i18n-mixin-to-localize.js', ...config.jscodeshiftArgs, // Recast options via 5to6 diff --git a/bin/codemods/i18n-translate-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js similarity index 100% rename from bin/codemods/i18n-translate-to-localize.js rename to bin/codemods/i18n-mixin-to-localize.js From 7a5f637d0e83257893a3be0702b4f2500fb01ff8 Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Thu, 4 May 2017 14:51:06 +0200 Subject: [PATCH 5/9] Import localize --- bin/codemods/i18n-mixin-to-localize.js | 1 + 1 file changed, 1 insertion(+) diff --git a/bin/codemods/i18n-mixin-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js index f5dfaf345aa07..f46138a9d4241 100644 --- a/bin/codemods/i18n-mixin-to-localize.js +++ b/bin/codemods/i18n-mixin-to-localize.js @@ -29,6 +29,7 @@ export default function transformer(file, api) { [ createClassInstance.value ] ) )); + root.find(j.ImportDeclaration).at(0).insertBefore('import { localize } from \'i18n-calypso\';'); } } ); From 299f2da1dde35301a664600cf1ab06005f50fb19 Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Thu, 4 May 2017 17:21:01 +0200 Subject: [PATCH 6/9] Be smarter about localize import --- bin/codemods/i18n-mixin-to-localize.js | 21 ++++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) diff --git a/bin/codemods/i18n-mixin-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js index f46138a9d4241..5256ffd9cc924 100644 --- a/bin/codemods/i18n-mixin-to-localize.js +++ b/bin/codemods/i18n-mixin-to-localize.js @@ -29,7 +29,26 @@ export default function transformer(file, api) { [ createClassInstance.value ] ) )); - root.find(j.ImportDeclaration).at(0).insertBefore('import { localize } from \'i18n-calypso\';'); + + const i18nCalypsoImports = root.find(j.ImportDeclaration, { + source: { value: 'i18n-calypso' } + }) + if ( i18nCalypsoImports.size() ) { + const i18nCalypsoImport = i18nCalypsoImports.get(); + const localizeImport = j(i18nCalypsoImport).find(j.ImportSpecifier, { + local: { + type: 'Identifier', + name: 'localize' + } + }); + if ( ! localizeImport.size() ) { + i18nCalypsoImport.value.specifiers.push( j.importSpecifier( + j.identifier('localize') + )); + } + } else { + root.find(j.ImportDeclaration).at(0).insertAfter('import { localize } from \'i18n-calypso\';'); + } } } ); From fe6690be2af560842a267060d7714122482c18fc Mon Sep 17 00:00:00 2001 From: Bernhard Reiter Date: Mon, 8 May 2017 16:04:47 +0200 Subject: [PATCH 7/9] Don't duplicate localize imports --- bin/codemods/i18n-mixin-to-localize.js | 40 ++++++++++++++------------ 1 file changed, 22 insertions(+), 18 deletions(-) diff --git a/bin/codemods/i18n-mixin-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js index 5256ffd9cc924..a290e51a0b32f 100644 --- a/bin/codemods/i18n-mixin-to-localize.js +++ b/bin/codemods/i18n-mixin-to-localize.js @@ -2,6 +2,7 @@ export default function transformer(file, api) { const j = api.jscodeshift; const ReactUtils = require('react-codemod/transforms/utils/ReactUtils')(j); const root = j(file.source); + let foundThisTranslate = false; const createClassesInstances = ReactUtils.findAllReactCreateClassCalls( root ); @@ -23,34 +24,37 @@ export default function transformer(file, api) { ) ) ); if (thisTranslateInstances.size()) { + foundThisTranslate = true; j(createClassInstance).replaceWith( () => ( j.callExpression( j.identifier('localize'), [ createClassInstance.value ] ) )); + } + } ); - const i18nCalypsoImports = root.find(j.ImportDeclaration, { - source: { value: 'i18n-calypso' } - }) - if ( i18nCalypsoImports.size() ) { - const i18nCalypsoImport = i18nCalypsoImports.get(); - const localizeImport = j(i18nCalypsoImport).find(j.ImportSpecifier, { - local: { - type: 'Identifier', - name: 'localize' - } - }); - if ( ! localizeImport.size() ) { - i18nCalypsoImport.value.specifiers.push( j.importSpecifier( - j.identifier('localize') - )); + if ( foundThisTranslate ) { + const i18nCalypsoImports = root.find(j.ImportDeclaration, { + source: { value: 'i18n-calypso' } + }) + if ( i18nCalypsoImports.size() ) { + const i18nCalypsoImport = i18nCalypsoImports.get(); + const localizeImport = j(i18nCalypsoImport).find(j.ImportSpecifier, { + local: { + type: 'Identifier', + name: 'localize' } - } else { - root.find(j.ImportDeclaration).at(0).insertAfter('import { localize } from \'i18n-calypso\';'); + }); + if ( ! localizeImport.size() ) { + i18nCalypsoImport.value.specifiers.push( j.importSpecifier( + j.identifier('localize') + )); } + } else { + root.find(j.ImportDeclaration).at(0).insertAfter('import { localize } from \'i18n-calypso\';'); } - } ); + } return root .toSource({ From 312d3953ad929435d22fab9ec2b47bb60bc435a1 Mon Sep 17 00:00:00 2001 From: Jarda Snajdr Date: Tue, 9 May 2017 18:28:11 +0200 Subject: [PATCH 8/9] Wrap the exports instead of createClass if possible If the result of 'React.createClass' is assigned to a variable and that variable is later exported with 'export default' or 'module.exports =', wrap the exported variable with 'localize': export default localize( TheComponent ); --- bin/codemods/i18n-mixin-to-localize.js | 54 ++++++++++++++++++++++++-- 1 file changed, 50 insertions(+), 4 deletions(-) diff --git a/bin/codemods/i18n-mixin-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js index a290e51a0b32f..f4fb1c18572f1 100644 --- a/bin/codemods/i18n-mixin-to-localize.js +++ b/bin/codemods/i18n-mixin-to-localize.js @@ -6,6 +6,50 @@ export default function transformer(file, api) { const createClassesInstances = ReactUtils.findAllReactCreateClassCalls( root ); + // Find the declaration to wrap with the localize HOC. It can be the React.createClass + // itself, or an 'export default' or 'module.exports =' declaration, if present. + function findDeclarationsToWrap( createClassInstance ) { + // Is the created class being assigned to a variable? + const parentNode = createClassInstance.parentPath.value; + if (parentNode.type !== 'VariableDeclarator' || parentNode.id.type !== 'Identifier') { + return j(createClassInstance); + } + + const classIdentifier = { + type: 'Identifier', + name: parentNode.id.name, + }; + + // Is the variable later exported with 'export default'? + const exportDefaultDeclarations = root.find(j.ExportDefaultDeclaration, { + declaration: classIdentifier + }); + if (exportDefaultDeclarations.size()) { + return exportDefaultDeclarations.map(d => d.get('declaration')); + } + + // Is the variable later exported with 'module.exports ='? + const moduleExportsDeclarations = root.find(j.AssignmentExpression, { + left: { + type: 'MemberExpression', + object: { + type: 'Identifier', + name: 'module' + }, + property: { + type: 'Identifier', + name: 'exports', + } + }, + right: classIdentifier + }); + if (moduleExportsDeclarations.size()) { + return moduleExportsDeclarations.map(d => d.get('right')); + } + + return j(createClassInstance); + } + createClassesInstances.forEach( createClassInstance => { const thisTranslateInstances = j(createClassInstance).find(j.MemberExpression, { object: { type: 'ThisExpression'}, @@ -25,12 +69,14 @@ export default function transformer(file, api) { ) ); if (thisTranslateInstances.size()) { foundThisTranslate = true; - j(createClassInstance).replaceWith( () => ( - j.callExpression( + + const declarationsToWrap = findDeclarationsToWrap(createClassInstance); + declarationsToWrap.replaceWith( decl => { + return j.callExpression( j.identifier('localize'), - [ createClassInstance.value ] + [ decl.value ] ) - )); + }); } } ); From 700bcd2be862bd2df56d62a864131e1f9c07ef54 Mon Sep 17 00:00:00 2001 From: Jarda Snajdr Date: Tue, 9 May 2017 22:18:27 +0200 Subject: [PATCH 9/9] Wrap exports with connect() Detect if a class is wrapped with connect() in the export statement and add the 'localize' wrapper at the right place: export default connect( ... )( localize( TheComponent ) ); --- bin/codemods/i18n-mixin-to-localize.js | 56 +++++++++++++++++++++----- 1 file changed, 45 insertions(+), 11 deletions(-) diff --git a/bin/codemods/i18n-mixin-to-localize.js b/bin/codemods/i18n-mixin-to-localize.js index f4fb1c18572f1..a1d28b0598223 100644 --- a/bin/codemods/i18n-mixin-to-localize.js +++ b/bin/codemods/i18n-mixin-to-localize.js @@ -15,11 +15,38 @@ export default function transformer(file, api) { return j(createClassInstance); } + // AST matcher for the class identifier const classIdentifier = { type: 'Identifier', name: parentNode.id.name, }; + // AST matcher for the connected class identifier + const connectedClassIdentifier = { + type: 'CallExpression', + callee: { + type: 'CallExpression', + callee: { + type: 'Identifier', + name: 'connect', + } + }, + arguments: [ classIdentifier ] + }; + + // AST matcher for the module.exports expression + const moduleExportsExpression = { + type: 'MemberExpression', + object: { + type: 'Identifier', + name: 'module' + }, + property: { + type: 'Identifier', + name: 'exports', + } + }; + // Is the variable later exported with 'export default'? const exportDefaultDeclarations = root.find(j.ExportDefaultDeclaration, { declaration: classIdentifier @@ -28,25 +55,32 @@ export default function transformer(file, api) { return exportDefaultDeclarations.map(d => d.get('declaration')); } + // Is the variable later exported with 'export default connect()'? + const exportDefaultConnectDeclarations = root.find(j.ExportDefaultDeclaration, { + declaration: connectedClassIdentifier + }); + if (exportDefaultConnectDeclarations.size()) { + return exportDefaultConnectDeclarations.map(d => d.get('declaration').get('arguments', 0)); + } + // Is the variable later exported with 'module.exports ='? const moduleExportsDeclarations = root.find(j.AssignmentExpression, { - left: { - type: 'MemberExpression', - object: { - type: 'Identifier', - name: 'module' - }, - property: { - type: 'Identifier', - name: 'exports', - } - }, + left: moduleExportsExpression, right: classIdentifier }); if (moduleExportsDeclarations.size()) { return moduleExportsDeclarations.map(d => d.get('right')); } + // Is the variable later exported with 'module.exports = connect()'? + const moduleExportsConnectDeclarations = root.find(j.AssignmentExpression, { + left: moduleExportsExpression, + right: connectedClassIdentifier + }); + if (moduleExportsConnectDeclarations.size()) { + return moduleExportsConnectDeclarations.map(d => d.get('right').get('arguments', 0)); + } + return j(createClassInstance); }