1

I have a problem that seems to pop up randomly throughout the entire web app I have been working on.

My app will be moving along just fine and then, when moving from one view to another, the page will start to load but then continue on loading indefinitely. I can go back refresh and then continue on through the same view like there was absolutely no problem at all. When this happens the rest of code in my view still runs just fine, but the page just continues loading without producing any kind of Http Response.

Like I said I have tried to remove parts of my project to figure out where the issue may lie. The issue started to happen near the time I migrated my database to using South although I really am not sure if/how the two would be intertwined. Even if you have an idea of what might be causing the issue please respond I would greatly appreciate any help or even a general direction to go in.

urls.py

from django.conf.urls import patterns, url
from BucketList import views

urlpatterns = patterns('',
url(r'^$', views.index, name='index'),
url(r'^stats/$', views.index_stats, name='index stats'),
url(r'^item/(?P<id>\w+)/comment/', views.add_item_comment, name = 'add item comments'),
url(r'^item/(?P<id>\w+)/', views.index_items, name = 'index items'),
url(r'^userstats/(?P<id>\w+)/', views.user_stats, name='user profile'),
url(r'^create/$', views.create, name='create'),
url(r'^create/(?P<id>\w+)/', views.create_specific_item, name = 'create specific item'),
url(r'^mylist/$', views.my_list, name='mylist'),
url(r'^mylist/stats/$', views.my_list_stats, name='mylist stats'),
url(r'^mylist/edit/(?P<id>\w+)/', views.edit_bucket_list_item, name = 'edit my list item'),
url(r'^mylist/view/(?P<id>\w+)/', views.view_my_list_item, name = 'view my list item'),
url(r'^mylist/uncross/(?P<id>\w+)/', views.uncross_my_list_item, name = 'uncross my list item'),
url(r'^mylist/crossoff/(?P<id>\w+)/', views.cross_off_my_list_item, name = 'cross off'),
url(r'^mylist/deleteitem/(?P<id>\w+)/', views.delete_my_list_item, name = 'delete list item'),
url(r'^mylist/recommendation/$', views.recommendation, name = 'recommendation'),
url(r'^profile/edit/$', views.edit_profile, name = 'edit profile'),
)

settings.py

"""
Django settings for Bucket project.

For more information on this file, see
https://docs.djangoproject.com/en/1.6/topics/settings/

For the full list of settings and their values, see
https://docs.djangoproject.com/en/1.6/ref/settings/
"""

# Build paths inside the project like this: os.path.join(BASE_DIR, ...)
import os
BASE_DIR = os.path.dirname(os.path.dirname(__file__))


# Quick-start development settings - unsuitable for production
# See https://docs.djangoproject.com/en/1.6/howto/deployment/checklist/


DEBUG = True

TEMPLATE_DEBUG = True

ALLOWED_HOSTS = []


# Application definition

INSTALLED_APPS = (
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'BucketList',
'south',

)

MIDDLEWARE_CLASSES = (
'django.contrib.sessions.middleware.SessionMiddleware',
'django.middleware.common.CommonMiddleware',
'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
)

TEMPLATE_DIRS = [os.path.join(BASE_DIR, 'templates')]

ROOT_URLCONF = 'Bucket.urls'

WSGI_APPLICATION = 'Bucket.wsgi.application'


# Database
# https://docs.djangoproject.com/en/1.6/ref/settings/#databases

DATABASES = {
'default': {
    'ENGINE': 'django.db.backends.sqlite3',
    'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
}
}

# Internationalization
# https://docs.djangoproject.com/en/1.6/topics/i18n/

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'UTC'

USE_I18N = True

USE_L10N = True

USE_TZ = True


# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/1.6/howto/static-files/

STATIC_URL = '/static/'

LOGIN_URL = '/accounts/login/'

views.py

from django.shortcuts import render
from django.http import HttpResponse
from BucketList.models import BucketListItem, UserProfile, Comment
from django.contrib import auth
from forms import BucketListItemForm, UserProfileForm, UserProfileEditForm, BucketListItemEditForm, CustomItemEditForm, CommentForm
from django.http import HttpResponseRedirect
from django.core.context_processors import csrf
from django.contrib.auth.models import User
from django.db.models import Sum
from django.contrib.auth.forms import UserCreationForm
from django.utils import timezone
from django.contrib.auth.decorators import login_required



