completed the logic of the page PsychTest

This commit is contained in:
Денис Сарапулов 2023-05-16 02:24:06 +10:00
parent 67140144d7
commit c313690e11
14 changed files with 321 additions and 29 deletions

Binary file not shown.

View File

@ -1,6 +1,7 @@
from django.contrib import admin
from .models import Apartament, Photo, User
from .models import Apartament, Photo, User, PsychTestAnswers
admin.site.register(Apartament)
admin.site.register(Photo)
admin.site.register(User)
admin.site.register(PsychTestAnswers)

View File

@ -115,7 +115,6 @@ class UserFactory(factory.django.DjangoModelFactory):
favorites_apartments = CSV(1, 100, 1, 16);
comparison_apartments = CSV(1, 100, 1, 5);
psych_test_result = Random(20, 90);
openid_addr = OpenID_Address();
name = factory.faker.Faker('name');
date_of_birth = Date(1980, 2006);

View File

@ -16,9 +16,9 @@ class Migration(migrations.Migration):
migrations.CreateModel(
name='User',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('favorites_apartments', models.CharField(max_length=100, help_text="Избранные квартиры (CSV)")),
('comparison_apartments', models.CharField(max_length=100, help_text="Квартиры для сравнения (CSV)")),
('psych_test_result', models.IntegerField(validators=[MaxValueValidator(100)], null=True, help_text="Результат психологического теста")),
('openid_addr', models.CharField(max_length=1000, null=False, help_text='Адрес Open ID Connect (login@provider.com, для ВВГУ - login@vvsu.ru)')),
('name', models.CharField(max_length=256, help_text='ФИО Пользователя')),
('date_of_birth', models.DateField(help_text='Дата рождения пользователя')),

View File

@ -0,0 +1,104 @@
# Generated by Django 4.2.1 on 2023-05-15 14:41
import django.core.validators
from django.db import migrations, models
import django.db.models.deletion
class Migration(migrations.Migration):
dependencies = [
('pairent_app', '0005_user'),
]
operations = [
migrations.AlterModelOptions(
name='user',
options={'verbose_name': 'Пользователь', 'verbose_name_plural': 'Пользователи'},
),
migrations.AlterField(
model_name='user',
name='about_me',
field=models.CharField(max_length=1000, verbose_name='Поле "О Себе"'),
),
migrations.AlterField(
model_name='user',
name='city',
field=models.CharField(max_length=1000, null=True, verbose_name='Город пользователя'),
),
migrations.AlterField(
model_name='user',
name='comparison_apartments',
field=models.CharField(max_length=100, verbose_name='Квартиры для сравнения (CSV)'),
),
migrations.AlterField(
model_name='user',
name='date_of_birth',
field=models.DateField(verbose_name='Дата рождения пользователя'),
),
migrations.AlterField(
model_name='user',
name='discord',
field=models.CharField(max_length=1000, null=True, verbose_name='Дискорд ник пользователя'),
),
migrations.AlterField(
model_name='user',
name='email',
field=models.CharField(max_length=1000, null=True, verbose_name='Почтовый ящик пользователя в формате user@example.com'),
),
migrations.AlterField(
model_name='user',
name='favorites_apartments',
field=models.CharField(max_length=100, verbose_name='Избранные квартиры (CSV)'),
),
migrations.AlterField(
model_name='user',
name='gender',
field=models.CharField(max_length=1, verbose_name='Пол пользователя (f,m,n,?)'),
),
migrations.AlterField(
model_name='user',
name='name',
field=models.CharField(max_length=256, verbose_name='ФИО Пользователя'),
),
migrations.AlterField(
model_name='user',
name='openid_addr',
field=models.CharField(max_length=1000, verbose_name='Адрес Open ID Connect (login@provider.com, для ВВГУ - login@vvsu.ru)'),
),
migrations.AlterField(
model_name='user',
name='phone',
field=models.CharField(max_length=30, null=True, verbose_name='Телефон пользователя в международном формате (+00000000)'),
),
migrations.AlterField(
model_name='user',
name='role',
field=models.CharField(max_length=1, verbose_name='Роль пользователя (s - student, a - admin, m - moderator)'),
),
migrations.AlterField(
model_name='user',
name='telegram',
field=models.CharField(max_length=1000, null=True, verbose_name='Телеграм пользователя'),
),
migrations.CreateModel(
name='PsychTestAnswers',
fields=[
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
('first_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на первый вопрос')),
('second_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на второй вопрос')),
('third_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на третий вопрос')),
('fourth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на четвертый вопрос')),
('fifth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на пятый вопрос')),
('sixth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на шестой вопрос')),
('seventh_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на седьмой вопрос')),
('eighth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на восьмой вопрос')),
('nineth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на девятый вопрос')),
('tenth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на десятый вопрос')),
('eleventh_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на одиннадцатый вопрос')),
('twelfth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на двенадцатый вопрос')),
('thirteenth_question', models.IntegerField(validators=[django.core.validators.MaxValueValidator(5)], verbose_name='Ответ на тринадцатый вопрос')),
('users', models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, to='pairent_app.user', verbose_name='Пользователь')),
],
),
]

