Обновить utils/clients.py
This commit is contained in:
parent
bf84ee2820
commit
8d0cfdbe17
169
utils/clients.py
169
utils/clients.py
|
@ -12,6 +12,8 @@ from sqlalchemy import select, and_
|
|||
from sqlalchemy.exc import IntegrityError
|
||||
from model.database import Client, AppliedJob, Job
|
||||
|
||||
from sqlalchemy import func, or_
|
||||
import urllib.parse
|
||||
from dotenv import load_dotenv
|
||||
import os
|
||||
|
||||
|
@ -23,53 +25,75 @@ url_up = os.getenv('UP_DOMEN')
|
|||
|
||||
|
||||
|
||||
|
||||
async def get_filtered_jobs(db: AsyncSession, user_job_titles, minimum_annual_salary, salary_currency,
|
||||
user_location_type, user_locations, user_levels, user_job_types): #
|
||||
# Строим фильтры для каждого из параметров пользователя
|
||||
filters = []
|
||||
user_location_type, user_locations, user_levels, user_job_types):
|
||||
title_filters = []
|
||||
location_filters = []
|
||||
|
||||
# Фильтрация по job_title (примерное совпадение)
|
||||
# Очистка и нормализация входных данных
|
||||
def clean_text(text):
|
||||
return urllib.parse.unquote(text).strip().lower()
|
||||
|
||||
# 2. Фильтр по должностям (OR-группа)
|
||||
if user_job_titles:
|
||||
title_filters = [Job.job_title.ilike(f"%{title}%") for title in user_job_titles]
|
||||
filters.append(or_(*title_filters))
|
||||
seen_titles = set() # Для избежания дубликатов
|
||||
for title in user_job_titles:
|
||||
clean_title = clean_text(title)
|
||||
if clean_title in seen_titles:
|
||||
continue
|
||||
seen_titles.add(clean_title)
|
||||
|
||||
# Фильтрация по minimum_annual_salary (если указано)
|
||||
if minimum_annual_salary is not None:
|
||||
filters.append(Job.minimum_annual_salary >= minimum_annual_salary)
|
||||
words = clean_title.split()
|
||||
if len(words) > 1:
|
||||
# Для составных названий ищем все слова через AND
|
||||
word_filters = [func.lower(Job.job_title).contains(word) for word in words]
|
||||
title_filters.append(and_(*word_filters))
|
||||
else:
|
||||
title_filters.append(func.lower(Job.job_title).contains(clean_title))
|
||||
|
||||
# Фильтрация по salary_currency (если указано)
|
||||
if salary_currency is not None:
|
||||
filters.append(Job.salary_currency == salary_currency)
|
||||
|
||||
# Фильтрация по location_type (если указано)
|
||||
if user_location_type:
|
||||
filters.append(Job.location_type == user_location_type)
|
||||
|
||||
# Фильтрация по location (разделяем по каждому городу)
|
||||
# 3. Фильтр по локациям (OR-группа)
|
||||
if user_locations:
|
||||
location_filters = [Job.location.ilike(location) for location in user_locations]
|
||||
filters.append(or_(*location_filters))
|
||||
seen_locations = set()
|
||||
for location in user_locations:
|
||||
clean_loc = clean_text(location)
|
||||
if clean_loc in seen_locations:
|
||||
continue
|
||||
seen_locations.add(clean_loc)
|
||||
|
||||
# Фильтрация по job_level (если указаны)
|
||||
if user_levels:
|
||||
filters.append(Job.job_level.in_(user_levels))
|
||||
location_filters.append(func.lower(Job.location).contains(clean_loc))
|
||||
|
||||
# Фильтрация по job_type (если указаны)
|
||||
if user_job_types:
|
||||
filters.append(Job.job_type.in_(user_job_types))
|
||||
# Обработка составных локаций (City, Country)
|
||||
if ',' in clean_loc:
|
||||
main_part = clean_loc.split(',')[0].strip()
|
||||
location_filters.append(func.lower(Job.location).contains(main_part))
|
||||
|
||||
# Выполняем запрос с применением всех фильтров
|
||||
query = select(Job).filter(*filters)
|
||||
# 4. Комбинирование фильтров
|
||||
final_filters = []
|
||||
if title_filters:
|
||||
final_filters.append(or_(*title_filters))
|
||||
if location_filters:
|
||||
final_filters.append(or_(*location_filters))
|
||||
|
||||
if not final_filters:
|
||||
return []
|
||||
|
||||
# 5. Формирование и выполнение запроса
|
||||
query = select(Job).filter(*final_filters)
|
||||
|
||||
# Для отладки
|
||||
print("Final query:", str(query))
|
||||
|
||||
# Выполняем асинхронный запрос
|
||||
result = await db.execute(query)
|
||||
|
||||
# Получаем все результаты
|
||||
jobs = result.scalars().all()
|
||||
|
||||
print(f"Found {len(jobs)} matching jobs")
|
||||
for job in jobs:
|
||||
print(f"Match: {job.job_title} | {job.location}")
|
||||
|
||||
return jobs
|
||||
|
||||
|
||||
|
||||
async def upsert_client(db: AsyncSession, user_id: str, user_login: str, user_nicename: str, user_email: str, phone: str, json_data: str):
|
||||
# Проверяем, существует ли клиент с таким логином или email
|
||||
async with db.begin():
|
||||
|
@ -153,17 +177,53 @@ async def del_jobs(db: AsyncSession, user_id: str):
|
|||
# return {"message": f"{len(applied_jobs)} вакансий добавлено в AppliedJob"}
|
||||
|
||||
|
||||
async def add_jobs(db: AsyncSession, user_id: str):
|
||||
# Получаем все активные вакансии (предполагаю, что ты хотел использовать True, а не 3)
|
||||
query = select(Job).where(Job.active == 3)
|
||||
result = await db.execute(query)
|
||||
jobs = result.scalars().all()
|
||||
async def add_jobs(db: AsyncSession, user_id: str, up):
|
||||
print(up)
|
||||
|
||||
try:
|
||||
user_data = up
|
||||
print(type(user_data))
|
||||
job_preferences = user_data.get('job_preferences', {})
|
||||
|
||||
job_titles = job_preferences.get('job_titles', [])
|
||||
locations = job_preferences.get('locations', [])
|
||||
|
||||
location_types = [k for k, v in job_preferences.get('location_types', {}).items() if v is True]
|
||||
job_levels = [k for k, v in job_preferences.get('job_levels', {}).items() if v is True]
|
||||
job_types = [k for k, v in job_preferences.get('job_types', {}).items() if v is True]
|
||||
|
||||
print("Job Titles:", job_titles)
|
||||
print("Locations:", locations)
|
||||
print("Location Types (True only):", location_types)
|
||||
print("Job Levels (True only):", job_levels)
|
||||
print("Job Types (True only):", job_types)
|
||||
|
||||
except json.JSONDecodeError as e:
|
||||
print("Ошибка декодирования JSON:", e)
|
||||
|
||||
jobs = await get_filtered_jobs(
|
||||
db,
|
||||
user_job_titles=job_titles,
|
||||
minimum_annual_salary=None,
|
||||
salary_currency=None,
|
||||
user_location_type=None,
|
||||
user_locations=locations,
|
||||
user_levels=None,
|
||||
user_job_types=None
|
||||
)
|
||||
|
||||
for job in jobs:
|
||||
print(job.job_title, job.location, job.job_level, job.job_type)
|
||||
# # Получаем все активные вакансии (предполагаю, что ты хотел использовать True, а не 3)
|
||||
# # query = select(Job).where(Job.active == 3)
|
||||
# # result = await db.execute(query)
|
||||
# # jobs = result.scalars().all()
|
||||
|
||||
if not jobs:
|
||||
return {"message": "Нет вакансий по данному фильтру"}
|
||||
|
||||
applied_jobs = []
|
||||
scheduled_count = 0
|
||||
added_count = 0
|
||||
|
||||
for job in jobs:
|
||||
# Проверяем, существует ли уже такая пара client_id + job_id
|
||||
|
@ -177,18 +237,21 @@ async def add_jobs(db: AsyncSession, user_id: str):
|
|||
existing = check_result.scalar_one_or_none()
|
||||
|
||||
if not existing:
|
||||
# Первые 5 добавим со статусом Scheduled, остальные Backlogged
|
||||
status = "Scheduled" if scheduled_count < 5 else "Backlogged"
|
||||
applied_jobs.append(
|
||||
AppliedJob(client_id=user_id, job_id=job.job_id, status=status)
|
||||
new_applied = AppliedJob(
|
||||
client_id=user_id,
|
||||
job_id=job.job_id,
|
||||
status=status
|
||||
)
|
||||
if status == "Scheduled":
|
||||
scheduled_count += 1
|
||||
db.add(new_applied)
|
||||
await db.commit() # коммитим каждую запись сразу
|
||||
scheduled_count += 1 if status == "Scheduled" else 0
|
||||
added_count += 1
|
||||
|
||||
if applied_jobs:
|
||||
db.add_all(applied_jobs)
|
||||
await db.commit()
|
||||
return {"message": f"{len(applied_jobs)} вакансий добавлено в AppliedJob (Scheduled: {scheduled_count})"}
|
||||
if added_count > 0:
|
||||
return {
|
||||
"message": f"{added_count} вакансий добавлено в AppliedJob (Scheduled: {scheduled_count}, Backlogged: {added_count - scheduled_count})"
|
||||
}
|
||||
else:
|
||||
return {"message": "Все вакансии уже были добавлены ранее"}
|
||||
|
||||
|
@ -323,8 +386,9 @@ async def get_delite(db, data):
|
|||
|
||||
async def get_update(db: AsyncSession, data: update):
|
||||
user_id = data.user_id
|
||||
print(data)
|
||||
up_client = requests.get(f"{url_up}{user_id}") # Лучше заменить на httpx.AsyncClient
|
||||
|
||||
print("22222")
|
||||
if up_client.status_code == 200:
|
||||
datas = up_client.json()
|
||||
|
||||
|
@ -353,7 +417,7 @@ async def get_update(db: AsyncSession, data: update):
|
|||
email_addr = data_dict['email_addr']
|
||||
user_id = data_dict['user_id']
|
||||
phone_num = data_dict['phone_num']
|
||||
print(data_dict)
|
||||
# print(data_dict)
|
||||
|
||||
# Обновляем или создаём клиента
|
||||
async with db.begin():
|
||||
|
@ -387,3 +451,10 @@ async def get_update(db: AsyncSession, data: update):
|
|||
|
||||
|
||||
|
||||
|
||||
|
||||
async def get_users(db: AsyncSession, data: update):
|
||||
user_id = data.user_id
|
||||
client = await db.get(Client, user_id)
|
||||
return
|
||||
print(client.json_data)
|
Loading…
Reference in New Issue