Django ImportError cannot import name request

15,438

This is due to discrepancy in Python version.

In Python 2.7, you might have to replace:

from urllib import request

in your forms.py with

import urllib2

Again the urllib2 > Request module does not have the urlopen method. So you will have to replace the line

response = request.urlopen(image_url)

with:

response = urllib2.urlopen(image_url)

in your forms.py

There is a nice discussion about the differences between urllib and urllib2 here on this SO post

Share:
15,438
WaR1o
Author by

WaR1o

Updated on June 04, 2022

Comments

  • WaR1o
    WaR1o almost 2 years

    I'm learning Django using book Django-By-Example by Antonio Mele. For now I reached chapter 5 and now I'm trying to create image sharing app. But despite following all instructions in that chapter I'm getting ImportError when I try to add the image from external URL in django development server.

        ImportError at /images/create/
    
    cannot import name request
    
    Request URL:    http://127.0.0.1:8000/images/create/?title=%20Django%20and%20Duke&url=http://upload.wikimedia.org/wikipedia/commons/8/85/Django_Reinhardt_and_Duke_Ellington_(Gottlieb).jpg.
    Django Version:     1.8.6
    Exception Location:     /home/ciotar/projects/VirtualEnvs/env/bookmarks/bookmarks/images/forms.py in <module>, line 1
    Python Version:     2.7.11
    

    I'm using Pycharm and have set python 3.5 interpreter from active virtualenv instance. Not sure why Django runs with python 2.7 though. I wonder if this problem could appear because of 'request' name conflict between forms.py and views.py modules?

    /images/urls.py

    urlpatterns = [
        url(r'^create/$', views.image_create, name='create'),
    ]
    

    /images/views.py

    from django.shortcuts import render, redirect
    from django.contrib.auth.decorators import login_required
    from django.contrib import messages
    from .forms import ImageCreateForm
    
    
    @login_required
    def image_create(request):
        """
        View for creating an Image using the JavaScript Bookmarklet.
        """
        if request.method == 'POST':
            # form is sent
            form = ImageCreateForm(data=request.POST)
            if form.is_valid():
                # form data is valid
                cd = form.cleaned_data
                new_item = form.save(commit=False)
                # assign current user to the item
                new_item.user = request.user
                new_item.save()
                messages.success(request, 'Image added successfully')
                # redirect to new created item detail view
                return redirect(new_item.get_absolute_url())
        else:
            # build form with data provided by the bookmarklet via GET
            form = ImageCreateForm(data=request.GET)
    
        return render(request, 'images/image/create.html', {'section': 'images',
                                                            'form': form})
    

    /images/forms.py

    from urllib import request
    from django.core.files.base import ContentFile
    from django.utils.text import slugify
    from django import forms
    from .models import Image
    
    
    class ImageCreateForm(forms.ModelForm):
    
        class Meta:
            model = Image
            fields = ('title', 'url', 'description')
            widgets = {
                'url': forms.HiddenInput,
            }
    
        def clean_url(self):
            url = self.cleaned_data['url']
            valid_extensions = ['jpg', 'jpeg']
            extension = url.rsplit('.', 1)[1].lower()
            if extension not in valid_extensions:
                raise forms.ValidationError('The given URL does not match valid image extensions.')
            return url
    
        def save(self, force_insert=False, force_update=False, commit=True):
            image = super(ImageCreateForm, self).save(commit=False)
            image_url = self.cleaned_data['url']
            image_name = '{}.{}'.format(slugify(image.title),
                                        image_url.rsplit('.', 1)[1].lower())
    
            # download image from the given URL
            response = request.urlopen(image_url)
            image.image.save(image_name,
                             ContentFile(response.read()),
                             save=False)
    
            if commit:
                image.save()
            return image