View File

@ -0,0 +1,22 @@
# Generated by Django 4.2.1 on 2023-05-15 15:23
from django.db import migrations
class Migration(migrations.Migration):
dependencies = [
('pairent_app', '0006_alter_user_options_alter_user_about_me_and_more'),
]
operations = [
migrations.AlterModelOptions(
name='psychtestanswers',
options={'verbose_name': 'Ответ на психологический тест', 'verbose_name_plural': 'Ответы на психологический тест'},
),
migrations.RenameField(
model_name='psychtestanswers',
old_name='users',
new_name='user',
),
]

View File

@ -85,7 +85,7 @@ class User(models.Model):
favorites_apartments = models.CharField(max_length=100, verbose_name="Избранные квартиры (CSV)")
comparison_apartments = models.CharField(max_length=100, verbose_name="Квартиры для сравнения (CSV)")
psych_test_result = models.IntegerField(validators=[MaxValueValidator(100)], null=True, verbose_name="Результат психологического теста")
openid_addr = models.CharField(max_length=1000, null=False, verbose_name='Адрес Open ID Connect (login@provider.com, для ВВГУ - login@vvsu.ru)')
name = models.CharField(max_length=256, verbose_name='ФИО Пользователя')
date_of_birth = models.DateField(verbose_name='Дата рождения пользователя')
@ -104,4 +104,26 @@ class User(models.Model):
class Meta:
verbose_name = "Пользователь"
verbose_name_plural = "Пользователи"
verbose_name_plural = "Пользователи"
class PsychTestAnswers(models.Model):
"""Модель ответов на психологический тест"""
user = models.ForeignKey(User, on_delete=models.CASCADE, verbose_name="Пользователь")
first_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на первый вопрос")
second_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на второй вопрос")
third_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на третий вопрос")
fourth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на четвертый вопрос")
fifth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на пятый вопрос")
sixth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на шестой вопрос")
seventh_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на седьмой вопрос")
eighth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на восьмой вопрос")
nineth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на девятый вопрос")
tenth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на десятый вопрос")
eleventh_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на одиннадцатый вопрос")
twelfth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на двенадцатый вопрос")
thirteenth_question = models.IntegerField(validators=[MaxValueValidator(5)], verbose_name="Ответ на тринадцатый вопрос")
class Meta:
verbose_name = "Ответ на психологический тест"
verbose_name_plural = "Ответы на психологический тест"

View File

@ -10,7 +10,7 @@ urlpatterns = format_suffix_patterns([
path("apartaments/comparison/", views.ApartamentGetManyViewSet.as_view({'get': 'retrieve'})), # пример: apartaments/comparison/?user_id=1 user_id - id пользователя
path("apartaments/favorite/", views.ApartamentGetManyViewSet.as_view({'get': 'list'})), # пример: apartaments/favorite/?user_id=1 user_id - id пользователя
path("apartaments/filters/", views.ApartmentFilter.as_view({'post': 'list'})),
path("psych_test/add_result/<int:pk>", views.PsychTestAddResultViewSet.as_view({'patch': 'update'})), # пример: psych_test/add_result/1/?result=50 result - результат псих теста пользователя
path("psych_test/add_result/<int:pk>", views.PsychTestAddResultViewSet.as_view({'post': 'create'})), # пример: psych_test/add_result/1/?result=50 result - результат псих теста пользователя
path("users/get_compatible", views.CompatibleUsersView.as_view({'post': 'list'})),
re_path(r'^auth/vvsu/', views.VVSUAuthProxy),
])

View File