def index(request):
    #The main Bucket List Page View, sorted by pubdate so the most recent are at the top
    all_list_items = BucketListItem.objects.all().order_by('-pub_date')

    context = {'all_list_items': all_list_items}

    return render(request, 'BucketList/index.html', context)

@login_required  
def index_items(request, id):
    #When a user clicks on a Bucket List Item on the index page it will take them here with a brief overview of that items information
    item = BucketListItem.objects.get(pk = id)
    current_user = UserProfile.objects.get(pk = request.user.id)
    comments = Comment.objects.filter(item = item)
    if request.POST:
        form = CommentForm(request.POST)
        if form.is_valid():
            body = form.cleaned_data['body']
            my_model = form.save(commit = False)
            my_model.created = timezone.now()
            my_model.author = current_user.user
            my_model.item = item
            my_model.body = body
            my_model.save()
            form = CommentForm()
    else:
        form = CommentForm()

    context = {'item': item,
                      'id': id,
                      'comments': comments,
                      'form': form,
                      }

    context.update(csrf(request))

    return render(request, 'BucketList/index_items.html', context)


@login_required
def user_stats(request, id):
    #A public stats/profile page that displays their basic profile information as well as their bucket list
    item = User.objects.all().filter(username = id)
    item_profile = item[0].userprofile
    list_of_all = BucketListItem.objects.all().filter(pub_by = item)
    context = {'id': id,
                      'item': item[0],
                      'list_of_all': list_of_all,
                      'item_profile': item_profile,
                    }
    return render(request, 'BucketList/user_stats.html', context)


@login_required
def index_stats(request):
    #This page compiles interesting statistics about all of the Bucket List Items on the main index page and displays that information
    list_of_all = BucketListItem.objects.all().count()
    total_cost = BucketListItem.objects.all().aggregate(Sum('cost'))
    total_time = BucketListItem.objects.all().aggregate(Sum('time'))
    total_crossed_off = BucketListItem.objects.all().aggregate(Sum('crossed_off'))
    number_of_users = User.objects.all().count()
    cost_per_user = total_cost['cost__sum']/number_of_users
    time_per_user = total_time['time__sum']/number_of_users
    items_per_user = list_of_all/number_of_users
    crossed_off_per_user = total_crossed_off['crossed_off__sum']/number_of_users

    context = {'list_of_all': list_of_all,
                      'total_cost': total_cost['cost__sum'],
                      'total_time': total_time['time__sum'],
                      'total_crossed_off': total_crossed_off['crossed_off__sum'],
                      'crossed_off_per_user': crossed_off_per_user,
                      'number_of_users': number_of_users,
                      'cost_per_user': cost_per_user,
                      'time_per_user': time_per_user,
                      'items_per_user': items_per_user,
                      }

    return render(request, 'BucketList/index_stats.html', context)


@login_required
def my_list(request):
    #The current users personal Bucket List view with links to create more list items or learn statistics about their list
    personal_list = BucketListItem.objects.all().filter(pub_by = request.user.id)

    context = {'personal_list': personal_list,
                      'user': request.user.username
                    }

    return render(request, 'BucketList/mylist.html', context)



@login_required
def my_list_stats(request):
    #General statistics about the current users Bucket List
    personal_list = BucketListItem.objects.all().filter(pub_by = request.user.id)
    total_cost = BucketListItem.objects.all().filter(pub_by = request.user.id).aggregate(Sum('cost'))
    total_time = BucketListItem.objects.all().filter(pub_by = request.user.id).aggregate(Sum('time'))
    total_crossed_off = BucketListItem.objects.all().filter(pub_by = request.user.id).aggregate(Sum('crossed_off'))
    cost_per_list_item = total_cost['cost__sum']/personal_list.count()
    time_per_list_item = total_time['time__sum']/personal_list.count()

    context = {'personal_list': personal_list,
                      'user': request.user.username,
                      'total_cost': total_cost['cost__sum'],
                      'total_time': total_time['time__sum'],
                      'total_crossed_off': total_crossed_off['crossed_off__sum'],
                      'cost_per_list_item': cost_per_list_item,
                      'time_per_list_item': time_per_list_item,
                      }

    return render(request, 'BucketList/my_list_stats.html', context)



