From e53024c9bc399cdd10f4921947f654d394f5caea Mon Sep 17 00:00:00 2001 From: caoqianming Date: Fri, 21 Jan 2022 16:13:32 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BA=BA=E8=84=B8=E8=AF=86=E5=88=AB=E6=95=B0?= =?UTF-8?q?=E6=8D=AE=E7=94=A8=E7=BC=93=E5=AD=98=E5=A4=84=E7=90=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hb_server/apps/hrm/services.py | 29 ++++++++++++++-------- hb_server/apps/hrm/signals.py | 6 ++++- hb_server/apps/hrm/tasks.py | 27 +++++++++++++++++++-- hb_server/apps/hrm/views.py | 44 ++++++++++++++-------------------- hb_server/server/settings.py | 4 ++-- 5 files changed, 69 insertions(+), 41 deletions(-) diff --git a/hb_server/apps/hrm/services.py b/hb_server/apps/hrm/services.py index a80cb8e..8cfb277 100644 --- a/hb_server/apps/hrm/services.py +++ b/hb_server/apps/hrm/services.py @@ -3,7 +3,9 @@ import uuid import face_recognition import os from apps.hrm.models import Employee +from apps.hrm.tasks import update_all_user_facedata_cache from apps.system.models import User +from django.core.cache import cache class HRMService: @@ -22,18 +24,25 @@ class HRMService: return None, '头像解码失败' # 匹配人脸库 - user_faces = Employee.objects.filter(face_data__isnull=False, - user__is_active=True).values('user', 'face_data') - user_l = [] - face_l = [] - for i in user_faces: - user_l.append(i['user']) - face_l.append(i['face_data']) + face_datas = cache.get('face_datas') + face_users = cache.get('face_users') + if face_datas is None: + update_all_user_facedata_cache() - results = face_recognition.compare_faces(face_l, unknown_face_encoding, tolerance=0.5) + results = face_recognition.compare_faces(face_datas, unknown_face_encoding, tolerance=0.5) for index, value in enumerate(results): if value: # 识别成功 - user = User.objects.get(id=user_l[index]) + user = User.objects.get(id=face_users[index]) return user, '' - return None, '识别失败' \ No newline at end of file + return None, '识别失败' + + def get_facedata_from_img(cls, img_rpath): + try: + photo_path = settings.BASE_DIR + img_rpath + picture_of_me = face_recognition.load_image_file(photo_path) + my_face_encoding = face_recognition.face_encodings(picture_of_me)[0] + face_data_list = my_face_encoding.tolist() + return face_data_list + except: + return None \ No newline at end of file diff --git a/hb_server/apps/hrm/signals.py b/hb_server/apps/hrm/signals.py index a2a7312..7e8c922 100644 --- a/hb_server/apps/hrm/signals.py +++ b/hb_server/apps/hrm/signals.py @@ -2,8 +2,12 @@ from django.db.models.signals import post_save from apps.system.models import User from django.dispatch import receiver from apps.hrm.models import Employee +from django.conf import settings +import face_recognition +import logging +logger = logging.getLogger('log') @receiver(post_save, sender=User) def createEmployee(sender, instance, created, **kwargs): if created: - Employee.objects.get_or_create(user=instance) \ No newline at end of file + Employee.objects.get_or_create(user=instance) diff --git a/hb_server/apps/hrm/tasks.py b/hb_server/apps/hrm/tasks.py index bd4449b..d5d5a9f 100644 --- a/hb_server/apps/hrm/tasks.py +++ b/hb_server/apps/hrm/tasks.py @@ -1,8 +1,31 @@ from __future__ import absolute_import, unicode_literals from celery import shared_task +from apps.hrm.models import Employee +from apps.system.models import User +from django.core.cache import cache @shared_task -def x(): - print('ok') \ No newline at end of file +def update_all_user_not_atwork(): + """ + 将所有员工设为非在岗状态 + """ + User.objects.all().update(is_atwork=False) + +@shared_task +def update_all_user_facedata_cache(): + """ + 更新人脸数据缓存 + """ + facedata_queyset = Employee.objects.filter(face_data__isnull=False, + user__is_active=True).values('user', 'face_data') + face_users = [] + face_datas = [] + for i in facedata_queyset: + face_users.append(i['user']) + face_datas.append(i['face_data']) + cache.set('face_users', face_users, timeout=None) + cache.set('face_datas', face_datas, timeout=None) + + \ No newline at end of file diff --git a/hb_server/apps/hrm/views.py b/hb_server/apps/hrm/views.py index 9c533d0..e41ee48 100644 --- a/hb_server/apps/hrm/views.py +++ b/hb_server/apps/hrm/views.py @@ -8,10 +8,9 @@ from apps.hrm.services import HRMService from apps.system.mixins import CreateUpdateModelAMixin, OptimizationMixin from apps.hrm.models import ClockRecord, Employee from apps.hrm.serializers import ClockRecordListSerializer, EmployeeSerializer, FaceClockCreateSerializer, FaceLoginSerializer -import face_recognition -from django.conf import settings -from django.core.cache import cache -import logging + + + from rest_framework.generics import CreateAPIView from rest_framework import status from rest_framework_simplejwt.tokens import RefreshToken @@ -19,20 +18,8 @@ from rest_framework import exceptions from apps.system.models import User from apps.system.serializers import UserSimpleSerializer from rest_framework.permissions import AllowAny -logger = logging.getLogger('log') -def load_face_data(username:int, path:str): - """ - 将某用户face_encoding加载进缓存 - """ - face_datas = cache.get_or_set('face_datas', {}, timeout=None) - photo_path = settings.BASE_DIR + path - picture_of_me = face_recognition.load_image_file(photo_path) - my_face_encoding = face_recognition.face_encodings(picture_of_me)[0] - face_datas[username] = my_face_encoding - cache.set('face_datas', face_datas, timeout=None) - return my_face_encoding # Create your views here. class EmployeeViewSet(CreateUpdateModelAMixin, OptimizationMixin, UpdateModelMixin, RetrieveModelMixin, GenericViewSet): @@ -44,16 +31,21 @@ class EmployeeViewSet(CreateUpdateModelAMixin, OptimizationMixin, UpdateModelMix serializer_class = EmployeeSerializer ordering = ['-pk'] - def perform_update(self, serializer): - instance = serializer.save(update_by = self.request.user) - try: - photo_path = settings.BASE_DIR + instance.photo - picture_of_me = face_recognition.load_image_file(photo_path) - my_face_encoding = face_recognition.face_encodings(picture_of_me)[0] - instance.face_data = my_face_encoding.tolist() - instance.save() - except: - logger.error('人脸识别出错') + def update(self, request, *args, **kwargs): + partial = kwargs.pop('partial', False) + instance = self.get_object() + data = request.data + serializer = self.get_serializer(instance, data=data, partial=partial) + serializer.is_valid(raise_exception=True) + photo = data.get('photo', None) + if instance.photo != photo: + f_l = HRMService.get_facedata_from_img(photo) + if f_l: + serializer.save(update_by=request.user, face_data = f_l) + return Response() + return Response('头像识别失败', status=status.HTTP_400_BAD_REQUEST) + serializer.save(update_by=request.user) + return Response() class ClockRecordViewSet(CreateModelMixin, ListModelMixin, GenericViewSet): diff --git a/hb_server/server/settings.py b/hb_server/server/settings.py index cc780f3..5cf9d99 100644 --- a/hb_server/server/settings.py +++ b/hb_server/server/settings.py @@ -194,7 +194,7 @@ AUTHENTICATION_BACKENDS = ( # CACHES = { # "default": { # "BACKEND": "django_redis.cache.RedisCache", -# "LOCATION": "redis://redis:6379/1", +# "LOCATION": "redis://127.0.0.1:6379/0", # "OPTIONS": { # "CLIENT_CLASS": "django_redis.client.DefaultClient", # "PICKLE_VERSION": -1 @@ -203,7 +203,7 @@ AUTHENTICATION_BACKENDS = ( # } # celery配置,celery正常运行必须安装redis -CELERY_BROKER_URL = "redis://redis:6379/0" # 任务存储 +CELERY_BROKER_URL = "redis://127.0.0.1:6379/1" # 任务存储 CELERYD_MAX_TASKS_PER_CHILD = 100 # 每个worker最多执行300个任务就会被销毁,可防止内存泄露 CELERY_TIMEZONE = 'Asia/Shanghai' # 设置时区 CELERY_ENABLE_UTC = True # 启动时区设置