@ -9,7 +9,7 @@ from django.db.models.query import QuerySet
from django.core.validators import validate_email
from django.core.exceptions import ValidationError
from .models import Apartament, User
from .models import Apartament, User, PsychTestAnswers
from .serializer import (ApartamentListSerializer,
ApartamentDetailSerializer,
PsychTestAddResultSerializer,
@ -30,6 +30,7 @@ class ApartamentViewSet(viewsets.ReadOnlyModelViewSet):
elif self.action == "retrieve":
return ApartamentDetailSerializer
class ApartamentGetManyViewSet(viewsets.ReadOnlyModelViewSet):
"""Вывод отдельных квартир для сравнения"""
def get_queryset(self): # получение id квартир для избранного или сравнения
@ -60,6 +61,7 @@ class ApartamentGetManyViewSet(viewsets.ReadOnlyModelViewSet):
apartaments.append(ApartamentListSerializer(i).data)
return Response({'results': apartaments})
class ApartmentFilter(viewsets.ViewSet):
"""Вывод списка квартир или отдельной квартиры"""
@ -90,12 +92,28 @@ class ApartmentFilter(viewsets.ViewSet):
class PsychTestAddResultViewSet(viewsets.ViewSet):
def get_object(self, pk):
return User.objects.filter(pk=pk)
def update(self, request, pk):
return User.objects.get(pk=pk)
def create(self, request, pk):
user = self.get_object(pk)
result = request.query_params.get("result", None)
user.update(psych_test_result=result)
return Response(PsychTestAddResultSerializer(User.objects.get(pk=pk)).data)
results = request.data
PsychTestAnswers.objects.create(
user=user,
first_question=results['first'],
second_question=results['second'],
third_question=results['third'],
fourth_question=results['fourth'],
fifth_question=results['fifth'],
sixth_question=results['sixth'],
seventh_question=results['seventh'],
eighth_question=results['eighth'],
nineth_question=results['nineth'],
tenth_question=results['tenth'],
eleventh_question=results['eleventh'],
twelfth_question=results['twelfth'],
thirteenth_question=results['thirteenth']
)
return Response({'successfully': 'results post'})
class CompatibleUsersView(viewsets.ViewSet):
def list(self, req: Request):

View File

@ -9,6 +9,7 @@
"bootstrap-icons": "^1.10.5",
"font-awesome": "^4.7.0",
"formik": "^2.2.9",
"oidc-client-ts": "^2.2.3",
"react": "^18.2.0",
"react-awesome-slider": "^4.1.0",
"react-bootstrap": "^2.7.4",

View File

@ -1,26 +1,28 @@
import axios from 'axios';
import constants from '../constants';
import axios from "axios";
import constants from "../constants";
const { API_ROOT } = constants;
export default class ApartamentService {
static async getAll(limit, offest) {
const response = await axios.get(API_ROOT + '/api/apartaments/', {
const response = await axios.get(API_ROOT + "/api/apartaments/", {
params: {
limit: limit,
...(offest !== 0 ? {offset: offest} : {})
}
})
...(offest !== 0 ? { offset: offest } : {}),
},
});
return response;
}
static async getById(id) {
const response = await axios.get(API_ROOT + '/api/apartament/' + id + '/')
const response = await axios.get(
API_ROOT + "/api/apartament/" + id + "/"
);
return response;
}
static async getComparisons() {
const response = await axios.get(API_ROOT + '/api/comparison/')
const response = await axios.get(API_ROOT + "/api/comparison/");
return response;
}
}
}

View File

@ -0,0 +1,13 @@
import axios from "axios";
import constants from "../constants";
const { API_ROOT } = constants;
export default class PsychTestAddResult {
static async addById(id, answers) {
const data = await axios.post(
API_ROOT + "/api/psych_test/add_result/" + id,
answers
);
}
}

View File