@login_required
def view_my_list_item(request, id):
    #View of a current users Bucket List Item with options to cross off or edit the Bucket List Item
    logged_in = request.user.id
    item = BucketListItem.objects.filter(pk = id)
    context = {'logged_in': logged_in,
                      'item': item[0],
                    }
    return render(request, 'BucketList/view_my_list_item.html', context)



@login_required
def cross_off_my_list_item(request, id):
    #The view that crosses off the Bucket List Item
    item = BucketListItem.objects.get(pk = id)
    item.crossed_off = True
    item.pub_date = timezone.now()
    item.save()

    context = {'item': item,
                      'User': User,
                    }

    return render(request, 'BucketList/crossed_off.html', context)



@login_required
def uncross_my_list_item(request, id):
    #The view that uncrosses off the Bucket List Item
    item = BucketListItem.objects.get(pk = id)
    item.crossed_off = False
    item.pub_date = timezone.now()
    item.save()

    context = {'item': item,
                      'User': User,
                    }
    return render(request, 'BucketList/uncross.html', context)



@login_required
def delete_my_list_item(request, id):
    #The view that uncrosses off the Bucket List Item
    item = BucketListItem.objects.get(pk = id)
    title = item.text
    item.delete()

    context = {'title': title,
                      'User': User,
                    }

    return render(request, 'BucketList/delete.html', context)



@login_required
def create(request):
    #Creates a Bucket List Item, the user only fills out the Name and Type of the item while the rest of the fields are auto-filled: publication date, published by, crossed off, time, hours, and cost 
    if request.POST:
        form = BucketListItemForm(request.POST)
        if form.is_valid():
            user = User.objects.get(id=request.user.id)
            my_model = form.save(commit = False)
            new_cost = form.cleaned_data['cost']
            new_time = form.cleaned_data['time']
            new_hours = form.cleaned_data['hours']
            my_model.pub_by = user
            my_model.crossed_off = False
            my_model.time = new_time
            my_model.hours = new_hours
            my_model.cost = new_cost
            my_model.save()
            return HttpResponseRedirect('/bucketlist/mylist/')
    else:
        form = BucketListItemForm()

    args = {}
    args.update(csrf(request))
    args['form'] = form

    return render(request, 'BucketList/create_item.html', args)


@login_required
def edit_bucket_list_item(request, id):
    #This view lets the user edit their Bucket List Item and directs them to other forms necessary to make the changes needed
    item = BucketListItem.objects.get(pk = id)
    if request.method == "POST":
        form = BucketListItemEditForm(request.POST)
        if form.is_valid():
            text = form.cleaned_data['text']
            goal_type = form.cleaned_data['goal_type']
            cost = form.cleaned_data['cost']
            time = form.cleaned_data['time']
            hours = form.cleaned_data['hours']
            item.text = text
            item.cost = cost
            item.time = time
            item.hours = hours
            item.goal_type = goal_type
            item.pub_date = timezone.now()
            item.save()
            return HttpResponseRedirect('/bucketlist/mylist/')
    else:
        form = BucketListItemEditForm({'text': item.text, 'goal_type': item.goal_type, 'cost': item.cost, 'time': item.time, 'hours': item.hours})
        context = {'form': form,
                           'id': item.id,
                          }
        context.update(csrf(request))

    return render(request, 'BucketList/edit_bucket_list_item.html', context)


