1👍
Problem
I think the bottom line is that your first instinct that the page yelp.html
was being overwritten was correct. Your yelping
returns render(request, 'app/yelp.html')
, which has no data in it, because no context has been given to it. Now this view function first calls yelp_main(request)
, which also returns render(request, 'app/yelp.html')
, the page with no data again. But it does call def query_api(request, term, location):
. This does return data with the page since it has a context, dic
with it, render(request, 'app/yelp.html', dic)
. But query_api
returns to yelp_main
which overwrites it with the no data version of the page, and then the original calling function replaces that with another no data version of the page.
Solution
Instead of returning pages with render, could you just return an empty HttpResponse, and then only at the end send the dictionary:
# views.py
from django.http import HttpResponse
@csrf_exempt
def yelping(request):
form = YelpForm(request.POST or None)
if form.is_valid():
form.save(commit=False)
term = request.POST['term']
location = request.POST['location']
form.save()
print("yelping", term, location)
yelp_main(request)
messages.success(request, "Search successful." )
return redirect('app:yelping')
#return render(request, 'app/yelp.html', {'form' : form})
messages.error(request, "Unsuccessful Search. Invalid information.")
assert isinstance(request, HttpRequest)
# NOTE: I removed the .first() from the following line
yelp_data = Business.objects.filter(business_id=business_id).order_by('-id')
dic = {
'yelp_data': yelp_data,
}
print(dic)
return render(request, 'app/yelp.html', dic)
and
# yelp.py
from django.http import HttpResponse
@csrf_exempt
def yelp_main(request):
#request.session._get_or_create_session_key()
term = request.POST.get('term')
location = request.POST.get('location')
db()
print("yelp_api", term, location)
query_api(request, term, location)
return HttpResponse("OK")
#return render(request, 'app/yelp.html')
def query_api(request, term, location):
print("query_api", term, location)
response = search(API_KEY, term, location)
businesses = response.get('businesses')
if not businesses:
print(u'No businesses for {0} in {1} found.'.format(term, location))
return
business_id = businesses[0]['id']
response = get_business(API_KEY, business_id)
write_to_file = json.dumps([response], indent=4)
with open('app/API/YelpAPI/yelp.json', 'w') as f:
f.write(write_to_file)
return HttpResponse("OK")
#return render(request, 'app/yelp.html', dic)
Edit
Why the dict is only printing one piece of data?
I may have misunderstood by what you meant by one piece of data.
Business.objects.filter(business_id=business_id).order_by('-id').first()
will return the Business object, which includes all the fields of that class, but if you print
it it will only show the business_name
. Why? Because that’s what you asked Django to print when you defined
def __str__(self):
return self.business_name
If, as I think you want to print out all the rows, then remove the .first()
since that will return one Business object, which is obviously not something you can iterate through, giving you "Business is not iterable". Then in your HTML you should be able to do:
{% for y in yelp_data %}
<td>{{ y.business_name }}</td>
<td>{{ y.phone }}</td>
<td>{{ y.city }}</td>
...
{% endfor %}