#python #django #django-socialauth
#python #django #django-socialauth
Вопрос:
Я внедрил social-auth для Google, чтобы пользователи могли входить в систему. Я не могу понять, как ограничить доступ посетителей к общим представлениям, таким как UpdateView, ListView или CreateView, если они не вошли в систему с помощью системы социальной авторизации. Вот код.
views.py
class AchievementCreate(CreateView):
form_class = AchievementForm2
model = Achievements
def form_valid(self, form):
achieves = form.save(commit=False)
achieves.resume = Resume.objects.get(pk=2)
return super(AchievementCreate, self).form_valid(form)
def home(request):
#logout(request)
uname=""
if request.method == 'POST' and 'submit' in request.POST:
submit = request.POST['submit']
if submit=="sign-out":
logout(request)
if '_auth_user_id' in request.session:
uname=sm.UserSocialAuth.objects.get(
user_id=int(request.session['_auth_user_id'])
).user
request.session['uname']=str(uname)
return render(request,'cv/home.html',{'uname': uname})
home.html
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8"/>
<title>Home</title>
</head>
<body>
<form method="post" action="{% url 'cv:home' %}">{% csrf_token %}
{% if uname %}
Helo, {{uname}}<br>
The user already signed in. He may need to sign out<br>
<input type="submit" name="submit" value="sign-out">
{% else %}
Please sign-in<br>
<a href="{% url 'social:begin' 'google-oauth2' %}">Google login</a>
{% endif %}
</form>
</body>
</html>
urls.py
urlpatterns = [
url(r'^$', views.IndexView.as_view(), name='index'),
url(r'^achievements/(?P<pk>[0-9] )/delete/$', views.AchievementDelete.as_view(), name='achievement-delete'),
url(r'^achievements/(?P<pk>[0-9] )/$', views.AchievementUpdate.as_view(), name='achievement-update'),
url(r'^achievements/add/$', login_required(views.AchievementCreate.as_view()), name='achievement-add'),
url(r'^home/$', views.home, name='home'),]
Я хочу, чтобы класс «AchievementCreate» был доступен только в том случае, если пользователь вошел в систему. Но я не понимаю, как. Можно ли использовать сеансы? Как в этом случае?
Комментарии:
1.
login_required
Декоратор не работает?2. Нет. Это не так.
Ответ №1:
Нам нужно написать mixins, чтобы проверить, вошел ли пользователь в систему или нет.
В Django 1.9 введен LoginRequiredMixin:
from django.contrib.auth.mixins import LoginRequiredMixin
class UserProfile(LoginRequiredMixin, View):
login_url = '/login/'
Следующий код представляет собой пользовательский mixin, который проверяет, активен или неактивен пользователь. Если пользователь неактивен, он выйдет из сеанса. Нам нужно записать микшины в отдельный файл, например mixins.py , импортировать микшины в представлениях
class UserMixin(object):
def dispatch(self, request, *args, **kwargs):
user = self.request.user
if user:
if user.is_active:
return super(UserMixin, self).dispatch(request, *args, **kwargs)
else:
logout(self.request)
return HttpResponseRedirect(reverse('cv:home'))
В Views.py
from mixins.py import UserMixin
class UserEdit(UserMixin, View):
model = UserProfile
template_name = "dashboard/edit_user.html"
Ответ №2:
Вам нужно импортировать декоратор login_required и поместить @login_reqired перед представлением. Это представление будет доступно только при входе в систему.
Пример:
from django.contrib.auth.decorators import login_required
@login_required
#put your view here
Комментарии:
1. Вы использовали его в своем views.py или просто перед видом в url.py ?
2. Я использовал это, и это сработало. @method_decorator(login_required) def dispatch(self, * аргументы, ** kwargs): возвращает super(AchievementCreate, self).dispatch(* аргументы, ** kwargs)
3. Есть ли какой-либо способ получить доступ к «request.session [‘uname’]» внутри общего класса представления?
4. Я использую модель auth_user из django, и все, что мне нужно вызвать, это
request.user.<attribute>
5. Когда я пытаюсь это сделать, я получаю сообщение «запрос глобального имени не определен».
Ответ №3:
Итак, вы используете «social-auth» для своей системы входа. В вашем случае вам придется использовать пользовательскую функцию. Я предполагаю, что вы можете получить доступ к зарегистрированному пользователю, обратившись к: request.SESSION
Если это так, то вы можете переопределить метод отправки вашего CreateView:
class AchievementCreate(CreateView):
.....
.....
def dispatch(self, request, *args, **kwargs):
user = request.session['_auth_user_id']
# handle authentication
Ответ №4:
def home(request):
if request.user.is_authenticated:
# Do something for authenticated users
else:
# Do something for anonymous users
https://docs.djangoproject.com/en/3.1/topics/auth/default/#authentication-in-web-requests