0

I have this JSON file (truncated):

{
    "** Please contact a mod by posting on the forums **": {
        "tvdb_id": "257937",
        "last_updated": 1341780286,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/17288.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/17288.jpg"
        }
    },
    "Jamies Best Ever Christmas": {
        "tvdb_id": "214161",
        "last_updated": 1329701153,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/9126.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/9126.jpg"
        }
    },
    "Kuromajo-san ga Tooru!!": {
        "tvdb_id": "257914",
        "last_updated": 1395775431,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/15640.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/15640.jpg"
        }
    }
}

and this code:

$(".tvshow").select2({
  placeholder: "Type in a TV show",
  multiple: true,
  maximumSelectionSize: 1,
  minimumInputLength: 2,
  maximumInputLength: 20,
  query: function(query) {
    var data = {results: []};
    var value = $(".select2-input").val();
    $.ajax ({
      type: "GET",
      url: 'shows.json',
      dataType: "jsonp",
      json: "callbackname",
      crossDomain : true,
      success: function (result) {
        $.each(result, function (i, show) {
          // write everything in an array
          data.results.push({id: this.tvdb_id, text: this.title, poster: this.images.poster, bg: this.fanart });
          console.log(this.title);
          selectedTVshow = this.title;
          // results = data.results;

          // return array
          query.callback(data);
        })
      },
      error: function (data) {
        // console.log('error');
      }
    })
  }
})

When I search for Jamies Best Ever Christmas I want it to return the name and the respective tvdb_id and details.

In my above code you can see console.log(this.title);. This is wrong, because there is no title: value inside the JSON object. How can I get this to work and retrieve data?

Demo: http://jsfiddle.net/6pGFC/ (use first input field to get autocomplete, not second)

Thanks a lot!

Alex
  • 1,576
  • 3
  • 17
  • 35
  • I left an [answer](http://stackoverflow.com/a/22797760/225905) on your other question that seems to line up with what you want to do. Can you help me understand why that answer won't work? – Vishal Kotcherlakota Apr 01 '14 at 22:15
  • @VishalKotcherlakota: Because I’m not using Underscore.js. And it’s throwing a console error as it is: “Resource interpreted as Script but transferred with MIME type text/plain” – Alex Apr 01 '14 at 22:17
  • You need to make sure your script type is `text/javascript`, I think. Happy hunting. – Vishal Kotcherlakota Apr 01 '14 at 22:25
  • BTW, jQuery has a `$.map()` feature you may find useful: https://api.jquery.com/jQuery.map/ – Vishal Kotcherlakota Apr 01 '14 at 22:27

2 Answers2

1

It looks like you want to do a mapping operation to transform the data into something easier to work with. Underscore.js is a fantastic tool for this.

var mappedResults = _.map(result, function(key, value, list) {
    return {name:key, tvdb_id:value.tvdb_id};
});

This will turn this:

{
    "** Please contact a mod by posting on the forums **": {
        "tvdb_id": "257937",
        "last_updated": 1341780286,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/17288.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/17288.jpg"
        }
    },
    "Jamies Best Ever Christmas": {
        "tvdb_id": "214161",
        "last_updated": 1329701153,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/9126.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/9126.jpg"
        }
    },
    "Kuromajo-san ga Tooru!!": {
        "tvdb_id": "257914",
        "last_updated": 1395775431,
        "images": {
            "poster": "http://zapp.trakt.us/images/posters/15640.jpg",
            "fanart": "http://zapp.trakt.us/images/fanart/15640.jpg"
        }
    }
}

...into this:

[
    {name:"** Please contact a mod by posting on the forums **", tvdb_id:"257937"},
    {name:"Jamies Best Christmas", tvdb_id:"21461"},
    {name:"Kuromajo-san ga Tooru!!", tvdb_id:"257914"}
]

Once that's done, you can filter it like so:

function getMatchingIds(searchterm) {
    return _.filter(mappedResults, function(entry) {
        return (entry.name.indexOf(searchterm) != -1);
    }
}

I should also add that jQuery has its own $.map feature that does something similar.

Vishal Kotcherlakota
  • 1,134
  • 4
  • 13
  • 36
1

There are a couple of issues in your example.

  1. You dropbox file is not JSONP. It is JSON. (so jquery cannot parse it)
  2. Since you are iterating over an object and not over an array with $.each the arguments passed to the function are key and value, so in your case the i is the key. (see https://api.jquery.com/jQuery.each/)

In general the searching should happen in the server side, and not on the client (especially for 5mb files)

Here is demo that has fixed (i have re-uploaded the corrected file to my dropbox) the above two problems http://jsfiddle.net/6pGFC/3/
(too slow though since it tries to display all the json)

Gabriele Petrioli
  • 191,379
  • 34
  • 261
  • 317