from django.db import transaction from rest_framework.decorators import action from rest_framework.exceptions import ParseError from rest_framework.response import Response from rest_framework.serializers import Serializer from apps.utils.serializers import PkSerializer from apps.utils.viewsets import CustomModelViewSet from .filters import MtaskFilter, UtaskFilter from .models import Mtask, Utask, Mtaskb from .serializers import (MtaskSerializer, SchedueSerializer, UtaskSerializer, MtaskDaySerializer, MtaskAddInfoSerializer, SchedueMtasksSerializer, MtaskbSerializer, MtaskbUpdateSerializer, MtaskbAddSerializer) from .services import PmService from django.utils import timezone # Create your views here. class UtaskViewSet(CustomModelViewSet): """ list: 生产大任务 生产大任务 """ queryset = Utask.objects.all() serializer_class = UtaskSerializer filterset_class = UtaskFilter select_related_fields = ['material'] ordering_fields = ['priority', 'start_date'] ordering = ["priority", '-start_date'] def perform_destroy(self, instance): if instance.state >= Utask.UTASK_WORKING: raise ParseError('该任务状态不可删除') return super().perform_destroy(instance) @action(methods=['post'], detail=True, perms_map={'post': 'utask.submit'}, serializer_class=Serializer) @transaction.atomic def submit(self, request, *args, **kwargs): """提交任务 提交任务 """ obj = self.get_object() PmService.utask_submit(obj) return Response() @action(methods=['post'], detail=True, perms_map={'post': 'utask.toggle'}, serializer_class=Serializer) @transaction.atomic def toggle(self, request, *args, **kwargs): """停止/恢复任务 停止/恢复任务 """ obj = self.get_object() user = request.user now = timezone.now() if obj.state == Utask.UTASK_WORKING: obj.state = Utask.UTASK_STOP obj.update_by = user obj.update_time = now obj.save() # 停止所有小任务 Mtask.objects.filter( utask=obj, state=Mtask.MTASK_ASSGINED).update(state=Mtask.MTASK_STOP, update_by=user, update_time=now) elif obj.state == Utask.UTASK_STOP: obj.state = Utask.UTASK_WORKING obj.update_by = user obj.update_time = now obj.save() # 恢复所有小任务 Mtask.objects.filter( utask=obj, state=Mtask.MTASK_STOP).update(state=Mtask.MTASK_ASSGINED, update_by=user, update_time=now) else: raise ParseError('该状态下不可变更') return Response() @action(methods=['post'], detail=False, perms_map={'post': 'utask.schedue'}, serializer_class=SchedueSerializer) @transaction.atomic def schedue_utasks(self, request, *args, **kwargs): """从多个订单明细生成大任务 从多个订单明细生成大任务 """ sr = SchedueSerializer(data=request.data) sr.is_valid(raise_exception=True) vdata = sr.validated_data PmService.make_utasks_from_orderitems(request.user, request.data['orderitems'], vdata['start_date'], vdata['end_date'], vdata.get('belong_dept', None)) return Response() @action(methods=['post'], detail=False, perms_map={'post': 'utask.schedue'}, serializer_class=SchedueMtasksSerializer) @transaction.atomic def schedue_mtasks(self, request, *args, **kwargs): """任务分解(支持分解到天或仅仅到工段) 任务分解 """ sr = SchedueMtasksSerializer(data=request.data) sr.is_valid(raise_exception=True) vdata = sr.validated_data utasks = Utask.objects.filter( id__in=vdata['ids'], state=Utask.UTASK_CREATED) for i in utasks: PmService.schedue_mtasks(request.user, i, vdata.get("schedule_type", "to_day")) return Response() @action(methods=['post'], detail=False, perms_map={'post': 'utask.assgin'}, serializer_class=PkSerializer) @transaction.atomic def assgin(self, request, *args, **kwargs): """下达任务 下达任务 """ ids = request.data.get('ids', []) user = request.user now = timezone.now() utasks = Utask.objects.filter( id__in=ids, state=Utask.UTASK_DECOMPOSE) # 已分解的任务 Mtask.objects.filter(utask__in=utasks, state=Mtask.MTASK_CREATED).update( state=Mtask.MTASK_ASSGINED, update_by=user, update_time=now) utasks.update( state=Utask.UTASK_ASSGINED, update_by=user, update_time=now) # 此处要更新订单状态 from apps.sam.models import OrderItem, Order orderIds = OrderItem.objects.filter( utask__in=utasks).values_list('order', flat=True).distinct() Order.objects.filter(id__in=orderIds, state=Order.ORDER_SUBMITED).update( state=Order.ORDER_DOING) return Response() class MtaskViewSet(CustomModelViewSet): """ list: 生产任务 生产任务 """ queryset = Mtask.objects.all() serializer_class = MtaskSerializer filterset_class = MtaskFilter select_related_fields = ['material_in', 'material_out', 'mgroup'] prefetch_related_fields = ['mlog_mtask', 'b_mtask'] ordering_fields = ["utask__priority", 'start_date', 'mgroup__process__sort', 'create_time'] ordering = ["utask__priority", '-start_date', 'route__sort', 'mgroup__process__sort', '-create_time'] @action(methods=['post'], detail=False, perms_map={'post': '*'}, serializer_class=MtaskDaySerializer) @transaction.atomic def day(self, request): """获取指定车间指定日期的代表工序生产任务 获取指定车间指定日期的代表工序生产任务 """ sr = MtaskDaySerializer(data=request.data) sr.is_valid(raise_exception=True) vdata = sr.validated_data mtasks = Mtask.objects.filter( is_count_utask=True, mgroup__belong_dept__name=vdata['belong_dept_name'], start_date__lte=vdata['date'], end_date__gte=vdata['date']).order_by( 'utask', 'mgroup__process__sort', 'create_time' ) data = MtaskSerializer(instance=mtasks, many=True).data return Response(data) @action(methods=['get'], detail=True, perms_map={'get': '*'}) @transaction.atomic def related(self, request, *args, **kwargs): """获取已下达的所有的兄弟小任务 获取已下达的所有的兄弟小任务 """ obj = self.get_object() rdata = MtaskSerializer(instance=obj.related, many=True).data return Response(rdata) def perform_destroy(self, instance): if instance.state != Mtask.MTASK_CREATED: raise ParseError('该任务非创建中不可删除') return super().perform_destroy(instance) @action(methods=['post'], detail=True, perms_map={'post': 'mtask.submit'}, serializer_class=PkSerializer) @transaction.atomic def submit(self, request, *args, **kwargs): """提交任务(根据任务ID) 提交任务后不可更新日志 """ mtask: Mtask = self.get_object() user = request.user PmService.mtask_submit(mtask, user) return Response() @action(methods=['post'], detail=True, perms_map={'post': 'mtask.submit'}, serializer_class=Serializer) @transaction.atomic def submit_related_same_day(self, request, *args, **kwargs): """提交同一天该部门下大任务的所有兄弟小任务 提交同一天的该部门下大任务的所有兄弟小任务 """ mtask = self.get_object() mtasks = mtask.related for mtask in mtasks: PmService.mtask_submit(mtask, self.request.user) return Response() @action(methods=['post'], detail=True, perms_map={'post': 'mlog.create'}, serializer_class=MtaskAddInfoSerializer) @transaction.atomic def add_info(self, request, *args, **kwargs): """添加与任务相关的日志信息 添加与任务相关的日志信息 """ obj = self.get_object() sr = MtaskAddInfoSerializer(instance=obj, data=request.data) sr.is_valid(raise_exception=True) sr.save() return Response() @action(methods=['post'], detail=True, perms_map={'post': 'mtaskb.create'}, serializer_class=MtaskbAddSerializer) @transaction.atomic def add_mtaskb(self, request, *args, **kwargs): mtask = self.get_object() if mtask.state != Mtask.MTASK_ASSGINED: raise ParseError('该任务不可分配') sr = MtaskbAddSerializer(data=request.data, many=True) sr.is_valid(raise_exception=True) vdata = sr.validated_data total = 0 userIds = [] for v in vdata: total += v['count'] userIds.append(v['handle_user'].id) if total != mtask.count: raise ParseError('任务数量与分配数量不匹配') for v in vdata: mtaskb, _ = Mtaskb.objects.get_or_create(mtask=mtask, handle_user=v['handle_user']) mtaskb.count = v['count'] mtaskb.save() dobjs = Mtaskb.objects.filter(mtask=mtask).exclude(handle_user__in=userIds) from apps.wpm.models import Mlog if Mlog.objects.filter(mtaskb__in=dobjs).exists(): raise ParseError('已存在工作日志,无法修改分配') else: dobjs.delete() return Response() class MtaskbViewSet(CustomModelViewSet): queryset = Mtaskb.objects.all() serializer_class = MtaskbSerializer update_serializer_class = MtaskbUpdateSerializer filterset_fields = {"mtask": ["exact"], "handle_user": ["exact"], "mtask__mgroup": ["exact"]} ordering = ['id']