我试图在 Django 中创建一个 API 客户端服务器模型,但每次我在登录视图中登录用户时。当我需要使用登录中的信息和会话时,由于某种原因,它会在我的故事视图中重置为 AnonymousUser。如果我使用@login required,它只会将我重定向到登录页面,就好像我刚才不只是授权并与用户创建会话一样。这是我的观点.py:
@csrf_exempt
def login_view(request):
if request.method == 'POST':
payload = request.POST
# Validate payload keys
if 'Username' not in payload or 'Password' not in payload:
return JsonResponse({'message': 'Username or password missing'}, status=400)
username = payload['Username']
password = payload['Password']
user = authenticate(request, username=username, password=password)
if user is not None:
# Log the user in and store session data
login(request, user)
return JsonResponse({'message': 'Login successful', 'user_id':user.id}, status=200)
else:
# Incorrect username or password
return JsonResponse({'message': 'Incorrect username or password'}, status=401)
@csrf_exempt
@login_required
def stories(request):
if request.method == 'POST':
if request.user.is_authenticated:
print(request.user.username)
# Retrieve data from the POST request
headline = request.POST.get('Headline')
category = request.POST.get('Category')
region = request.POST.get('Region')
details = request.POST.get('Details')
# Get the current user's author object
author = Author.objects.get(user=request.user.id)
author_name = author.name
# Create a new story object
new_story = Stories.objects.create(
headline=headline,
story_cat=category,
story_region=region,
autho_name=author,
story_date=timezone.now(),
story_details=details
)
return JsonResponse({'message': 'Story created successfully'}, status=201)
else:
return JsonResponse({'message': 'Authentication required'}, status=503)
else:
return JsonResponse({'message': 'Method not allowed'}, status=503)
这是我的客户处理程序:
def login():
global login_status
url = 'http://127.0.0.1:8000/api/login/'
username = input("Enter username: ")
password = input("Enter password: ")
payload = {'Username': username, 'Password': password}
# Make sure to set 'Content-Type' header to 'application/x-www-form-urlencoded'
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
# Encode the payload as 'application/x-www-form-urlencoded'
data = '&'.join([f"{key}={value}" for key, value in payload.items()])
r = requests.post(url, data=data, headers=headers)
response_data = r.json()
if r.status_code == 200:
print("Login successful")
login_status = True
else:
print("Login failed:", response_data.get('message'))
def Post_story():
global login_status
url = 'http://127.0.0.1:8000/api/stories/'
headline = input("Enter a headline: ")
category = input("Enter a category(pol, art, tech, trivia): ")
region = input("Enter a region(uk, eu, w): ")
details = input("Enter story details: ")
payload = {'Headline': headline, 'Category': category, 'Region': region, 'Details': details}
# Make sure to set 'Content-Type' header to 'application/x-www-form-urlencoded'
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
# Encode the payload as 'application/x-www-form-urlencoded'
data = '&'.join([f"{key}={value}" for key, value in payload.items()])
r = requests.post(url, data=data, headers=headers)
response_data = r.json()
if r.status_code == 201:
print("Post successful")
else:
print("Post failed:", response_data.get('message'))
while True:
if login_status == False:
command = input("Enter command (login/exit): ").strip()
if command == "login":
login()
elif command == "exit":
break
else:
print("Invalid command. Please enter 'login', or 'exit'.")
if login_status == True:
command = input("Enter command (post/logout/exit): ").strip()
if command == "post":
Post_story()
elif command == "logout":
logout()
elif command == "exit":
break
else:
print("Invalid command. Please enter 'post', 'logout', or 'exit'.")
如果需要我的 url.py:
from django.urls import path
from . import views
urlpatterns = [
# ex: /api/
path("", views.index, name="index"),
# ex: /api/login
path("login/", views.login_view, name="login"),
# ex: /api/logout
path("logout/", views.logout_view, name="logout"),
# ex: /api/stories
path("stories/", views.stories, name="stories"),
]
我尝试过弄乱我的settings.py,尝试使用 request.session 手动存储会话数据,但由于某种原因,视图发生变化时,会话就会丢失。我想避免使用外部库进行会话存储,但我也尝试在控制台中清除会话。
删除
@csrf_exempt
两个视图。
@login_required
def stories(request):
if request.method == 'POST':
if request.user.is_authenticated:
print(request.user.username)
# Retrieve data from the POST request
headline = request.POST.get('Headline')
category = request.POST.get('Category')
region = request.POST.get('Region')
details = request.POST.get('Details')
# Get the current user's author object
author = Author.objects.get(user=request.user.id)
author_name = author.name
# Create a new story object
new_story = Stories.objects.create(
headline=headline,
story_cat=category,
story_region=region,
autho_name=author,
story_date=timezone.now(),
story_details=details
)
return JsonResponse({'message': 'Story created successfully'}, status=201)
else:
return JsonResponse({'message': 'Authentication required'}, status=503)
else:
return JsonResponse({'message': 'Method not allowed'}, status=503)
您让
stories
仅接受帖子请求。您返回 get 请求的错误消息。这是错误的。
因此,当用户登录后,他们会使用 get 方法重定向到
stories
。但View不接受get请求。
这就是问题所在。
使用以下语法。
@login_required
def stories(request):
if request.method == 'POST':
if request.user.is_authenticated:
#PROCESS THE POST REQUEST
return JsonResponse({'message': 'Story created successfully'}, status=201)
else:
#REDIRECT TO LOGIN
return JsonResponse({'message': 'Authentication required'}, status=503)
else:
#RUNDER STORIES VIEW/FORM
return JsonResponse({'message': 'Method not allowed'}, status=503)