Search code examples
djangounit-testing

How do I get around ModuleNotFoundError: No module named 'dot env


I am doing the official django tutorial polls app on part 5 which is about testing in django. As a part of the instructions I am supposed to go into my models.py file and run the python manage.py shell command to activate a shell terminal. From there I am supposed to run a series of commands to import things for my test.

Link to material: https://docs.djangoproject.com/en/4.2/intro/tutorial05/

The commands I need to run are:

>>> import datetime
>>> from django.utils import timezone
>>> from polls.models import Question
>>> # create a Question instance with pub_date 30 days in the future
>>> future_question = Question(pub_date=timezone.now() + datetime.timedelta(days=30))
>>> # was it published recently?
>>> future_question.was_published_recently()
True

I run the import datetime, and from django.utils import timezone and there are no issues. Once I get to from polls.models import Question I am hit with an error message no modulenotfounderror" no module named dot env.

enter image description here

I have tried looking at stack overflow articles and they suggested installing it via pip. So I exited my shell command and tried installing dotenv with pip. When I do so I get the following error message shown in the screenshot. enter image description here

I looked at this stack overflow article python modulenotfounderror and ran the pip install python-dotenv command and got this error when attempting:

I have since uninstalled that command hoping to reset back to what I had when I started the problem.

I have posted this question to django forums and discord to see if I can get an answer.

I have searched on youtube to see if I can get around this.

My specific question would be how do I get this django test to work. I believe it has to do with this dotenv error.

Do you think since its a tutorial I could just update the code to what it is saying in the instructions and move on?

from pathlib import Path
import os 
from dotenv import load_dotenv, find_dotenv

load_dotenv(find_dotenv())

SECRET_KEY = os.environ['SECRET_KEY']
# https://stackoverflow.com/questions/15209978/where-to-store-secret-keys-django either this or remove it
# I did option one and it worked! 

# Build paths inside the project like this: BASE_DIR / 'subdir'.
BASE_DIR = Path(__file__).resolve().parent.parent


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

# SECURITY WARNING: keep the secret key used in production secret!



# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []

# Application definition

INSTALLED_APPS = [
    'polls.apps.PollsConfig',
    'django.contrib.admin', 
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
]

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    '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',
]

ROOT_URLCONF = 'mysite.urls'

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
            ],
        },
    },
]

WSGI_APPLICATION = 'mysite.wsgi.application'


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

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.postgresql',
        'NAME': 'mysite_database',
    }
}


# Password validation
# https://docs.djangoproject.com/en/4.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
    {
        'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
    },
]


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

LANGUAGE_CODE = 'en-us'

TIME_ZONE = 'America/Chicago'

USE_I18N = True

USE_TZ = True


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

STATIC_URL = 'static/'

Default primary key field type

https://docs.djangoproject.com/en/4.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'


Solution

  • The answer to the original question is to run pip install python-dotenv (PyPI link) as opposed to pip install dotenv, a package that hasn't been updated since 2018, as seen in the Github link.

    Now for the KeyError you ran into.

    KeyError means it didn't find the key SECRET_KEY, which from your screenshots is probably because there is no .env file that I can see. Just create a file called .env (NOTE, it must be called .env with a . and not just env), and this is where you will store secret keys (which hopefully you won't post on StackOverflow). Something like this:

    # .env
    
    SECRET_KEY=aBcDeFgHiJkLmNoPqRsTuVwXyZ123456789
    DATABASE_PASSWORD=aVeryStrongDatabsePassword
    ANOTHER_KEY=ujhgasdhfcdahfda123794123472314723judh
    
    # Any other variables you need to keep secret
    

    You can easily generate long, secure passwords and keys using secrets.

    Finally, please copy and paste code. Do not use screenshots for this. Checkout why should I not use screenshots? And checkout this link, 5 Ways to Embed Code in StackOverflow if you're not sure how.