I am creating an API and my app isn’t saving user information to the POSTGRES database. Can someone look over my code and tell me what is wrong?
SECRET_KEY = os.environ['SECRET_KEY']
ALLOWED_HOSTS = ['salty-sands-40947.herokuapp.com','.herokuapp.com']
DEBUG = True
# Application definition
INSTALLED_APPS = [
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'aroomieapp',
'oauth2_provider',
'social_django',
'social.apps.django_app.default',
'rest_framework_social_oauth2',
"push_notifications"
]
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 = 'aroomie.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',
'django.template.context_processors.media',
'social_django.context_processors.backends',
'social_django.context_processors.login_redirect',
],
},
},
]
WSGI_APPLICATION = 'aroomie.wsgi.application'
# Database
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
}
}
# Password validation
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/1.10/topics/i18n/
LANGUAGE_CODE = 'en-us'
TIME_ZONE = 'UTC'
USE_I18N = True
USE_L10N = True
USE_TZ = True
LOGIN_REDIRECT_URL = '/'
# Setting the image path in server
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')
MEDIA_URL = '/media/'
# This package help us to replace our database with Postgresql
import dj_database_url
db_from_env = dj_database_url.config()
DATABASES['default'].update(db_from_env)
AUTHENTICATION_BACKENDS = (
# Others auth providers (e.g. Google, OpenId, etc)
# Facebook OAuth2
'social_core.backends.facebook.FacebookOAuth2',
# django-rest-framework-social-oauth2
'rest_framework_social_oauth2.backends.DjangoOAuth2',
# Django
'django.contrib.auth.backends.ModelBackend',
)
# Facebook configuration
SOCIAL_AUTH_FACEBOOK_KEY = os.environ['FACEBOOK_KEY']
SOCIAL_AUTH_FACEBOOK_SECRET = os.environ['FACEBOOK_SECRET']
# Define SOCIAL_AUTH_FACEBOOK_SCOPE to get extra permissions from facebook. Email is not sent by default, to get it, you must request the email permission:
SOCIAL_AUTH_FACEBOOK_SCOPE = [
'email',
# 'user_birthday',
]
SOCIAL_AUTH_FACEBOOK_PROFILE_EXTRA_PARAMS = {
'fields': 'id, name, email, age_range, gender'
}
# Login process customization purpose
SOCIAL_AUTH_PIPELINE = (
'social_core.pipeline.social_auth.social_details',
'social_core.pipeline.social_auth.social_uid',
'social_core.pipeline.social_auth.auth_allowed',
'social_core.pipeline.social_auth.social_user',
'social_core.pipeline.user.get_username',
'social_core.pipeline.user.create_user',
'aroomieapp.social_auth_pipeline.extend_user_profile', # <--- set the path to the function
'social_core.pipeline.social_auth.associate_user',
'social_core.pipeline.social_auth.load_extra_data',
'social_core.pipeline.user.user_details',
)
UPDATE (TRACEBACK)
2017-04-28T00:02:32.455554+00:00 app[web.1]: Internal Server Error: /api/user/profile/
2017-04-28T00:02:32.455575+00:00 app[web.1]: Traceback (most recent call last):
2017-04-28T00:02:32.455577+00:00 app[web.1]: File "/app/.heroku/python/lib/python3.5/site-packages/django/core/handlers/exception.py", line 39, in inner
2017-04-28T00:02:32.455578+00:00 app[web.1]: response = get_response(request)
2017-04-28T00:02:32.455579+00:00 app[web.1]: File "/app/.heroku/python/lib/python3.5/site-packages/django/core/handlers/base.py", line 187, in _get_response
2017-04-28T00:02:32.455581+00:00 app[web.1]: response = self.process_exception_by_middleware(e, request)
2017-04-28T00:02:32.455582+00:00 app[web.1]: File "/app/.heroku/python/lib/python3.5/site-packages/django/core/handlers/base.py", line 185, in _get_response
2017-04-28T00:02:32.455583+00:00 app[web.1]: response = wrapped_callback(request, *callback_args, **callback_kwargs)
2017-04-28T00:02:32.455584+00:00 app[web.1]: File "/app/aroomieapp/apis.py", line 60, in user_get_profile
2017-04-28T00:02:32.455584+00:00 app[web.1]: expires__gt = timezone.now())
2017-04-28T00:02:32.455585+00:00 app[web.1]: File "/app/.heroku/python/lib/python3.5/site-packages/django/db/models/manager.py", line 85, in manager_method
2017-04-28T00:02:32.455585+00:00 app[web.1]: return getattr(self.get_queryset(), name)(*args, **kwargs)
2017-04-28T00:02:32.455586+00:00 app[web.1]: File "/app/.heroku/python/lib/python3.5/site-packages/django/db/models/query.py", line 385, in get
2017-04-28T00:02:32.455586+00:00 app[web.1]: self.model._meta.object_name
2017-04-28T00:02:32.455587+00:00 app[web.1]: oauth2_provider.models.DoesNotExist: AccessToken matching query does not exist.
2017-04-28T00:02:32.511548+00:00 heroku[router]: at=info method=GET path="/api/user/profile/?access_token=" host=salty-sands-40947.herokuapp.com request_id=c9c65c38-9617-4616-906f-78cd06dca05c fwd="69.203.1.36" dyno=web.1 connect=1ms service=97ms status=500 bytes=70045 protocol=https
Code with database information:
# This package help us to replace our database with Postgresql
import dj_database_url
db_from_env = dj_database_url.config(conn_max_age=500)
DATABASES['default'].update(db_from_env)
AUTHENTICATION_BACKENDS = (
# Others auth providers (e.g. Google, OpenId, etc)
# Facebook OAuth2
'social_core.backends.facebook.FacebookAppOAuth2',
'social_core.backends.facebook.FacebookOAuth2',
# django-rest-framework-social-oauth2
'rest_framework_social_oauth2.backends.DjangoOAuth2',
# Django
'django.contrib.auth.backends.ModelBackend',
)
# Facebook configuration
SOCIAL_AUTH_FACEBOOK_KEY = os.environ['FACEBOOK_KEY']
SOCIAL_AUTH_FACEBOOK_SECRET = os.environ['FACEBOOK_SECRET']
# Define SOCIAL_AUTH_FACEBOOK_SCOPE to get extra permissions from facebook. Email is not sent by default, to get it, you must request the email permission:
SOCIAL_AUTH_FACEBOOK_SCOPE = [
'email',
# 'user_birthday',
]
SOCIAL_AUTH_FACEBOOK_PROFILE_EXTRA_PARAMS = {
'fields': 'id, name, email, age_range, gender'
}
# Login process customization purpose
SOCIAL_AUTH_PIPELINE = (
'social_core.pipeline.social_auth.social_details',
'social_core.pipeline.social_auth.social_uid',
'social_core.pipeline.social_auth.auth_allowed',
'social_core.pipeline.social_auth.social_user',
'social_core.pipeline.user.get_username',
'social_core.pipeline.user.create_user',
'aroomieapp.social_auth_pipeline.extend_user_profile', # <--- set the path to the function
'social_core.pipeline.social_auth.associate_user',
'social_core.pipeline.social_auth.load_extra_data',
'social_core.pipeline.user.user_details',
)
social_auth_pipeline:
from aroomieapp.models import Profile
def extend_user_profile(backend, user, request, response, *args, **kwargs):
if backend.name == 'facebook':
avatar = 'https://graph.facebook.com/%s/picture?type=normal' % response['id']
gender = response['gender']
age_min = response['age_range']['min'] if response['age_range'].get('min') else 0
age_max = response['age_range']['max'] if response['age_range'].get('max') else 0
lifestyle_info = "0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0"
if not Profile.objects.filter(user_id=user.id):
Profile.objects.create(user_id=user.id, age_min=age_min, age_max=age_max, gender=gender, avatar=avatar, lifestyle_info=lifestyle_info)
I am also getting an AccessToken error message when it tries to create one. I really am stuck and I do not know where to go from here.
Thank you
2
Answers
So I figured it out. It had to do with the creation of my client_id and client_secret tokens. Sometimes the Heroku generated client_id and client_secret tokens aren't generated. So what you have to do to work around this is to go into your django admin and create a new application. With the following settings: Client type: confidential or public Authorization grant type: Authorization code Name: Name of service (in my case Facebook)
This will give you the client_id and client_secret tokens but they will ONLY work if you click submit to create the application. Once that is done, your API will be able to communicate with your application.
Your settings don’t mention PostgresSQL. They only specify a sqlite3 database.
You should follow the instructions and add: