From 75b1fecb536983465a8cad21ac32cdb740c35233 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C3=80=C3=AE=C3=97=C3=9A=C3=95=C3=B1?= Date: Tue, 26 Jul 2022 19:17:55 +0800 Subject: [PATCH] =?UTF-8?q?=E5=B9=B4=E5=BA=A6=E8=B6=8B=E5=8A=BF?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- api/api_v1/endpoints/forms.py | 64 ++++++++++++- models/interview_zsgc.py | 46 ++++++++++ utils/func.py | 15 ++++ 接口文档/年度趋势接口文档.txt | 163 ++++++++++++++++++++++++++++++++++ 4 files changed, 287 insertions(+), 1 deletion(-) create mode 100644 接口文档/年度趋势接口文档.txt diff --git a/api/api_v1/endpoints/forms.py b/api/api_v1/endpoints/forms.py index be35c95..c11bfb5 100644 --- a/api/api_v1/endpoints/forms.py +++ b/api/api_v1/endpoints/forms.py @@ -8,7 +8,7 @@ from motor.motor_asyncio import AsyncIOMotorDatabase from utils.dingding import get_redis_alluid, send_dates from utils.jianli import get_resume -from utils.func import get_every_days +from utils.func import get_every_days, get_every_months import crud, schemas from datetime import datetime from core.configuration import * @@ -724,3 +724,65 @@ async def interview_trend_form( res_msg[chk_date]['创建面试的申请数'] += 1 * count_num return schemas.Msg(code=200, msg='ok', data=res_msg) + + +# 年度招聘趋势报表 +@router.post("/year_trend_form") +async def year_trend_form( + request: Request, + interview: InterviewDo = Depends(InterviewDo), + ck_db: CKDrive = Depends(get_ck_db) +) -> schemas.Msg: + """ 招聘趋势分析报表 """ + await interview.init() + res = interview.get_year_form_sql() + sql = res['sql'] + data = await ck_db.execute(sql) + if not data: + return schemas.Msg(code=-9, msg='无数据', data=None) + sdate = res['sdate'] + edate = res['edate'] + months = get_every_months(sdate, edate) + res_msg = {} + for i in months: + res_msg[str(i)] = { + '简历推荐数': 0, + '有效简历数': 0, + '到场面试数': 0, + '面试通过': 0, + 'offer发出数': 0, + '入职人数': 0, + '转正人数': 0, + '离职人数': 0, + '主动离职': 0, + '被动离职': 0 + } + + for chk_data in data.values(): + chk_date = datetime.strftime(chk_data['date'], '%Y-%m') + if chk_date not in res_msg: + continue + chk_stage = chk_data['interview_stage'] + count_num = chk_data['value'] + if chk_stage >= 1: + res_msg[chk_date]['简历推荐数'] += 1 * count_num + if chk_stage >= 2: + res_msg[chk_date]['有效简历数'] += 1 * count_num + if chk_stage >= 3: + res_msg[chk_date]['到场面试数'] += 1 * count_num + if chk_stage >= 4: + res_msg[chk_date]['面试通过'] += 1 * count_num + if chk_stage >= 5: + res_msg[chk_date]['offer发出数'] += 1 * count_num + if chk_stage >= 7: + res_msg[chk_date]['入职人数'] += 1 * count_num + if chk_stage >= 8: + res_msg[chk_date]['转正人数'] += 1 * count_num + if chk_stage >= 9: + res_msg[chk_date]['离职人数'] += 1 * count_num + res_msg[chk_date]['主动离职'] += 1 * count_num + if chk_stage >= 10: + res_msg[chk_date]['离职人数'] += 1 * count_num + res_msg[chk_date]['被动离职'] += 1 * count_num + + return schemas.Msg(code=200, msg='ok', data=res_msg) diff --git a/models/interview_zsgc.py b/models/interview_zsgc.py index 8d79012..f28595d 100644 --- a/models/interview_zsgc.py +++ b/models/interview_zsgc.py @@ -677,6 +677,52 @@ class InterviewDo: 'sql': sql } + # 年度招聘数据sql + def get_year_form_sql(self): + whereStr = '' + is_date = 0 + if self.where: + for key, value in self.where.items(): + if key in ['start_time', 'end_time']: + is_date = 1 + continue + if isinstance(value, str): + whereStr += str(key) + ' = ' + "'" + value + "'" + ' ' + continue + whereStr += str(key) + ' = ' + str(value) + ' ' + whereStr = whereStr.strip() + + # 有日期条件 + start_time = self.where.get('start_time', '') + end_time = self.where.get('end_time', '') + if is_date: + if whereStr: + sql = f"select toStartOfMonth(addHours(`event_time`, 0)) as date,interview_stage, count() as value from HR.resumes where {whereStr}" + else: + sql = f"select toStartOfMonth(addHours(`event_time`, 0)) as date,interview_stage, count() as value from HR.resumes" + if start_time or end_time: + sql += f" where" + if start_time: + if whereStr: + sql += f" and date >= '{start_time}'" + else: + sql += f" date >= '{start_time}'" + if end_time: + sql += f" and date <= '{end_time}'" + # 没有日期条件 + else: + if whereStr: + sql = f"select toStartOfMonth(addHours(`event_time`, 0)) as date,interview_stage, count() as value from HR.resumes where {whereStr}" + else: + sql = f"select toStartOfMonth(addHours(`event_time`, 0)) as date,interview_stage, count() as value from HR.resumes" + sql += f" group by date, interview_stage" + print(sql) + return { + 'sql': sql, + 'sdate': start_time, + 'edate': end_time, + } + if __name__ == '__main__': col = 'max_interview_stage' diff --git a/utils/func.py b/utils/func.py index 2bc6b2b..a117add 100644 --- a/utils/func.py +++ b/utils/func.py @@ -294,3 +294,18 @@ def get_every_days(sdate, edate): true_day = datetime.datetime.strftime(day, '%Y-%m-%d') days.append(true_day) return days + + +# 获取两个日期之间的所有月份 +def get_every_months(sdate, edate): + start_date = datetime.datetime.strptime(sdate, '%Y-%m-%d') + end_date = datetime.datetime.strptime(edate, '%Y-%m-%d') + months = (start_date.year - end_date.year) * 12 + end_date.month - start_date.month + month_range = ['%04d-%02d' % (int(start_date.year + mon // 12), int(mon % 12 + 1)) + for mon in range(start_date.month - 1, start_date.month + months)] + + return month_range + + +if __name__ == '__main__': + get_every_months('2022-01-01', '2022-12-31') diff --git a/接口文档/年度趋势接口文档.txt b/接口文档/年度趋势接口文档.txt new file mode 100644 index 0000000..bb7e98a --- /dev/null +++ b/接口文档/年度趋势接口文档.txt @@ -0,0 +1,163 @@ +·: /api/v1/forms/year_trend_form + +: +{ + "data_in": "string", # Ϊ"" + "interview_query": {"start_time":"2022-01-01", "end_time":"2022-12-31"}, # ʱ ʽ -- ַ + "find_column": [ + "string" # Ϊ [] + ] +} + + +ֵ: +{ + "code": 200, + "msg": "ok", + "data": { + "2022-01": { # ·ݶӦ + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-02": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-03": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-04": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-05": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-06": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-07": { + "Ƽ": 23, + "Ч": 23, + "": 23, + "ͨ": 23, + "offer": 23, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-08": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-09": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-10": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-11": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + }, + "2022-12": { + "Ƽ": 0, + "Ч": 0, + "": 0, + "ͨ": 0, + "offer": 0, + "ְ": 0, + "ת": 0, + "ְ": 0, + "ְ": 0, + "ְ": 0 + } + } +} \ No newline at end of file