Git Product home page Git Product logo

underscore-contrib's Introduction

This is the repository for the legacy DocumentCloud site, please see the current repository here:

https://github.com/muckrock/documentcloud

______                                      _   _____ _                 _
|  _  \                                    | | /  __ \ |               | |
| | | |___   ___ _   _ _ __ ___   ___ _ __ | |_| /  \/ | ___  _   _  __| |
| | | / _ \ / __| | | | '_ ` _ \ / _ \ '_ \| __| |   | |/ _ \| | | |/ _` |
| |/ / (_) | (__| |_| | | | | | |  __/ | | | |_| \__/\ | (_) | |_| | (_| |
|___/ \___/ \___|\__,_|_| |_| |_|\___|_| |_|\__|\____/_|\___/ \__,_|\__,_|

DocumentCloud is a catalog of primary source documents and a tool for annotating, organizing and publishing them on the web. Documents are contributed by journalists, researchers and archivists.

This codebase contains the entirety of DocumentCloud.org, and pulls together the rest of our open-source projects: Docsplit is used to extract data from incoming documents; that work is parallelized across CloudCrowd; data on the client-side is modeled by Backbone.js, which depends on Underscore.js for all of its abilities; Jammit concatenates and compresses the dozens of CSS and JS files into a single asset package; the NYTimes' Document Viewer displays the documents, while Pixel Ping records the traffic.

If you find a security issue while browsing the source, please email [email protected] to inform us of the problem.

Code contributed to this project is provided under the MIT license (see the LICENSE file). Some components of the project are subject to their own licenses as indicated (see /vendor and /public/javascripts/vendor directories).

underscore-contrib's People

Contributors

alphagit avatar bruun avatar darrenn avatar dbwhddn10 avatar dependabot[bot] avatar eborden avatar fogus avatar gsamokovarov avatar gyeates avatar jgonggrijp avatar jonahbron avatar joshuacc avatar knowtheory avatar krawaller avatar locks avatar megawac avatar mieszko4 avatar netsydemiro avatar pdubroy avatar pwlmaciejewski avatar raganwald avatar seidtgeist avatar serabe avatar sroccaserra avatar streetstrider avatar tgriesser avatar tomrogers42 avatar tracend avatar tricknotes avatar zimme avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

underscore-contrib's Issues

Pass property key as iterator to _.uniq

Allow uniq to follow sortBy, groupBy etc’s API in allowing iteration by string as well as function.

var colours = [
    {
        name: 'Crimson',
        value: '#DC143C'
    },
    {
        name: 'Floral White',
        value: '#FFFAF0'
    },
    {
        name: 'Red',
        value: '#DC143C'
    },
    {
        name: 'Teal',
        value: '#008080'
    }
];

colours = _.uniq( colours, 'value' );

Implemented in 1cc1528

Consider adding curry2, curry3, rcurry2 and rcurry3

For the common cases of currying we might benefit from having explicit functions for 2 and 3 parameter currying. The questions include:

  • Can they be faster than curry currently in place?
  • Should they allow var args on the final call?

What else should we consider?

Improved API to mapArgs?

I'm wondering if it would be better to have _.mapArgs not be curried. As of right now it is used like so:

squareAndDouble = _.mapArgs(doubleNum)(square);
squareAndDouble(3);
// => 18

However, I'd find the following more intuitive.

squareAndDouble = _.mapArgs(doubleNum, square);
squareAndDouble(3);
// => 18

This keeps the typical Underscore pattern of putting the "operand" value first, and the "operator" value second within one call. Is there a compelling reason to use the curried version @fogus ?

Library organization

The underscore.contrib library should be organized along separations of functionality as _.mixins. Underscore is organized in the following ways:

  • Collections
  • Arrays
  • Functions
  • Objects
  • Utils
  • Chaining

We could certainly organize the same way, but maybe something less coarse is in order:

  • Objects
  • Arrays
  • Sets
  • Combinators
  • Iterators
  • Utils
  • Strings
  • Monads
  • Predicates
  • Curry
  • Dispatch
  • Trampolines

Or maybe something more technical:

  • Higher-order functions
  • Applicative functions
  • Collection functions
  • Combinators
  • Curry
  • Multimethods

This is an invitation for ideas. I'm not married to either of these schemes and would like feedback if you have some ideas.

Documentation wrong for first and last

The documentation for .first and .last correctly indicates that it returns an array - but the example shows that it returns the value.

Minor, but confusing

deepGet (deepAccessor?)

I just wrote up an implementation of deepGet for a separate library and thought that it might fit in well with underscore-contrib's object selectors.

The goal is to avoid the typical hassle of dealing with TypeError: Cannot read property 'someprop' of undefined (and the similar error for null) when trying to access deeply nested properties. deepGet will transparently handle those cases for you.

In my implementation both null and undefined are treated as non-values.

Implementation: https://github.com/joshuacc/drabs/blob/master/src/drabs.js#L5

Usage:

var rels = {
    Viola: {
        Orsino: {
            Olivia: {
                Cesario: null
            }
        }
    }
};

// Getting a deep property that has a real value
deepGet(rels, ["Viola", "Orsino", "Olivia"]);
//=> { Cesario: null }

// Getting a non-existent property
deepGet(rels, ["Viola", "Harry", "Sally"]);
//=> undefined

// Getting a null property
deepGet(rels, ["Viola", "Orsino", "Olivia", "Cesario"]);
//=> undefined

// Getting a deep property via a string-based property list
deepGet(rels, "Viola.Orsino.Olivia");
//=> { Cesario: null }

// Returning a default value if the property was a non-value/non-existent
deepGet(rels, ["Viola", "Orsino", "Olivia", "Cesario"], "Hmmm.");
//=> "Hmmm."

It's not currently written in the same style as Underscore, but if there is interest, I can take a crack at adapting it.

Allow users of walk functions to customize the walking strategy

It would be nice if the functions in _.walk would allow callers to customize how the structure is walked, in the same way that DOM elements are handled specially. Walking a parse tree is one example where this would be really useful.

I am planning on implementing this, but I'd like some feedback on what the API should be like. I'm thinking of a few different options:

  • Add an iterStrategy argument to all the functions, which would then get passed to walk. E.g., you would do _.walk.pluck(obj, 'myProp', true, domWalker)
  • Allow the entire walk module to be parameterized like this: _.walk(domWalker).pluck(obj, 'myProp', true). However, this would mean changing the current meaning of invoking _.walk. Alternatively, something like _.walk.CustomWalk(domWalker).pluck, but that's getting pretty wordy.

Any thoughts?

Add character encoding to qUnit html files

FireFox is giving the following warning:

The character encoding of the HTML document was not declared. The document will render with garbled text in some browser configurations if the document contains characters from outside the US-ASCII range. The character encoding of the page must be declared in the document or in the transfer protocol.

Underscore considering a conflicting _.nth method

Just wanted to give ya a heads up @fogus that Underscore is considering an _.nth method that conflicts with underscore-contrib's (reverse arg signature). See PR #1252. It seems the reason the OP can't use underscore-contrib's is because yall check for in-bounds indexes or throw an error, instead of returning undefined.

The bounds check in the contrib implementation also stops you from being able to easily map tables w/ heterogenous rows (it throws an exception), maintaing the javascript behavior of returning undefined seems better (you can simply compact them out, or perform whatever action is necessary for a missing column in your data). It is also consistent w/ Lisp's behavior of returning NIL

Pipeline enhancement

I'd like it if the Pipeline could take both a number of parameters as well as an array of functions.
The change would be pretty simple:

    pipeline: function(/*, funs */){
      var funs = arguments;

      // Also handle an array of functions
      if(funs[0].length){
            funs = funs[0];
        }
      return function(seed) {
        return _.reduce(funs,
                        function(l,r) { return r(l); },
                        seed);
      };
    },

Problems installing 0.2.0 with npm

@fogus Reproduced this issue on two independent systems. It looks like there may have been trouble publishing the 0.2.0 .tgz file to the npm registry. Installing 0.1.4 worked just fine. Is it possible to republish?

Here's the error:

$ npm install underscore-contrib --save
npm http GET https://registry.npmjs.org/underscore-contrib
npm http 200 https://registry.npmjs.org/underscore-contrib
npm http GET https://registry.npmjs.org/underscore-contrib/-/underscore-contrib-0.2.0.tgz
npm http 404 https://registry.npmjs.org/underscore-contrib/-/underscore-contrib-0.2.0.tgz
npm ERR! fetch failed https://registry.npmjs.org/underscore-contrib/-/underscore-contrib-0.2.0.tgz
npm ERR! Error: 404 Not Found
npm ERR!     at WriteStream.<anonymous> (/usr/local/lib/node_modules/npm/lib/utils/fetch.js:47:16)
npm ERR!     at WriteStream.EventEmitter.emit (events.js:117:20)
npm ERR!     at fs.js:1596:14
npm ERR!     at /usr/local/lib/node_modules/npm/node_modules/graceful-fs/graceful-fs.js:90:5
npm ERR!     at Object.oncomplete (fs.js:107:15)
npm ERR! If you need help, you may report this log at:
npm ERR!     <http://github.com/isaacs/npm/issues>
npm ERR! or email it to:
npm ERR!     <[email protected]>

npm ERR! System Linux 2.6.32-279.2.1.el6.x86_64
npm ERR! command "/usr/local/bin/node" "/usr/local/bin/npm" "install" "underscore-contrib" "--save"
npm ERR! cwd /httpd/lhb/projectname
npm ERR! node -v v0.10.5
npm ERR! npm -v 1.1.65
npm ERR!
npm ERR! Additional logging details can be found in:
npm ERR!     /httpd/lhb/projectname/npm-debug.log
npm ERR! not ok code 0

Replace snapshot with a more robust deep clone

The snapshot function is a little simplistic right now. We should look into replacing it with something more robust. Basing it off of Lo-Dash's cloneDeep would probably be a good start.

Safer way of mixing in functions?

Currently, the way that contrib is built, all of a sub-library's functions are automatically mixed in to Underscore. This works if you are using only Underscore, but if you are either using Lo-Dash or additional plugins like underscore.string, we can end up clobbering existing functions.

Especially with Lo-Dash beginning to expand its suite of string utils, I'd like to see a safer way of mixing in contrib's functions. Underscore.string has a basic implementation of this where you can either mixin functions individually, or mixin everything.

The first thing that occurs to me is to add a _.safeMixin method that won't clobber stuff, and can potentially log which functions aren't being mixed in.

Of course, this might be something that should be fixed at the Underscore/Lo-Dash level instead.

Any thoughts on the best way to do this?

Port the functional iterators from allong.es into underscore-contrib

Names should be brought into line with underscore standards. e.g. what it calls .fold should be renamed reduce and aliased as foldl.

Currently, it is namespaced. So if we do this in underscore-contrib, the above function would become _.iterators.reduce. If that is not appropriate, we should consider a preface such as _.iteratorFoldl or suffix such as _.reduceIterator.

Behavior of _.isAssociative and string primitives?

The comments for _.isAssociative describe an associative object as one which has elements which can be accessed by a key/index. Except for the term "object", string primitives meet this definition. However, _.isAssociative("string") will currently return false.

So it seems like this should be changed in one of two ways:

  1. Change the name to isAssociativeObject or...
  2. Return true for strings.

I can create a pull request to resolve this, but I'm not sure which way is preferred.

How should we treat _.always now that Underscore has _.constant? Also, versioning.

Underscore recently added _.constant which is identical to contrib's _.always. Should we remove _.always, switch it to an alias (safer), or leave it as-is (safest)?

This also brings up the general question of versioning contrib. So far, we've treated contrib's versions as completely independent of Underscore's. But as Underscore adds features that originated in contrib, it will become difficult to develop against all past versions of Underscore.

I'm wondering if it might be a good idea to start versioning against a specific release of Underscore the way that lodash-contrib does. If we were to target the latest Underscore release (1.6.0), contrib's version would be 160.0.0.

Even if we don't decide to use contrib's version numbers that way, we should start at least specifying which version of Underscore we're expecting.

Any thoughts @fogus ?

Feature Suggestion: unsplat to handle multiple arities

Right now, _.unsplat emulates CoffeeScript's (args...) -> ..., meaning the function it decorates must expect one parameter, and all of the arguments are wrapped and passed to that one parameter.

An enhancement is to also respect forms such as (first, args...) -> ... which would look something like this:

function echo2 (first, rest) { return [first, rest]; }
function echo3 (first, second, rest) { return [first, second, rest]; }

unsplat(echo2)(1, 2, 3, 4, 5)
  //=> [1, [2, 3, 4, 5]]
unsplat(echo3)(1, 2, 3, 4, 5)
  //=> [1, 2, [3, 4, 5]]

pick/omit with a predicate

Suggesting smarter pick (like lodash's) and omit functions which accept a predicate instead of a list of keys. In other terms, a (negated) filter which acts on object property values:

_.pickwhen(_.truthy, {foo: true, bar: false});
// -> {foo: true}

_.omitwhen(_.isEmpty, {foo: [], bar: {}, baz: 'not empty'});
// -> {baz: 'not empty'}

var compacto = _.partial(_.omitwhen, _.falsy);
compacto({foo: false, bar: false});
// {}

Note: Reversed arguments in favor of partial application. This might of course clash with the argument order "style" of other _ and _.contrib functions. Suggestions welcome.

Where are the ucfirst/lcfirst string helper functions?

I expected to find the basics lcfirst and ucfirst string functions in the utilsString helper, but nothing. Are they somewhere else in underscore?

I don't use underscore yet, not really but I want to. And I also don't understand how extends underscore with underscore-contrib server side with node.js. Client side is easy, simply import the contrib script but there is no example about server side!

Thanks.

Add functions for solving "duck wrapping" problems

Looking at this...
http://brehaut.net/blog/2013/duck_wrapping

The article suggests that there be separate functions for auto-unboxing containers, and not auto-unboxing containers. There's a good point there, especially for functional programmers. It's not a frequent case, but I'm sure that sometimes, someone actually wants to end up with something that looks like [1, 2, [3]], without kludgery.

Should we include such functions? If so, let's spec them out, and write some code to handle them properly.

Bump version on npm

The last version of underscore-contrib on npm was v0.1.4, published 5 months ago.

Given the npm registry is back up and there's so much great new stuff in the library can we bump it to 0.2.0?

$ npm version minor
$ git push --tags && git push && npm publish

Create a package.json for publishing to npm

This might imply making the test suite jasmine-node compatible, as that would make it very easy to set up a publish script that verifies the test suite before publishing

AMD support?

Documentation / support for using this client-side with AMD would be helpful.

`_.defaults` for primitives?

Previously discussed in #33 and #34.

It would be quite nice some situations to be able to have a concise way of specifying a default value when a function may return undefined or null. My initial thought was to extend _.defaults to handle primitive values. But after looking at the source, I think it might unnecessarily complicate defaults.

So my next line of thought is that a more specialized method might be a better choice. Perhaps something like _.firstValue, where null and undefined are understood to be non-values.

The method would just return the first non-null/non-undefined argument, like so:

_.firstValue(undefined, "my string");
// => "my string"

_.firstValue(undefined, null, "my string");
// => "my string"

_.firstValue(undefined, "my string", null);
// => "my string"

Then it would be very easy to handle cases like _.getPath returning undefined/null.

var obj = { a: { b: "b" } };

_.firstValue(_.getPath(["a","b"]), "nothing found");
// => "b"

_.firstValue(_.getPath(["a","b", "c"]), "nothing found");
// => "nothing found"

Obviously, it's not too hard to use if (x != null) { }, but I think that _.firstValue is a bit nicer and makes it easier to just keep piping data through functions without explicitly writing conditionals.

Any thoughts on this proposal?

Add _.not to underscore.util.existential

Not seems easy right?

function not(b) { return !(!!b); }

Then:

not(false);
//=> true

But then:

not('');
//=> true

This is JavaScript -- but is that the _.not that we want?

The utilities in existential intentionally simplify truthiness to be:

  • null, false and undefined are falsey
  • everything else is truthy

Is this the _.not we want?

Installing underscore-contrib pulls devDependencies

I just installed underscore-contrib to use in my package using npm as follows

npm install --save underscrore-contrib

And it seems to me that the install pulls underscore-contrib's devDependencies and their transitive dependencies such as grunt-contrib-quinit and its dependencies grunt-lib-phantomjs and so on. The entire dependency graph has been installed.

This should not be the case. If I want to use underscore-contrib, I'd only like to pull underscore-contrib and its dependencies and not the devDependencies.

Please let me know if I am missing something.

Revise combinators to work with methods as well as functions

Currently, several of the combinators have, buried within them a call to .apply(null, ...). For example:

fnull: function(fun /*, defaults */) {
  var defaults = _.rest(arguments);

  return function(/*args*/) {
    var args = _.toArray(arguments);
    var sz = _.size(defaults);

    for(var i = 0; i < sz; i++) {
      if (!existy(args[i]))
        args[i] = defaults[i];
    }

    return fun.apply(null, args);
  };
}

This works perfectly for standalone functions but cannot be used on methods because it erases the current object context. If fun.apply(null, args) is replaced with fun.apply(this, args), fnull (and others with similar calls to .apply) can be used with methods as well as with standalone functions.

_.fix acts weird when too few arguments supplied

Hi,

Please, take look at the example below:
http://requirebin.com/?gist=5996118

You can see there how _.fix behaves when it expects at least 2 arguments and there is only one on call - placeholders stay (and they are _objects). This isn't something I would expect. I think that unsupplied arguments should be filled asundefined.

Another strange behavior shows up when you uncomment 9th line. If you examine console you will see that arguments are saved between calls and that can lead to pretty nasty bugs.

My proposition is to forget arguments between calls and make them undefined if not given. So that code above would print 1, undefined, 3

var foo = function (a, b, c) { 
  console.log(a, b, c);
};

var bar = _.fix(foo, _, _, 3);

bar(1, 2); // 1, 2, 3
bar(1); // 1, undefined, 3

I can make a pull request if that's ok.

Cheers!

add more _.is<thing> predicates?

I have run across a number of cases where testing for literals in javascript is difficult. For example, much of this code:

https://github.com/thinkthroughmath/ttm-coffeescript-math/blob/master/src/math/build_expression_from_javascript_object.coffee

was rather tricky to write because determining the literal types was difficult.

Thus, I'm proposing we add a few extra methods:

isString
isFunction
isNumber

... etc. I don't know exactly which ones would make sense, but I am sure some would, and I would be willing to prototype these. This is something I have been wanting to work on for a while.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.