@login_required
def edit_profile(request):
    #A view that allows the user to edit their current profile information
    current_user = UserProfile.objects.get(pk = request.user.id)
    if request.method == "POST":
        form = UserProfileEditForm(request.POST)
        if form.is_valid():
            new_age = form.cleaned_data['new_age']
            new_life_expectancy = form.cleaned_data['new_life_expectancy']
            new_yearly_earnings = form.cleaned_data['new_yearly_earnings']
            new_hourly_wage = form.cleaned_data['new_hourly_wage']
            current_user.yearly_earnings = new_yearly_earnings
            current_user.hourly_wage = new_hourly_wage
            current_user.life_expectancy = new_life_expectancy
            current_user.age = new_age   
            current_user.save()
            return HttpResponseRedirect('/bucketlist/mylist/')
    else:
        form = UserProfileEditForm({'new_age': current_user.age, 'new_life_expectancy': current_user.life_expectancy, 'new_yearly_earnings': current_user.yearly_earnings, 'new_hourly_wage': current_user.hourly_wage})
        context = {'form': form,
                        }
        context.update(csrf(request))
    return render(request, 'BucketList/edit_user_profile.html', form)
  • "it doesn't work sometimes but I don't know why" is meaningless. We can't help you solve the problem without at least *some* point of reference to what the hell you're talking about. Please narrow down the issue, try figuring out *what* is happening and *what part* of the code is causing it. If you open the chrome console, do you see an error? If it's a certain view, can you share the code for it? If you're using something out of the ordinary (custom middleware perhaps) **share it**. What django version, how does urls.py look like - The more you give us the better (up to a point, but still) – yuvi Sep 15 '14 at 20:19
  • First of all I wanted to say thank you for the response. I apologize for being too broad with my question. When the freezing issue occurs nothing whatsoever is visible in the chrome console. There is not one certain view that is causing the problem. It is happening across every view but not in any consistent sort of interval. Sometimes I can navigate across 20 pages within my app before it happens when other times it will happen repeatedly with the same view. There are no error messages whatsoever, just a blank loading chrome console. I am not using any custom middleware. – Michael Sullivan Sep 15 '14 at 20:59
  • quick followups: 1. what version of django are you using 2. are you sure this isn't a browser issue? Have you tried using a different one? Or a different computer? 3. Can you also share your `settings.py` (and remember to omit the personal information - passwords, secret key etc...) – yuvi Sep 16 '14 at 06:10
  • I am using django version 1.6. I have tried using firefox and internet explorer as well. The problem occurs on both of those although it does happen more on firefox and much more often on IE. Other web pages don't seem to have any problems. Could I have an issue with internet settings? I have not yet tried a different computer. – Michael Sullivan Sep 16 '14 at 14:11
  • 1. How does chrome behave? 2. what version of IE? (**this is important**) 3. have you tried a different computer? – yuvi Sep 16 '14 at 14:26
  • Chrome will infinitely load the page with no error messages and no error messages in my development server either. According to the server everything is working just fine. The same exact thing happens in firefox and IE10. I have been trying to access the development server on a different computer but have been having difficulty setting it up (not because I am encountering any problems, I just have never done this before) – Michael Sullivan Sep 16 '14 at 14:40
  • I accessed the development server with chrome from a different computer (using a Chromebook, so I didn't get to try IE or firefox) and the problem seemed to be completely gone. It never once occurred when navigation through the main part of the site. Then I accessed the admin and the problem still does occur but it seems as though only when looking around in the site admin. – Michael Sullivan Sep 16 '14 at 15:21
  • I know I asked for several files already, but what you shared till now look fine, so I'm gonna ask to see `views.py` too. In the meantime, try removing django (delete the directory as well, don't just `pip uninstall`) and then cleanly reinstall it from scratch. – yuvi Sep 16 '14 at 16:03
  • I added views.py. I left out one of the views that had some sensitive information in it. But the rest is all there. I will try removing django right away and post my results. – Michael Sullivan Sep 16 '14 at 17:07
  • so right off the bat - you don't need to csrf anything. If you're using `render`, [this happens automatically](http://stackoverflow.com/a/17409197/2387772). Remove all `csrf()` calls. Does it make any difference? – yuvi Sep 16 '14 at 17:44
  • I did not know that, thanks! I found and removed some adware on my system as well (Win32/CostMin) and removed all of the csrf() calls. I can no longer replicate the problem, it appears to be fixed. Thank you so much for the help yuvi and thank you for putting up with my vague question. – Michael Sullivan Sep 16 '14 at 18:10
  • Sure thing. Next time, try those things yourself (all I did was suggest you look at different parts - and for most part, almost all of them have nothing to do with django). I'll post a proper answer with some debugging tips – yuvi Sep 16 '14 at 21:25

1 Answers1

1

Looking at your views it seems you are calling csrf() on the request, and then sending the response back with render. The whole point of render is that it automatically enforces all context processors, so you don't have to manually call csrf().

Even though it usually shouldn't matter, in my experience I have noticed that a duplicate call to csrf can sometimes cause weird and unexpected behavior after a few requests.

As we discussed in the comments, after applying this change (among a few others) the problem stopped happening. My prime suspect is the csrf() call but it can easily be that you had a corrupted django installation (next time, use a virtualenv) or some other local issue that had nothing to do with django.

Community
  • 1
  • 1
yuvi
  • 18,155
  • 8
  • 56
  • 93