@ -1,14 +1,27 @@
import PsychTestQuestion from "../../components/PsychTestQuestion";
import React, { useState } from "react";
import PsychTestAddResult from "../../API/PsychTestAddResult";
import { useNavigate } from "react-router-dom";
const PsychTest = () => {
const navigate = useNavigate();
const [answers, setAnswers] = useState({
first: 0,
second: 0,
third: 0,
fourth: 0,
fifth: 0,
sixth: 0,
seventh: 0,
eighth: 0,
nineth: 0,
tenth: 0,
eleventh: 0,
twelfth: 0,
thirteenth: 0,
});
// TODO: Может как-то изменить, а то я сидел и тупил
// TODO: Может как-то изменить, а то я сидел и тупил только не ругайте
const answerChangeHandler = (answer, account) => {
if (account == "first") {
setAnswers((previous) => ({
@ -25,12 +38,64 @@ const PsychTest = () => {
...previous,
third: answer,
}));
} else if (account == "fourth") {
setAnswers((previous) => ({
...previous,
fourth: answer,
}));
} else if (account == "fifth") {
setAnswers((previous) => ({
...previous,
fifth: answer,
}));
} else if (account == "sixth") {
setAnswers((previous) => ({
...previous,
sixth: answer,
}));
} else if (account == "seventh") {
setAnswers((previous) => ({
...previous,
seventh: answer,
}));
} else if (account == "eight") {
setAnswers((previous) => ({
...previous,
eight: answer,
}));
} else if (account == "nineth") {
setAnswers((previous) => ({
...previous,
nineth: answer,
}));
} else if (account == "tenth") {
setAnswers((previous) => ({
...previous,
tenth: answer,
}));
} else if (account == "eleventh") {
setAnswers((previous) => ({
...previous,
eleventh: answer,
}));
} else if (account == "twelfth") {
setAnswers((previous) => ({
...previous,
twelfth: answer,
}));
} else if (account == "thirteenth") {
setAnswers((previous) => ({
...previous,
thirteenth: answer,
}));
}
};
const submitHandler = (event) => {
const submitHandler = async (event) => {
event.preventDefault();
console.log(answers);
const result = await PsychTestAddResult.addById(1, answers); // 1 - это id пользователя
console.log(result);
navigate("/");
};
return (
@ -52,6 +117,56 @@ const PsychTest = () => {
account="third"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 4"
account="fourth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 5"
account="fifth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 6"
account="sixth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 7"
account="seventh"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 8"
account="eighth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 9"
account="nineth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 10"
account="tenth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 11"
account="eleventh"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 12"
account="twelfth"
onChangeAnswer={answerChangeHandler}
/>
<PsychTestQuestion
name="Название вопроса 13"
account="thirteenth"
onChangeAnswer={answerChangeHandler}
/>
<button type="submit">Отправить</button>
</form>
</div>

View File

@ -994,7 +994,6 @@
integrity sha512-x/rqGMdzj+fWZvCOYForTghzbtqPDZ5gPwaoNGHdgDfF2QA/XZbCBp4Moo5scrkAMPhB7z26XM/AaHuIJdgauA==
"@babel/runtime@^7.12.5", "@babel/runtime@^7.21.0", "@babel/runtime@^7.5.5", "@babel/runtime@^7.6.3", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7", "@babel/runtime@^7.9.2":
version "7.21.5"
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.21.5.tgz#8492dddda9644ae3bda3b45eabe87382caee7200"
integrity sha512-8jI69toZqqcsnqGGqwGS4Qb1VwLOEp4hz+CXPywcvjs60u3B4Pom/U/7rm4W8tMOYEB+E9wgD0mW1l3r8qlI9Q==
@ -1443,7 +1442,6 @@
"@types/react" "*"
"@types/react@*", "@types/react@>=16.9.11":
version "18.2.6"
resolved "https://registry.yarnpkg.com/@types/react/-/react-18.2.6.tgz#5cd53ee0d30ffc193b159d3516c8c8ad2f19d571"
integrity sha512-wRZClXn//zxCFW+ye/D2qY65UsYP1Fpex2YXorHc8awoNamkMZSvBxwxdYVInsHOZZd2Ppq8isnSzJL5Mpf8OA==
@ -1756,7 +1754,6 @@ ci-info@^3.2.0:
resolved "https://registry.yarnpkg.com/ci-info/-/ci-info-3.8.0.tgz#81408265a5380c929f0bc665d62256628ce9ef91"
integrity sha512-eXTggHWSooYhq49F2opQhuHWgzucfF2YgODK4e1566GQs5BIfP30B0oenwBJHfWxAs2fyPB1s7Mg949zLf61Yw==
classnames@^2.3.2:
version "2.3.2"
resolved "https://registry.yarnpkg.com/classnames/-/classnames-2.3.2.tgz#351d813bf0137fcc6a76a16b88208d2560a0d924"
@ -3122,7 +3119,6 @@ pretty-format@^29.0.0, pretty-format@^29.5.0:
ansi-styles "^5.0.0"
react-is "^18.0.0"
prop-types-extra@^1.1.0:
version "1.1.1"
resolved "https://registry.yarnpkg.com/prop-types-extra/-/prop-types-extra-1.1.1.tgz#58c3b74cbfbb95d304625975aa2f0848329a010b"
@ -3132,7 +3128,6 @@ prop-types-extra@^1.1.0:
warning "^4.0.0"
prop-types@^15.6.2, prop-types@^15.8.1:
version "15.8.1"
resolved "https://registry.yarnpkg.com/prop-types/-/prop-types-15.8.1.tgz#67d87bf1a694f48435cf332c24af10214a3140b5"
integrity sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==