from datetime import date, timedelta from django.shortcuts import render from idna import valid_contextj from numpy import number from rest_framework import serializers from rest_framework.generics import ListAPIView, CreateAPIView from rest_framework.views import APIView from rest_framework.response import Response from apps.hrm.models import ClockRecord from apps.mtm.models import Process, Step from apps.pm.models import ProductionPlan, SubProductionPlan from apps.srm.serializers import AtWorkCountSerializer, PlanGanttSerializer, ProcessYieldSerializer, ProductCountSerializer, SrmCountSerializer from apps.srm.services import SrmServices from apps.wpm.models import WProduct, WproductFlow from django.db.models import Count, F, Sum # Create your views here. class GanttPlan(ListAPIView): """ 计划-子计划甘特图 """ perms_map = {'get':'*'} serializer_class = PlanGanttSerializer queryset = ProductionPlan.objects.filter(is_deleted=False, is_planed=True).prefetch_related('subplan_plan', 'subplan_plan__process') ordering = ['-id'] class ProductCountView(CreateAPIView): """ 产品数量统计 """ perms_map = {'post':'*'} serializer_class = ProductCountSerializer def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) vdata = serializer.validated_data res = SrmServices.get_product_count(**vdata) return Response(res) class PlanCountView(CreateAPIView): """ 计划数量统计 """ perms_map = {'post':'*'} serializer_class = SrmCountSerializer def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) vdata = serializer.validated_data res = SrmServices.get_plan_count(**vdata) return Response(res) class OrderCountView(CreateAPIView): """ 订单数量统计 """ perms_map = {'post':'*'} serializer_class = SrmCountSerializer def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) vdata = serializer.validated_data res = SrmServices.get_order_count(**vdata) return Response(res) class ProcessNowView(CreateAPIView): """ 工序当前进度 """ perms_map = {'post':'*'} serializer_class = serializers.Serializer def create(self, request, *args, **kwargs): objs = SubProductionPlan.objects.filter(production_plan__state__in =[ProductionPlan.PLAN_STATE_WORKING, ProductionPlan.PLAN_STATE_ASSGINED]).order_by('process__number').values('process', 'process__name').annotate(count_ok=Sum('count_ok'), count=Sum('count'), count_real=Sum('count_real'), count_notok=Sum('count_notok')) return Response(objs) class ProcessYieldView(CreateAPIView): """ 工序成品率统计 """ perms_map = {'post':'*'} serializer_class = ProcessYieldSerializer def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) vdata = serializer.validated_data wpfs = WproductFlow.objects.filter(is_lastlog=True) if vdata.get('datetime_start', None): wpfs = wpfs.filter(update_time__gte = vdata.get('datetime_start')) if vdata.get('datetime_end', None): wpfs = wpfs.filter(update_time__lte = vdata.get('datetime_end')) # 根据产品日志记录进行聚合 count_ok_g = list(wpfs.filter(act_state__in=[WProduct.WPR_ACT_STATE_INM, WProduct.WPR_ACT_STATE_OK, WProduct.WPR_ACT_STATE_SELLED]).values('step__process__id').annotate(count_ok=Count('id'))) count_notok_g = list( ( wpfs.filter(act_state__in=[WProduct.WPR_ACT_STATE_NOTOK, WProduct.WPR_ACT_STATE_SCRAP]).exclude(step__process__id=1) | wpfs.filter(act_state__in=[WProduct.WPR_ACT_STATE_NOTOK, WProduct.WPR_ACT_STATE_SCRAP], step__process__id=1).exclude(number=None) )\ .values('step__process__id', ).annotate(count_notok=Count('id'))) ret = [] process_l = list(Process.objects.filter(is_deleted=False).order_by('number').values('id', 'name')) for i in process_l: ret_item = {'id':i['id'], 'name':i['name'], 'count_ok':0, 'count_notok':0, 'rate':1} for m in count_ok_g: if m['step__process__id'] == ret_item['id']: ret_item['count_ok'] = m['count_ok'] for n in count_notok_g: if n['step__process__id'] == ret_item['id']: ret_item['count_notok'] = n['count_notok'] rate = (ret_item['count_ok']/(ret_item['count_ok']+ret_item['count_notok'])) \ if ret_item['count_ok']+ret_item['count_notok']>0 else 1 ret_item['rate'] = rate ret.append(ret_item) return Response(ret) class AtWorkCountView(CreateAPIView): """ 到岗天数统计 """ perms_map = {'get':'*'} serializer_class = AtWorkCountSerializer def create(self, request, *args, **kwargs): serializer = self.get_serializer(data=request.data) serializer.is_valid(raise_exception=True) vdata = serializer.validated_data from workalendar.asia import China cal = China() count_workday = cal.get_working_days_delta( date(vdata['year'], vdata['month'], 1), (date(vdata['year'], vdata['month'], 1).replace(day=1) + timedelta(days=32)).replace(day=1) - timedelta(days=1) ) ret = ClockRecord.objects.filter( update_time__year = vdata['year'], update_time__month = vdata['month'] ).values( user_id = F('create_by'), number = F('create_by__employee_user__number'), username = F('create_by__username'), name = F('create_by__name'), dept_name = F('create_by__dept__name')).annotate( count = Count('id') ) ret_list = list(ret) for i in ret: i['count_workday'] = count_workday return Response(ret_list)