1

I have an array which looks like:

var data = [{
    key: ['blue-berries', 'strawberries'],
    title: 'Berries',
}, {
    key: 'chicken',
    title: 'Chicken',
}, {
    key: 'beef',
    title: 'Beef',
}, {
    key: 'something-else',
    title: 'Something Else',
}]

Assuming my 'query' was something like '/strawberries-with-some-other-stuff'

We should return the first item in the example array.

'/beef-with-some-other-whatever' Would return the 3rd (and so on)

As you can see, some key properties are arrays, others are just static strings

The following appears to work, using lodash _.find

var input = '/strawberries-with-some-other-stuff';

var result = _.find(data, function(d) {

    if (d.key instanceof Array) {
        return _.forEach(d.key, function(key) {
            if (input.indexOf(key + '-') == 0) {
                console.log('key- ', key + '-')
                return d
            } else return null;
        });
    } else {
        if (input.indexOf(d.key + '-') == 0) {
            return d
        }
    }
});

However, it's a false positive, as if I change input to '/beef-with-some-other-whatever' it still returns the first item in the array

I presume I'm misusing _.find somehow... Is there a better way?

5
  • Will the words be separated by -? Commented Dec 23, 2014 at 12:29
  • should test the indexOf == 1 for the "/" or am I missing something ? Commented Dec 23, 2014 at 12:36
  • @AmitJoki - usually, but this cannot be guaranteed Commented Dec 23, 2014 at 12:47
  • @Hacketo - Good point - in my actual app i replace '/' with '' Commented Dec 23, 2014 at 12:48
  • this code is working for me with indexOf == 1 and "/beef-with-some-other-whatever" Commented Dec 23, 2014 at 12:53

3 Answers 3

2
var input = '/strawberries-with-some-other-stuff';

var result = _.find(data, function (el) {
  if (Array.isArray(el.key)) {
    return _.find(el.key, function (k) {
      return input.indexOf(k + '-') >= 0;  // or return input.indexOf(k + '-') == 0; - need replace first symbol '/' 
    });
  }

  return input.indexOf(el.key + '-') >= 0;  // or return input.indexOf(el.key + '-') == 0; - need replace first symbol '/' 
});

Demo: http://jsbin.com/kucec/3/edit?js,console

Sign up to request clarification or add additional context in comments.

Comments

1

I don't know lodash or underscore or whatever. I think you could do it in native js

var str = "/beef-with-some-other-whatever";
var obj = data.filter(function(o){
    return str.match(/\w+/g).some(function(word){ 
       ~(word+"").indexOf(word);
    });
})[0];

Note that if word happened to be Array, it would call join(",") so it would still work.

Comments

1

There are a few points you're missing here:

  • You're returning a value from inside a forEach callback. That doesn't make any sense and it doesn't have any effect on anything.
  • The function you pass to _.find should be a predicate. That means it returns either true or false.

The following should work for your requirement:

var input = '/strawberries-with-some-other-stuff';

var result = _.find(data, function(d) {
    if (d.key instanceof Array) {
        return !!_.find(d.key, function(key) {
            return input.indexOf(key + '-') === 0;                
        });
    } 

    return input.indexOf(d.key + '-') === 0;
});

There is some duplicate code here, so you can simplify this a bit further:

var input = '/strawberries-with-some-other-stuff';

var result = _.find(data, function(d) {
    function matchesQuery(keyStr) { return input.indexOf(keyStr + '-') === 0; } 

    return (d.key instanceof Array)
        ? !!_.find(d.key, matchesQuery)
        : matchesQuery(d.key);
});

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.