From bdb5e4642f0271e0238ddbf79f70e1fcbe21df31 Mon Sep 17 00:00:00 2001 From: John-David Dalton Date: Mon, 19 Oct 2015 21:21:21 -0700 Subject: [PATCH] Add fp files. --- lodash.core.js => dist/lodash.core.js | 0 lodash.core.min.js => dist/lodash.core.min.js | 0 dist/lodash.fp.js | 425 ++++++++++++++++++ dist/lodash.fp.min.js | 9 + lodash.min.js => dist/lodash.min.js | 0 lib/fp/base.js | 208 +++++++++ lib/fp/bower.js | 13 + lib/fp/build.js | 63 +++ lib/fp/fp.js | 23 + lib/fp/mapping.js | 130 ++++++ lib/fp/node.js | 16 + lib/fp/util.js | 9 + lib/main/build.js | 1 + package.json | 5 +- 14 files changed, 901 insertions(+), 1 deletion(-) rename lodash.core.js => dist/lodash.core.js (100%) rename lodash.core.min.js => dist/lodash.core.min.js (100%) create mode 100644 dist/lodash.fp.js create mode 100644 dist/lodash.fp.min.js rename lodash.min.js => dist/lodash.min.js (100%) create mode 100644 lib/fp/base.js create mode 100644 lib/fp/bower.js create mode 100644 lib/fp/build.js create mode 100644 lib/fp/fp.js create mode 100644 lib/fp/mapping.js create mode 100644 lib/fp/node.js create mode 100644 lib/fp/util.js create mode 100644 lib/main/build.js diff --git a/lodash.core.js b/dist/lodash.core.js similarity index 100% rename from lodash.core.js rename to dist/lodash.core.js diff --git a/lodash.core.min.js b/dist/lodash.core.min.js similarity index 100% rename from lodash.core.min.js rename to dist/lodash.core.min.js diff --git a/dist/lodash.fp.js b/dist/lodash.fp.js new file mode 100644 index 000000000..2faa7fc50 --- /dev/null +++ b/dist/lodash.fp.js @@ -0,0 +1,425 @@ +(function webpackUniversalModuleDefinition(root, factory) { + if(typeof exports === 'object' && typeof module === 'object') + module.exports = factory(); + else if(typeof define === 'function' && define.amd) + define([], factory); + else if(typeof exports === 'object') + exports["fp"] = factory(); + else + root["fp"] = factory(); +})(this, function() { +return /******/ (function(modules) { // webpackBootstrap +/******/ // The module cache +/******/ var installedModules = {}; + +/******/ // The require function +/******/ function __webpack_require__(moduleId) { + +/******/ // Check if module is in cache +/******/ if(installedModules[moduleId]) +/******/ return installedModules[moduleId].exports; + +/******/ // Create a new module (and put it into the cache) +/******/ var module = installedModules[moduleId] = { +/******/ exports: {}, +/******/ id: moduleId, +/******/ loaded: false +/******/ }; + +/******/ // Execute the module function +/******/ modules[moduleId].call(module.exports, module, module.exports, __webpack_require__); + +/******/ // Flag the module as loaded +/******/ module.loaded = true; + +/******/ // Return the exports of the module +/******/ return module.exports; +/******/ } + + +/******/ // expose the modules object (__webpack_modules__) +/******/ __webpack_require__.m = modules; + +/******/ // expose the module cache +/******/ __webpack_require__.c = installedModules; + +/******/ // __webpack_public_path__ +/******/ __webpack_require__.p = ""; + +/******/ // Load entry module and return exports +/******/ return __webpack_require__(0); +/******/ }) +/************************************************************************/ +/******/ ([ +/* 0 */ +/***/ function(module, exports, __webpack_require__) { + + var baseConvert = __webpack_require__(1); + + /** + * Converts `lodash` to an auto-curried iteratee-first data-last version. + * + * @param {Function} lodash The lodash function. + * @returns {Function} Returns the converted lodash function. + */ + function bowerConvert(lodash) { + return baseConvert(lodash, lodash); + } + + module.exports = bowerConvert; + + +/***/ }, +/* 1 */ +/***/ function(module, exports, __webpack_require__) { + + var mapping = __webpack_require__(2), + mutateMap = mapping.mutateMap; + + /** + * The base implementation of `convert` which accepts a `util` object of methods + * required to perform conversions. + * + * @param {Object} util The util object. + * @param {string} name The name of the function to wrap. + * @param {Function} func The function to wrap. + * @returns {Function|Object} Returns the converted function or object. + */ + function baseConvert(util, name, func) { + if (!func) { + func = name; + name = null; + } + if (func == null) { + throw new TypeError; + } + var isLib = name == null && typeof func.VERSION == 'string'; + + var _ = isLib ? func : { + 'ary': util.ary, + 'curry': util.curry, + 'forEach': util.forEach, + 'isFunction': util.isFunction, + 'iteratee': util.iteratee, + 'keys': util.keys, + 'rearg': util.rearg + }; + + var ary = _.ary, + curry = _.curry, + each = _.forEach, + isFunction = _.isFunction, + keys = _.keys, + rearg = _.rearg; + + var baseAry = function(func, n) { + return function() { + var args = arguments, + length = Math.min(args.length, n); + + switch (length) { + case 1: return func(args[0]); + case 2: return func(args[0], args[1]); + } + args = Array(length); + while (length--) { + args[length] = arguments[length]; + } + return func.apply(undefined, args); + }; + }; + + var immutArrayWrap = function(func) { + return function() { + var index = -1, + length = arguments.length, + args = Array(length); + + while (length--) { + args[length] = arguments[length]; + } + var array = args[0]; + length = array ? array.length : 0; + + args[0] = Array(length); + while (++index < length) { + args[0][index] = array[index]; + } + func.apply(undefined, args); + return args[0]; + }; + }; + + var immutObjectWrap = function(func) { + return function() { + var index = -1, + length = arguments.length, + args = Array(length); + + while (++index < length) { + args[index] = arguments[index]; + } + args[0] = func({}, args[0]); + func.apply(undefined, args); + return args[0]; + }; + }; + + var iterateeAry = function(func, n) { + return function() { + var length = arguments.length, + args = Array(length); + + while (length--) { + args[length] = arguments[length]; + } + args[0] = baseAry(args[0], n); + return func.apply(undefined, args); + }; + }; + + var wrappers = { + 'iteratee': function(iteratee) { + return function(func, arity) { + arity = arity > 2 ? (arity - 2) : 1; + func = iteratee(func); + var length = func.length; + return length <= arity ? func : baseAry(func, arity); + }; + }, + 'mixin': function(mixin) { + return function(source) { + var func = this; + if (!isFunction(func)) { + return mixin(func, Object(source)); + } + var methods = [], + methodNames = []; + + each(keys(source), function(key) { + var value = source[key]; + if (isFunction(value)) { + methodNames.push(key); + methods.push(func.prototype[key]); + } + }); + + mixin(func, Object(source)); + + each(methodNames, function(methodName, index) { + var method = methods[index]; + if (isFunction(method)) { + func.prototype[methodName] = method; + } else { + delete func.prototype[methodName]; + } + }); + return func; + }; + }, + 'runInContext': function(runInContext) { + return function(context) { + return baseConvert(util, runInContext(context)); + }; + } + }; + + var wrap = function(name, func) { + var wrapper = wrappers[name]; + if (wrapper) { + return wrapper(func); + } + if (mutateMap.array[name]) { + func = immutArrayWrap(func); + } + else if (mutateMap.object[name]) { + func = immutObjectWrap(func); + } + var result; + each(mapping.caps, function(cap) { + each(mapping.aryMethodMap[cap], function(otherName) { + if (name == otherName) { + result = ary(func, cap); + if (cap > 1 && !mapping.skipReargMap[name]) { + result = rearg(result, mapping.methodReargMap[name] || mapping.aryReargMap[cap]); + } + var n = !isLib && mapping.aryIterateeMap[name]; + if (n) { + result = iterateeAry(result, n); + } + if (cap > 1) { + result = curry(result, cap); + } + return false; + } + }); + return !result; + }); + return result || func; + }; + + if (!isLib) { + return wrap(name, func); + } + // Iterate over methods for the current ary cap. + var pairs = []; + each(mapping.caps, function(cap) { + each(mapping.aryMethodMap[cap], function(name) { + var func = _[mapping.keyMap[name] || name]; + if (func) { + // Wrap the lodash method and its aliases. + var wrapped = wrap(name, func); + pairs.push([name, wrapped]); + each(mapping.aliasMap[name] || [], function(alias) { pairs.push([alias, wrapped]); }); + } + }); + }); + + // Assign to `_` leaving `_.prototype` unchanged to allow chaining. + each(pairs, function(pair) { _[pair[0]] = pair[1]; }); + return _; + } + + module.exports = baseConvert; + + +/***/ }, +/* 2 */ +/***/ function(module, exports) { + + module.exports = { + + /** Used to map method names to their aliases. */ + 'aliasMap': { + 'forEach': ['each'], + 'forEachRight': ['eachRight'], + 'first': ['head'] + }, + + /** Used to map method names to their iteratee ary. */ + 'aryIterateeMap': { + 'assignWith': 2, + 'cloneDeepWith': 1, + 'cloneWith': 1, + 'dropRightWhile': 1, + 'dropWhile': 1, + 'every': 1, + 'extendWith': 2, + 'filter': 1, + 'find': 1, + 'findIndex': 1, + 'findKey': 1, + 'findLast': 1, + 'findLastIndex': 1, + 'findLastKey': 1, + 'forEach': 1, + 'forEachRight': 1, + 'forIn': 1, + 'forInRight': 1, + 'forOwn': 1, + 'forOwnRight': 1, + 'isEqualWith': 2, + 'isMatchWith': 2, + 'map': 1, + 'mapKeys': 1, + 'mapValues': 1, + 'partition': 1, + 'reduce': 2, + 'reduceRight': 2, + 'reject': 1, + 'remove': 1, + 'some': 1, + 'takeRightWhile': 1, + 'takeWhile': 1, + 'times': 1, + 'transform': 2 + }, + + /** Used to map ary to method names. */ + 'aryMethodMap': { + 1: ( + 'attempt,ceil,create,curry,floor,iteratee,invert,memoize,method,methodOf,' + + 'mixin,restParam,reverse,round,runInContext,template,trim,trimLeft,trimRight,' + + 'words,zipObject').split(','), + 2: ( + 'ary,assign,at,bind,bindKey,cloneDeepWith,cloneWith,countBy,curryN,debounce,' + + 'defaults,defaultsDeep,delay,difference,drop,dropRight,dropRightWhile,' + + 'dropWhile,endsWith,every,extend,filter,find,find,findIndex,findKey,findLast,' + + 'findLastIndex,findLastKey,forEach,forEachRight,forIn,forInRight,forOwn,' + + 'forOwnRight,get,groupBy,includes,indexBy,indexOf,intersection,invoke,' + + 'isMatch,lastIndexOf,map,mapKeys,mapValues,maxBy,minBy,merge,omit,pad,padLeft,' + + 'padRight,parseInt,partition,pick,pull,pullAll,pullAt,random,range,rearg,reject,' + + 'remove,repeat,result,sampleSize,set,some,sortBy,sortByOrder,sortedIndexBy,' + + 'sortedLastIndexBy,sortedUniqBy,startsWith,sumBy,take,takeRight,takeRightWhile,' + + 'takeWhile,throttle,times,trunc,union,uniqBy,uniqueId,without,wrap,xor,zip').split(','), + 3: ( + 'assignWith,differenceBy,extendWith,inRange,intersectionBy,isEqualWith,' + + 'isMatchWith,mergeWith,omitBy,pickBy,pullAllBy,reduce,reduceRight,slice,' + + 'transform,unionBy,xorBy,zipWith').split(','), + 4: + ['fill'] + }, + + /** Used to map ary to rearg configs by method ary. */ + 'aryReargMap': { + 2: [1, 0], + 3: [2, 1, 0], + 4: [3, 2, 0, 1] + }, + + /** Used to map ary to rearg configs by method names. */ + 'methodReargMap': { + 'reduce': [2, 0, 1], + 'reduceRight': [2, 0, 1], + 'slice': [2, 0, 1], + 'transform': [2, 0, 1] + }, + + /** Used to iterate `mapping.aryMethodMap` keys. */ + 'caps': ['1', '2', '3', '4'], + + /** Used to map keys to other keys. */ + 'keyMap': { + 'curryN': 'curry', + 'curryRightN': 'curryRight', + 'debounceOpt': 'debounce', + 'throttleOpt': 'throttle' + }, + + /** Used to identify methods which mutate arrays or objects. */ + 'mutateMap': { + 'array': { + 'fill': true, + 'pull': true, + 'pullAll': true, + 'pullAllBy': true, + 'pullAt': true, + 'remove': true, + 'reverse': true + }, + 'object': { + 'assign': true, + 'assignWith': true, + 'defaults': true, + 'defaultsDeep': true, + 'extend': true, + 'extendWith': true, + 'merge': true, + 'mergeWith': true + } + }, + + /** Used to track methods that skip `_.rearg`. */ + 'skipReargMap': { + 'difference': true, + 'random': true, + 'range': true, + 'zipObject': true + } + }; + + +/***/ } +/******/ ]) +}); +; \ No newline at end of file diff --git a/dist/lodash.fp.min.js b/dist/lodash.fp.min.js new file mode 100644 index 000000000..ab94cfbde --- /dev/null +++ b/dist/lodash.fp.min.js @@ -0,0 +1,9 @@ +!function(e,t){"object"===typeof exports&&"object"===typeof module?module.exports=t():"function"===typeof define&&define.amd?define([],t):"object"===typeof exports?exports.fp=t():e.fp=t()}(this,function(){return function(e){function t(n){if(r[n])return r[n].exports;var i=r[n]={exports:{},id:n,loaded:!1};return e[n].call(i.exports,i,i.exports,t),i.loaded=!0,i.exports}var r={};return t.m=e,t.c=r,t.p="",t(0)}([function(e,t,r){function n(e){return i(e,e)}var i=r(1);e.exports=n},function(e,t,r){function n(e,t,r){ +if(r||(r=t,t=null),null==r)throw new TypeError;var o=null==t&&"string"==typeof r.VERSION,u=o?r:{ary:e.ary,curry:e.curry,forEach:e.forEach,isFunction:e.isFunction,iteratee:e.iteratee,keys:e.keys,rearg:e.rearg},f=u.ary,p=u.curry,s=u.forEach,c=u.isFunction,l=u.keys,d=u.rearg,h=function(e,t){return function(){var r=arguments,n=Math.min(r.length,t);switch(n){case 1:return e(r[0]);case 2:return e(r[0],r[1])}for(r=Array(n);n--;)r[n]=arguments[n];return e.apply(void 0,r)}},y=function(e){return function(){ +for(var t=-1,r=arguments.length,n=Array(r);r--;)n[r]=arguments[r];var i=n[0];for(r=i?i.length:0,n[0]=Array(r);++t2?r-2:1, +t=e(t);var n=t.length;return n>r?h(t,r):t}},mixin:function(e){return function(t){var r=this;if(!c(r))return e(r,Object(t));var n=[],i=[];return s(l(t),function(e){var a=t[e];c(a)&&(i.push(e),n.push(r.prototype[e]))}),e(r,Object(t)),s(i,function(e,t){var i=n[t];c(i)?r.prototype[e]=i:delete r.prototype[e]}),r}},runInContext:function(t){return function(r){return n(e,t(r))}}},x=function(e,t){var r=v[e];if(r)return r(t);a.array[e]?t=y(t):a.object[e]&&(t=g(t));var n;return s(i.caps,function(r){return s(i.aryMethodMap[r],function(a){ +if(e==a){n=f(t,r),r>1&&!i.skipReargMap[e]&&(n=d(n,i.methodReargMap[e]||i.aryReargMap[r]));var u=!o&&i.aryIterateeMap[e];return u&&(n=m(n,u)),r>1&&(n=p(n,r)),!1}}),!n}),n||t};if(!o)return x(t,r);var R=[];return s(i.caps,function(e){s(i.aryMethodMap[e],function(e){var t=u[i.keyMap[e]||e];if(t){var r=x(e,t);R.push([e,r]),s(i.aliasMap[e]||[],function(e){R.push([e,r])})}})}),s(R,function(e){u[e[0]]=e[1]}),u}var i=r(2),a=i.mutateMap;e.exports=n},function(e,t){e.exports={aliasMap:{forEach:["each"],forEachRight:["eachRight"], +first:["head"]},aryIterateeMap:{assignWith:2,cloneDeepWith:1,cloneWith:1,dropRightWhile:1,dropWhile:1,every:1,extendWith:2,filter:1,find:1,findIndex:1,findKey:1,findLast:1,findLastIndex:1,findLastKey:1,forEach:1,forEachRight:1,forIn:1,forInRight:1,forOwn:1,forOwnRight:1,isEqualWith:2,isMatchWith:2,map:1,mapKeys:1,mapValues:1,partition:1,reduce:2,reduceRight:2,reject:1,remove:1,some:1,takeRightWhile:1,takeWhile:1,times:1,transform:2},aryMethodMap:{1:"attempt,ceil,create,curry,floor,iteratee,invert,memoize,method,methodOf,mixin,restParam,reverse,round,runInContext,template,trim,trimLeft,trimRight,words,zipObject".split(","), +2:"ary,assign,at,bind,bindKey,cloneDeepWith,cloneWith,countBy,curryN,debounce,defaults,defaultsDeep,delay,difference,drop,dropRight,dropRightWhile,dropWhile,endsWith,every,extend,filter,find,find,findIndex,findKey,findLast,findLastIndex,findLastKey,forEach,forEachRight,forIn,forInRight,forOwn,forOwnRight,get,groupBy,includes,indexBy,indexOf,intersection,invoke,isMatch,lastIndexOf,map,mapKeys,mapValues,maxBy,minBy,merge,omit,pad,padLeft,padRight,parseInt,partition,pick,pull,pullAll,pullAt,random,range,rearg,reject,remove,repeat,result,sampleSize,set,some,sortBy,sortByOrder,sortedIndexBy,sortedLastIndexBy,sortedUniqBy,startsWith,sumBy,take,takeRight,takeRightWhile,takeWhile,throttle,times,trunc,union,uniqBy,uniqueId,without,wrap,xor,zip".split(","), +3:"assignWith,differenceBy,extendWith,inRange,intersectionBy,isEqualWith,isMatchWith,mergeWith,omitBy,pickBy,pullAllBy,reduce,reduceRight,slice,transform,unionBy,xorBy,zipWith".split(","),4:["fill"]},aryReargMap:{2:[1,0],3:[2,1,0],4:[3,2,0,1]},methodReargMap:{reduce:[2,0,1],reduceRight:[2,0,1],slice:[2,0,1],transform:[2,0,1]},caps:["1","2","3","4"],keyMap:{curryN:"curry",curryRightN:"curryRight",debounceOpt:"debounce",throttleOpt:"throttle"},mutateMap:{array:{fill:!0,pull:!0,pullAll:!0,pullAllBy:!0, +pullAt:!0,remove:!0,reverse:!0},object:{assign:!0,assignWith:!0,defaults:!0,defaultsDeep:!0,extend:!0,extendWith:!0,merge:!0,mergeWith:!0}},skipReargMap:{difference:!0,random:!0,range:!0,zipObject:!0}}}])}); \ No newline at end of file diff --git a/lodash.min.js b/dist/lodash.min.js similarity index 100% rename from lodash.min.js rename to dist/lodash.min.js diff --git a/lib/fp/base.js b/lib/fp/base.js new file mode 100644 index 000000000..889225088 --- /dev/null +++ b/lib/fp/base.js @@ -0,0 +1,208 @@ +var mapping = require('./mapping.js'), + mutateMap = mapping.mutateMap; + +/** + * The base implementation of `convert` which accepts a `util` object of methods + * required to perform conversions. + * + * @param {Object} util The util object. + * @param {string} name The name of the function to wrap. + * @param {Function} func The function to wrap. + * @returns {Function|Object} Returns the converted function or object. + */ +function baseConvert(util, name, func) { + if (!func) { + func = name; + name = null; + } + if (func == null) { + throw new TypeError; + } + var isLib = name == null && typeof func.VERSION == 'string'; + + var _ = isLib ? func : { + 'ary': util.ary, + 'curry': util.curry, + 'forEach': util.forEach, + 'isFunction': util.isFunction, + 'iteratee': util.iteratee, + 'keys': util.keys, + 'rearg': util.rearg + }; + + var ary = _.ary, + curry = _.curry, + each = _.forEach, + isFunction = _.isFunction, + keys = _.keys, + rearg = _.rearg; + + var baseAry = function(func, n) { + return function() { + var args = arguments, + length = Math.min(args.length, n); + + switch (length) { + case 1: return func(args[0]); + case 2: return func(args[0], args[1]); + } + args = Array(length); + while (length--) { + args[length] = arguments[length]; + } + return func.apply(undefined, args); + }; + }; + + var immutArrayWrap = function(func) { + return function() { + var index = -1, + length = arguments.length, + args = Array(length); + + while (length--) { + args[length] = arguments[length]; + } + var array = args[0]; + length = array ? array.length : 0; + + args[0] = Array(length); + while (++index < length) { + args[0][index] = array[index]; + } + func.apply(undefined, args); + return args[0]; + }; + }; + + var immutObjectWrap = function(func) { + return function() { + var index = -1, + length = arguments.length, + args = Array(length); + + while (++index < length) { + args[index] = arguments[index]; + } + args[0] = func({}, args[0]); + func.apply(undefined, args); + return args[0]; + }; + }; + + var iterateeAry = function(func, n) { + return function() { + var length = arguments.length, + args = Array(length); + + while (length--) { + args[length] = arguments[length]; + } + args[0] = baseAry(args[0], n); + return func.apply(undefined, args); + }; + }; + + var wrappers = { + 'iteratee': function(iteratee) { + return function(func, arity) { + arity = arity > 2 ? (arity - 2) : 1; + func = iteratee(func); + var length = func.length; + return length <= arity ? func : baseAry(func, arity); + }; + }, + 'mixin': function(mixin) { + return function(source) { + var func = this; + if (!isFunction(func)) { + return mixin(func, Object(source)); + } + var methods = [], + methodNames = []; + + each(keys(source), function(key) { + var value = source[key]; + if (isFunction(value)) { + methodNames.push(key); + methods.push(func.prototype[key]); + } + }); + + mixin(func, Object(source)); + + each(methodNames, function(methodName, index) { + var method = methods[index]; + if (isFunction(method)) { + func.prototype[methodName] = method; + } else { + delete func.prototype[methodName]; + } + }); + return func; + }; + }, + 'runInContext': function(runInContext) { + return function(context) { + return baseConvert(util, runInContext(context)); + }; + } + }; + + var wrap = function(name, func) { + var wrapper = wrappers[name]; + if (wrapper) { + return wrapper(func); + } + if (mutateMap.array[name]) { + func = immutArrayWrap(func); + } + else if (mutateMap.object[name]) { + func = immutObjectWrap(func); + } + var result; + each(mapping.caps, function(cap) { + each(mapping.aryMethodMap[cap], function(otherName) { + if (name == otherName) { + result = ary(func, cap); + if (cap > 1 && !mapping.skipReargMap[name]) { + result = rearg(result, mapping.methodReargMap[name] || mapping.aryReargMap[cap]); + } + var n = !isLib && mapping.aryIterateeMap[name]; + if (n) { + result = iterateeAry(result, n); + } + if (cap > 1) { + result = curry(result, cap); + } + return false; + } + }); + return !result; + }); + return result || func; + }; + + if (!isLib) { + return wrap(name, func); + } + // Iterate over methods for the current ary cap. + var pairs = []; + each(mapping.caps, function(cap) { + each(mapping.aryMethodMap[cap], function(name) { + var func = _[mapping.keyMap[name] || name]; + if (func) { + // Wrap the lodash method and its aliases. + var wrapped = wrap(name, func); + pairs.push([name, wrapped]); + each(mapping.aliasMap[name] || [], function(alias) { pairs.push([alias, wrapped]); }); + } + }); + }); + + // Assign to `_` leaving `_.prototype` unchanged to allow chaining. + each(pairs, function(pair) { _[pair[0]] = pair[1]; }); + return _; +} + +module.exports = baseConvert; diff --git a/lib/fp/bower.js b/lib/fp/bower.js new file mode 100644 index 000000000..22a8255b8 --- /dev/null +++ b/lib/fp/bower.js @@ -0,0 +1,13 @@ +var baseConvert = require('./base.js'); + +/** + * Converts `lodash` to an auto-curried iteratee-first data-last version. + * + * @param {Function} lodash The lodash function. + * @returns {Function} Returns the converted lodash function. + */ +function bowerConvert(lodash) { + return baseConvert(lodash, lodash); +} + +module.exports = bowerConvert; diff --git a/lib/fp/build.js b/lib/fp/build.js new file mode 100644 index 000000000..4cc217a61 --- /dev/null +++ b/lib/fp/build.js @@ -0,0 +1,63 @@ +'use strict'; + +var _ = require('lodash'), + async = require('async'), + fs = require('fs'), + path = require('path'), + uglify = require('uglify-js'), + webpack = require('webpack'); + +var entryPath = path.join(__dirname, 'bower.js'), + outputPath = path.join(__dirname, '..', '..', 'dist'), + filename = 'lodash.fp.js'; + +var webpackConfig = { + 'entry': entryPath, + 'output': { + 'path': outputPath, + 'filename': filename, + 'library': 'fp', + 'libraryTarget': 'umd' + }, + 'plugins': [ + new webpack.optimize.OccurenceOrderPlugin, + new webpack.optimize.DedupePlugin + ] +} + +var uglifyConfig = { + 'mangle': true, + 'compress': { + 'comparisons': false, + 'keep_fargs': true, + 'pure_getters': true, + 'unsafe': true, + 'unsafe_comps': true, + 'warnings': false + }, + 'output': { + 'ascii_only': true, + 'beautify': false, + 'max_line_len': 500 + } +} + +/*----------------------------------------------------------------------------*/ + +function minify(inputPath, callback) { + var output = uglify.minify(inputPath, uglifyConfig), + outputPath = inputPath.replace(/(?=\.js$)/, '.min'); + + fs.writeFile(outputPath, output.code, 'utf-8', callback); +} + +function onComplete(error) { + if (error) { + throw error; + } +} + +async.series([ + _.partial(webpack, webpackConfig), + _.partial(minify, path.join(outputPath, filename)) +], onComplete); diff --git a/lib/fp/fp.js b/lib/fp/fp.js new file mode 100644 index 000000000..e62e802f8 --- /dev/null +++ b/lib/fp/fp.js @@ -0,0 +1,23 @@ +var baseConvert = require('./base.js'), + util = require('./util.js'), + lodash = require('lodash'); + +/** + * Converts `func` of `name` to an auto-curried iteratee-first data-last version. + * If `name` is an object, the methods on it will be converted and the object returned. + * + * @param {string} name The name of the function to wrap. + * @param {Function} func The function to wrap. + * @returns {Function|Object} Returns the converted function or object. + */ +function convert(name, func) { + if (!func) { + func = name; + name = null; + } + return name == null + ? baseConvert(util, _.runInContext()) + : baseConvert(util, name, func); +} + +module.exports = convert; diff --git a/lib/fp/mapping.js b/lib/fp/mapping.js new file mode 100644 index 000000000..b9861e8ef --- /dev/null +++ b/lib/fp/mapping.js @@ -0,0 +1,130 @@ +module.exports = { + + /** Used to map method names to their aliases. */ + 'aliasMap': { + 'forEach': ['each'], + 'forEachRight': ['eachRight'], + 'first': ['head'] + }, + + /** Used to map method names to their iteratee ary. */ + 'aryIterateeMap': { + 'assignWith': 2, + 'cloneDeepWith': 1, + 'cloneWith': 1, + 'dropRightWhile': 1, + 'dropWhile': 1, + 'every': 1, + 'extendWith': 2, + 'filter': 1, + 'find': 1, + 'findIndex': 1, + 'findKey': 1, + 'findLast': 1, + 'findLastIndex': 1, + 'findLastKey': 1, + 'forEach': 1, + 'forEachRight': 1, + 'forIn': 1, + 'forInRight': 1, + 'forOwn': 1, + 'forOwnRight': 1, + 'isEqualWith': 2, + 'isMatchWith': 2, + 'map': 1, + 'mapKeys': 1, + 'mapValues': 1, + 'partition': 1, + 'reduce': 2, + 'reduceRight': 2, + 'reject': 1, + 'remove': 1, + 'some': 1, + 'takeRightWhile': 1, + 'takeWhile': 1, + 'times': 1, + 'transform': 2 + }, + + /** Used to map ary to method names. */ + 'aryMethodMap': { + 1: ( + 'attempt,ceil,create,curry,floor,iteratee,invert,memoize,method,methodOf,' + + 'mixin,restParam,reverse,round,runInContext,template,trim,trimLeft,trimRight,' + + 'words,zipObject').split(','), + 2: ( + 'ary,assign,at,bind,bindKey,cloneDeepWith,cloneWith,countBy,curryN,debounce,' + + 'defaults,defaultsDeep,delay,difference,drop,dropRight,dropRightWhile,' + + 'dropWhile,endsWith,every,extend,filter,find,find,findIndex,findKey,findLast,' + + 'findLastIndex,findLastKey,forEach,forEachRight,forIn,forInRight,forOwn,' + + 'forOwnRight,get,groupBy,includes,indexBy,indexOf,intersection,invoke,' + + 'isMatch,lastIndexOf,map,mapKeys,mapValues,maxBy,minBy,merge,omit,pad,padLeft,' + + 'padRight,parseInt,partition,pick,pull,pullAll,pullAt,random,range,rearg,reject,' + + 'remove,repeat,result,sampleSize,set,some,sortBy,sortByOrder,sortedIndexBy,' + + 'sortedLastIndexBy,sortedUniqBy,startsWith,sumBy,take,takeRight,takeRightWhile,' + + 'takeWhile,throttle,times,trunc,union,uniqBy,uniqueId,without,wrap,xor,zip').split(','), + 3: ( + 'assignWith,differenceBy,extendWith,inRange,intersectionBy,isEqualWith,' + + 'isMatchWith,mergeWith,omitBy,pickBy,pullAllBy,reduce,reduceRight,slice,' + + 'transform,unionBy,xorBy,zipWith').split(','), + 4: + ['fill'] + }, + + /** Used to map ary to rearg configs by method ary. */ + 'aryReargMap': { + 2: [1, 0], + 3: [2, 1, 0], + 4: [3, 2, 0, 1] + }, + + /** Used to map ary to rearg configs by method names. */ + 'methodReargMap': { + 'reduce': [2, 0, 1], + 'reduceRight': [2, 0, 1], + 'slice': [2, 0, 1], + 'transform': [2, 0, 1] + }, + + /** Used to iterate `mapping.aryMethodMap` keys. */ + 'caps': ['1', '2', '3', '4'], + + /** Used to map keys to other keys. */ + 'keyMap': { + 'curryN': 'curry', + 'curryRightN': 'curryRight', + 'debounceOpt': 'debounce', + 'throttleOpt': 'throttle' + }, + + /** Used to identify methods which mutate arrays or objects. */ + 'mutateMap': { + 'array': { + 'fill': true, + 'pull': true, + 'pullAll': true, + 'pullAllBy': true, + 'pullAt': true, + 'remove': true, + 'reverse': true + }, + 'object': { + 'assign': true, + 'assignWith': true, + 'defaults': true, + 'defaultsDeep': true, + 'extend': true, + 'extendWith': true, + 'merge': true, + 'mergeWith': true + } + }, + + /** Used to track methods that skip `_.rearg`. */ + 'skipReargMap': { + 'difference': true, + 'random': true, + 'range': true, + 'zipObject': true + } +}; diff --git a/lib/fp/node.js b/lib/fp/node.js new file mode 100644 index 000000000..943844f3f --- /dev/null +++ b/lib/fp/node.js @@ -0,0 +1,16 @@ +var baseConvert = require('./base.js'), + util = require('./util.js'); + +/** + * Converts `func` of `name` to an auto-curried iteratee-first data-last version. + * If `name` is an object, the methods on it will be converted and the object returned. + * + * @param {string} name The name of the function to wrap. + * @param {Function} func The function to wrap. + * @returns {Function|Object} Returns the converted function or object. + */ +function convert(name, func) { + return baseConvert(util, name, func); +} + +module.exports = convert; diff --git a/lib/fp/util.js b/lib/fp/util.js new file mode 100644 index 000000000..341b9de33 --- /dev/null +++ b/lib/fp/util.js @@ -0,0 +1,9 @@ +module.exports = { + 'ary': require('lodash/function/ary'), + 'curry': require('lodash/function/curry'), + 'forEach': require('lodash/internal/arrayEach'), + 'isFunction': require('lodash/lang/isFunction'), + 'iteratee': require('lodash/utility/iteratee'), + 'keys': require('lodash/internal/baseKeys'), + 'rearg': require('lodash/function/rearg') +}; diff --git a/lib/main/build.js b/lib/main/build.js new file mode 100644 index 000000000..ad9a93a7c --- /dev/null +++ b/lib/main/build.js @@ -0,0 +1 @@ +'use strict'; diff --git a/package.json b/package.json index 7945b80ac..82e4a11c8 100644 --- a/package.json +++ b/package.json @@ -4,6 +4,7 @@ "main": "lodash.js", "private": true, "devDependencies": { + "async": "^1.4.2", "chalk": "^1.1.1", "coveralls": "^2.11.4", "curl-amd": "0.8.12", @@ -19,7 +20,9 @@ "qunitjs": "~1.19.0", "request": "^2.65.0", "requirejs": "~2.1.20", - "sauce-tunnel": "2.2.3" + "sauce-tunnel": "2.2.3", + "uglify-js": "2.5.0", + "webpack": "^1.12.2" }, "scripts": { "style": "jscs lodash.js",