please help me!!!
My project backend is django and frontend uses react.
Local testing with localhost works fine.
When I go online on the server and adjust the apache domain name, the sessionid cannot be automatically stored.
I have tried many methods, but they are not available.
But I found that if I don’t use the apache proxy, it works fine if I use the ip directly, and the sessionid can also be stored.
What is the reason for this?
The code I put below.
By looking at the application page in chrome’s developer tools,
The cookies are used to determine whether the sessionid is successfully set.
In this process, the domain name request has not been stored, and the ip request is very normal.
doamin name request
doamin name result
Django Settings
INSTALLED_APPS = [
'whitenoise.runserver_nostatic',
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.messages',
'django.contrib.staticfiles',
'rest_framework',
'django_crontab',
'command_app',
'djcelery',
'corsheaders'
]
MIDDLEWARE = [
'django.contrib.sessions.middleware.SessionMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
'corsheaders.middleware.CorsMiddleware',
'django.middleware.common.CommonMiddleware',
# 'django.middleware.csrf.CsrfViewMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'django.middleware.security.SecurityMiddleware',
'whitenoise.middleware.WhiteNoiseMiddleware'
]
CORS_ALLOW_CREDENTIALS = True
CORS_ORIGIN_ALLOW_ALL = True
# CORS_ALLOW_ALL_ORIGINS = True
CORS_ALLOWED_ORIGINS = [
'http://react server ip:3000',
'https://react server ip:3000',
'http://localhost:3000',
'http://server ip:3000',
'https://server ip:3000',
'http://www.my domain name.com',
'https://www.my domain name.com',
'http://my domain name.com:3000',
'https://my domain name.com:3000',
'http://my domain name.com',
'https://my domain name.com',
]
REST_FRAMEWORK = {
"DEFAULT_AUTHENTICATION_CLASSES": ("CustomAuthentication", )
}
CORS_ALLOW_METHODS = (
'DELETE',
'GET',
'OPTIONS',
'PATCH',
'POST',
'PUT',
'VIEW',
)
CORS_ALLOW_HEADERS = (
'XMLHttpRequest',
'X_FILENAME',
'accept-encoding',
'authorization',
'content-type',
'dnt',
'origin',
'user-agent',
'x-csrftoken',
'x-requested-with',
'Pragma',
)
CACHES = {
'default': {
'BACKEND': "django_redis.cache.RedisCache",
"LOCATION": "redis://localhost:6379/3", # TODO 3
"OPTIONS": {
"CLIENT_CLASS": "django_redis.client.DefaultClient",
"CONNECTION_POOL_KWARGS": {"max_connections": 100}
}
}
}
SESSION_ENGINE = "django.contrib.sessions.backends.cache"
SESSION_CACHE_ALIAS = "default"
Django View
class LoginAPI(generics.GenericAPIView):
authentication_classes = (SessionAuthentication, )
serializer_class = LoginSerializer
def post(self, request):
print(request.session.session_key)
print(f"LoginAPI IsLogin: {request.user.is_authenticated}")
if request.user.is_authenticated:
return HttpResponse(dumps({'message': 'Login!'}), content_type='application/json', status=status.HTTP_200_OK)
serializer = self.get_serializer(data=request.data)
try:
serializer.is_valid(raise_exception=True)
except ValidationError:
return HttpResponse(status=status.HTTP_401_UNAUTHORIZED)
user = serializer.validated_data
login(request, user)
return HttpResponse(dumps({'message': 'Logout Success!'}),
content_type='application/json', status=status.HTTP_200_OK)
def get(self, request):
print(request.session.session_key)
if request.user.is_authenticated:
return HttpResponse(dumps({'message': 'Login!'}), content_type='application/json', status=status.HTTP_200_OK)
else:
return HttpResponse(dumps({'message': 'Not Login!'}), content_type='application/json', status=status.HTTP_401_UNAUTHORIZED)
def my_logout(request):
print(request.session.session_key)
print(f"my_logout Is Login: {request.user.is_authenticated}")
logout(request)
return HttpResponse(dumps({'message': 'Logout Success!'}), content_type='application/json', status=status.HTTP_200_OK)
urls.py
urls.py
urlpatterns = [
path('login/', LoginAPI.as_view()), # new web
path('logout/', my_logout), # new web
]
React Code
export default class App extends Component {
testRequest = () => {
axios({
method: 'GET',
url: 'http://server:8049/login/',
headers: {
'Accept': 'application/json',
'Content-Type': 'application/json'
},
withCredentials: true
}).then(res => {
alert(res.data)
})
}
handleSubmit = (event) => {
event.preventDefault()
this.testRequest()
axios.defaults.withCredentials = true;
const csrftoken = GetCookie('csrftoken')
console.log(csrftoken)
const data = new FormData(event.currentTarget);
axios({
method: 'POST',
url: 'http://server:8049/login/',
dataType: 'json',
data: {
'username': data.get('username'),
'password': data.get('password'),
},
headers: {
"X-CSRFtoken": csrftoken,
'Accept': 'application/json',
'Content-Type': 'application/json',
},
timeout: 100000000000,
withCredentials: true
}).then(res => {
console.log(res)
}).catch(res => {
console.log(res)
})
}
render() {
return (
<div><Box component="form" onSubmit={this.handleSubmit} noValidate sx={{mt: 1}}>
<TextField
margin="normal"
required
fullWidth
id="username"
label="UserName"
name="username"
autoComplete="username"
autoFocus
/>
<TextField
margin="normal"
required
fullWidth
name="password"
label="Password"
type="password"
id="password"
autoComplete="current-password"
/>
<FormControlLabel
control={<Checkbox value="remember" color="primary"/>}
label="Remember me"
/>
<Button
type="submit"
fullWidth
variant="contained"
sx={{mt: 3, mb: 2}}
>
Sign In
</Button>
<Grid container>
<Grid item xs>
<Link href="http://http://my domain name:8049/logout/"variant="body2">
logout
</Link>
</Grid>
<Grid item>
<Link href="#" variant="body2">
{"Don't have an account? Sign Up"}
</Link>
</Grid>
</Grid>
</Box>
</Box>
</div>)
}
}
Apache Code
<VirtualHost *:80>
ServerAdmin [email protected]
DocumentRoot /home/ec2-user/project_path
ServerName www.my domain name.com
ServerAlias my domain name.com
ProxyPass / http://localhost:8048/
ProxyPassReverse / http://localhost:8048/
</VirtualHost>
2
Answers
On a whim, I assigned subdomains to the frontend and backend. Is this guaranteed to be homologous. I sent a request in this case, and found that the backend domain name successfully stored the sessionid, and successfully determined the login status in the next request. Although it is very strange, it does fulfill my needs.
Change
ALLOWED_HOSTS
toALLOWED_HOSTS = ['*']
.