ga-wdi-exercises / pbj-project3

[project]
0 stars 2 forks source link

Initial API request w/Click Event #24

Closed jeffjones89 closed 9 years ago

jeffjones89 commented 9 years ago

Currently our external API request works, returns an array, and we are using a constructor function to pass that data into an array of food items that we're planning to use going forward.

The issue we are running into is that the API request is predicated on a user submitting a form to query the API itself, so I believe we're having trouble chaining the promise to an Item.fetch() that is undefined until the user actually fires the click event.

The items array will console.log in the console just fine, but any time we try to maniuplate the items array outside of the initial AJAX call it seems to be getting lost.

Happy to include the code that works initially (it's kinda lengthy), but we're a bit lost at how this all works in terms of chaining promises to a click event.

Sitting at the tables outside classroom 2.

RobertAKARobin commented 9 years ago

Using jQuery by itself, there isn't a way to "grab" the contents of a form when it's submitted. You have two main options: use jQuery to get all the values of the input elements inside the form, or use the jQuery Form plugin, which does let you grab the contents of a form.

http://malsup.com/jquery/form/

jeffjones89 commented 9 years ago

We've got the array we want to return in the console currently...the AJAX request returns an array of objects.

The Item.Fetch constructor creates new Items for each object, and pushes each into an array of Items that contains all 20 new Items.

So when trying to chain a view onto it (i.e. Item.fetch().then(function(items)){...etc}

it is telling us that it cannot read .then of undefined.

jeffjones89 commented 9 years ago
Item.fetch = function(){
  var submit = $('input[type=submit]');
  submit.on('click', function(){
  event.preventDefault();
  var restaurant = $('#menu-search').val();
  var url = "https://api.nutritionix.com/v1_1/search/"+ restaurant +"?results=0%3A20&cal_min=450&cal_max=50000&fields=*&appId=32443fbb&appKey=37587913d9144f31f691efdf130a12ab"
  var request = $.getJSON(url).then(function(response){
    $('#menu-search').val('');
    var itemsRes = response.hits;
    var items = [];
    for (var i = 0; i < itemsRes.length; i++){
      items.push(new Item(itemsRes[i].fields))
    }
    return items;
  }).then(function(items){
    console.log(items)
  }).fail(function(response){
    console.log("js failed to load");
  })
  return request;
});
jeffjones89 commented 9 years ago

That's for the console.log version to ensure we had our items array formatting correctly. Which it seems to be.

When we tried to chain, we removed the entire .then statement and just returned items from the $.getJSON.

RobertAKARobin commented 9 years ago

.then can only be added onto something asynchronous, like .getJSON or .ajax. The function inside .then must return something that's asynchronous.

For instance, this works:

$.ajax({

}).then(function(){
  return $.getJSON();
}).then(function(){
  console.log("done");
});

This doesn't work:

$.ajax({

}).then(function(){
  return "hello";
}).then(function(){
  console.log("done");
});

Your first .then doesn't contain anything asynchronous, and it just returns a garden-variety array, so you can't .then after it.

jeffjones89 commented 9 years ago

Think I figured it, I refactored the click event to our application.js file, which is now allowing the items array to persist through the promise.

Now just need to clean up the view/render functionality. Thanks.