Merge branch 'master' of http://gitea.xxhhcty.xyz:8080/zcdsj/factory
This commit is contained in:
commit
36df498e08
|
|
@ -2,13 +2,11 @@ from django_filters import rest_framework as filters
|
|||
from apps.mtm.models import Goal, Material, Route, RoutePack
|
||||
from django.db.models.expressions import F
|
||||
from rest_framework.exceptions import ParseError
|
||||
|
||||
from django.db.models import Sum, Q, Value, F, ExpressionWrapper, DecimalField
|
||||
from django.db.models.functions import Coalesce
|
||||
|
||||
class MaterialFilter(filters.FilterSet):
|
||||
tag = filters.CharFilter(method='filter_tag', label="low_inm:库存不足")
|
||||
count__gt = filters.NumberFilter(field_name='count', lookup_expr='gt')
|
||||
count_mb__gt = filters.NumberFilter(field_name='count_mb', lookup_expr='gt')
|
||||
count_wm__gt = filters.NumberFilter(field_name='count_wm', lookup_expr='gt')
|
||||
|
||||
class Meta:
|
||||
model = Material
|
||||
|
|
@ -30,7 +28,7 @@ class MaterialFilter(filters.FilterSet):
|
|||
|
||||
def filter_tag(self, queryset, name, value):
|
||||
if value == 'low_inm':
|
||||
queryset = queryset.exclude(count_safe=None).exclude(count_safe__lte=0).filter(
|
||||
queryset = Material.annotate_count(queryset.exclude(count_safe=None).exclude(count_safe__lte=0)).filter(
|
||||
count__lte=F('count_safe'))
|
||||
return queryset
|
||||
|
||||
|
|
|
|||
|
|
@ -6,6 +6,8 @@ from collections import defaultdict, deque
|
|||
from django.db.models import Q
|
||||
from datetime import datetime, timedelta
|
||||
from django.utils import timezone
|
||||
from django.db.models import Sum, Q, Value, F, ExpressionWrapper, DecimalField
|
||||
from django.db.models.functions import Coalesce
|
||||
|
||||
class Process(CommonBModel):
|
||||
"""
|
||||
|
|
@ -123,6 +125,25 @@ class Material(CommonAModel):
|
|||
def fname(self):
|
||||
return f'{self.name}|{self.specification if self.specification else ""}|{self.model if self.model else ""}|{self.process.name if self.process else ""}'
|
||||
|
||||
@staticmethod
|
||||
def annotate_count(qs):
|
||||
return qs.annotate(
|
||||
count_mb=Coalesce(
|
||||
Sum('mb_m__count', filter=Q(mb_m__state=10, mb_m__count__gt=0)),
|
||||
Value(0),
|
||||
output_field=DecimalField()
|
||||
),
|
||||
count_wm=Coalesce(
|
||||
Sum('wm_m__count', filter=Q(wm_m__state=10, wm_m__count__gt=0)),
|
||||
Value(0),
|
||||
output_field=DecimalField()
|
||||
)
|
||||
).annotate(
|
||||
count=ExpressionWrapper(
|
||||
F('count_wm') + F('count_mb'),
|
||||
output_field=DecimalField()
|
||||
)
|
||||
)
|
||||
|
||||
class Shift(CommonBModel):
|
||||
"""TN:班次
|
||||
|
|
|
|||
|
|
@ -38,13 +38,15 @@ class MaterialSerializer(CustomModelSerializer):
|
|||
count = serializers.SerializerMethodField()
|
||||
|
||||
def get_count_mb(self, obj):
|
||||
return getattr(obj, 'count_mb', 0)
|
||||
return getattr(obj, 'count_mb', None)
|
||||
|
||||
def get_count_wm(self, obj):
|
||||
return getattr(obj, 'count_wm', 0)
|
||||
return getattr(obj, 'count_wm', None)
|
||||
|
||||
def get_count(self, obj):
|
||||
return getattr(obj, 'count_mb', 0) + getattr(obj, 'count_wm', 0)
|
||||
if hasattr(obj, 'count_mb') and hasattr(obj, 'count_wm'):
|
||||
return getattr(obj, 'count_mb', 0) + getattr(obj, 'count_wm', 0)
|
||||
return None
|
||||
|
||||
class Meta:
|
||||
model = Material
|
||||
|
|
|
|||
|
|
@ -44,24 +44,8 @@ class MaterialViewSet(CustomModelViewSet):
|
|||
|
||||
def get_queryset(self):
|
||||
qs = super().get_queryset()
|
||||
if self.action in ["list", "retrieve"]:
|
||||
return qs.annotate(
|
||||
count_mb=Coalesce(
|
||||
Sum('mb_m__count', filter=Q(mb_m__state=10)),
|
||||
Value(0),
|
||||
output_field=DecimalField()
|
||||
),
|
||||
count_wm=Coalesce(
|
||||
Sum('wm_m__count', filter=Q(wm_m__state=10)),
|
||||
Value(0),
|
||||
output_field=DecimalField()
|
||||
)
|
||||
).annotate(
|
||||
count=ExpressionWrapper(
|
||||
F('count_wm') + F('count_mb'),
|
||||
output_field=DecimalField()
|
||||
)
|
||||
)
|
||||
if self.action in ["list", "retrieve"] and self.request.query_params.get('wiith_count', None) == 'yes':
|
||||
return Material.annotate_count(qs)
|
||||
return qs
|
||||
|
||||
def perform_destroy(self, instance):
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
from rest_framework import serializers
|
||||
from apps.utils.serializers import CustomModelSerializer
|
||||
from apps.utils.constants import EXCLUDE_FIELDS_DEPT, EXCLUDE_FIELDS_BASE, EXCLUDE_FIELDS
|
||||
from rest_framework.exceptions import ValidationError
|
||||
from rest_framework.exceptions import ValidationError, ParseError
|
||||
|
||||
from apps.pum.models import Supplier, PuPlan, PuPlanItem, PuOrder, PuOrderItem, SupplierAudit
|
||||
from apps.mtm.serializers import MaterialSerializer, MaterialSimpleSerializer
|
||||
|
|
@ -152,3 +152,9 @@ class SupplierAuditSerializer(CustomModelSerializer):
|
|||
model = SupplierAudit
|
||||
fields = "__all__"
|
||||
read_only_fields = EXCLUDE_FIELDS_BASE + ['ticket']
|
||||
|
||||
def create(self, validated_data):
|
||||
name = validated_data["name"]
|
||||
if Supplier.objects.filter(name=name).exists():
|
||||
raise ParseError('供应商名称已存在')
|
||||
return super().create(validated_data)
|
||||
|
|
@ -12,6 +12,7 @@ from rest_framework.response import Response
|
|||
from django.utils import timezone
|
||||
from apps.pum.services import PumService
|
||||
from apps.wf.mixins import TicketMixin
|
||||
from apps.wf.models import Ticket
|
||||
# Create your views here.
|
||||
|
||||
|
||||
|
|
@ -42,6 +43,13 @@ class SupplierAuditViewSet(TicketMixin, CustomModelViewSet):
|
|||
search_fields = ['name', 'material_name', 'material_cate']
|
||||
workflow_key = "wf_supplieraudit"
|
||||
|
||||
@staticmethod
|
||||
def add_supplier(ticket: Ticket, transition, new_ticket_data: dict):
|
||||
supplieraudit = SupplierAudit.objects.get(ticket=ticket)
|
||||
if Supplier.objects.filter(name=supplieraudit.name).exists():
|
||||
raise ParseError('供应商名称已存在')
|
||||
Supplier.objects.create(name=supplieraudit.name)
|
||||
|
||||
class PuPlanViewSet(CustomModelViewSet):
|
||||
"""
|
||||
list: 采购计划
|
||||
|
|
|
|||
|
|
@ -0,0 +1,19 @@
|
|||
# Generated by Django 3.2.12 on 2025-11-26 01:53
|
||||
|
||||
from django.db import migrations, models
|
||||
import django.db.models.deletion
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('qm', '0054_alter_ptest_val_xj'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='ftestitem',
|
||||
name='ftest',
|
||||
field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='items_ftest', to='qm.ftest', verbose_name='关联检验'),
|
||||
),
|
||||
]
|
||||
|
|
@ -94,7 +94,7 @@ class TicketSimpleSerializer(CustomModelSerializer):
|
|||
|
||||
|
||||
class TicketCreateSerializer(CustomModelSerializer):
|
||||
transition = serializers.PrimaryKeyRelatedField(queryset=Transition.objects.all(), write_only=True)
|
||||
transition = serializers.PrimaryKeyRelatedField(queryset=Transition.objects.all(), write_only=True, allow_null=True)
|
||||
title = serializers.CharField(allow_blank=True, required=False)
|
||||
|
||||
class Meta:
|
||||
|
|
|
|||
|
|
@ -0,0 +1,26 @@
|
|||
# Generated by Django 3.2.12 on 2025-11-26 01:53
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('wpm', '0124_auto_20251020_1009'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='mlogbw',
|
||||
name='number',
|
||||
field=models.TextField(db_index=True, verbose_name='单个编号'),
|
||||
),
|
||||
migrations.AddIndex(
|
||||
model_name='mlogb',
|
||||
index=models.Index(condition=models.Q(('material_out__isnull', False)), fields=['material_out'], name='mlogb_mat_out_not_null'),
|
||||
),
|
||||
migrations.AddIndex(
|
||||
model_name='mlogb',
|
||||
index=models.Index(condition=models.Q(('material_in__isnull', False)), fields=['material_in'], name='mlogb_mat_in_not_null'),
|
||||
),
|
||||
]
|
||||
|
|
@ -441,6 +441,20 @@ class Mlogb(BaseModel):
|
|||
need_inout = models.BooleanField('是否需要出入库', default=True)
|
||||
number_from = models.TextField('来源个编号', null=True, blank=True)
|
||||
|
||||
class Meta:
|
||||
indexes = [
|
||||
models.Index(
|
||||
fields=["material_out"],
|
||||
name="mlogb_mat_out_not_null",
|
||||
condition=Q(material_out__isnull=False),
|
||||
),
|
||||
models.Index(
|
||||
fields=["material_in"],
|
||||
name="mlogb_mat_in_not_null",
|
||||
condition=Q(material_in__isnull=False),
|
||||
),
|
||||
]
|
||||
|
||||
|
||||
def get_tracking(self):
|
||||
if self.material_in:
|
||||
|
|
@ -502,7 +516,7 @@ class MlogbDefect(BaseModel):
|
|||
class Mlogbw(BaseModel):
|
||||
"""TN: 单个产品生产/检验日志
|
||||
"""
|
||||
number = models.TextField('单个编号')
|
||||
number = models.TextField('单个编号', db_index=True)
|
||||
mlogb = models.ForeignKey(Mlogb, verbose_name='生产记录', on_delete=models.CASCADE, related_name="w_mlogb")
|
||||
mlogbw_from = models.ForeignKey("self", verbose_name='来源个', on_delete=models.CASCADE, null=True, blank=True, related_name="w_mlogbw_from")
|
||||
wpr = models.ForeignKey("wpmw.wpr", verbose_name='关联产品', on_delete=models.SET_NULL
|
||||
|
|
|
|||
|
|
@ -0,0 +1,18 @@
|
|||
# Generated by Django 3.2.12 on 2025-11-26 01:53
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('wpmw', '0008_wpr_data'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='wpr',
|
||||
name='number',
|
||||
field=models.CharField(blank=True, db_index=True, max_length=50, null=True, verbose_name='编号'),
|
||||
),
|
||||
]
|
||||
|
|
@ -16,7 +16,7 @@ class Wpr(BaseModel):
|
|||
TN: 动态产品
|
||||
"""
|
||||
|
||||
number = models.CharField("编号", max_length=50, null=True, blank=True)
|
||||
number = models.CharField("编号", max_length=50, null=True, blank=True, db_index=True)
|
||||
number_out = models.CharField("对外编号", max_length=50, null=True, blank=True, unique=True)
|
||||
version = models.PositiveIntegerField("版本号", default=9999)
|
||||
state = models.PositiveSmallIntegerField('状态', default=10, choices=WmStateOption.choices)
|
||||
|
|
|
|||
87
changelog.md
87
changelog.md
|
|
@ -1,3 +1,90 @@
|
|||
## 3.0.2025120109
|
||||
- feat: 新增功能
|
||||
- 供应商审核通过后即可添加供应商 [caoqianming]
|
||||
- 校验SupplierAudit供应商名称已存在 [caoqianming]
|
||||
- material list 如需获取库存数据需指定传参 [caoqianming]
|
||||
- 添加部分索引 [caoqianming]
|
||||
- srm -model-Papersecret 增加 organization 申请部门字段 [TianyangZhang]
|
||||
- 优化mlogbw list接口速度 [caoqianming]
|
||||
- srm-patent修改字段类型 [TianyangZhang]
|
||||
- resignation添加ticketrelate_name [caoqianming]
|
||||
- base get_object加锁时注意is_deleted过滤采用base_manager [caoqianming]
|
||||
- base wf 调用方法支持静态方法 [caoqianming]
|
||||
- mlogbw关于wpr的校验修改以支持手动新增 [caoqianming]
|
||||
- resignatioin提交时调用的方法 [caoqianming]
|
||||
- ResignationSerializer create bug [caoqianming]
|
||||
- base ticketmixin添加ticket_auto_submit_on_create [caoqianming]
|
||||
- resignation添加ticketMixin [caoqianming]
|
||||
- base wfmixin 修改时校验 [caoqianming]
|
||||
- base ticketDetail添加create_by_name [caoqianming]
|
||||
- 短信发送功能未开启 [caoqianming]
|
||||
- 批次号格式错误的校验 [caoqianming]
|
||||
- mioitemcreate时接收count_send [caoqianming]
|
||||
- mioitemw增加筛选条件 [caoqianming]
|
||||
- wpr_bxerp优化mlogbw的获取 [caoqianming]
|
||||
- do_out报错更明确 [caoqianming]
|
||||
- 优化ana batchwork [caoqianming]
|
||||
- 改版交接支持new_wm [caoqianming]
|
||||
- ofm-models borrowRecord 增加借阅数量 [TianyangZhang]
|
||||
- ofm-models fix bug [TianyangZhang]
|
||||
- feat : ofm -vehicle fix bug [TianyangZhang]
|
||||
- ofm 修改车辆model 字段 [TianyangZhang]
|
||||
- ofm-service fix bug [TianyangZhang]
|
||||
- feat:ofm-service 修改 bug [TianyangZhang]
|
||||
- ofm -修改 view 字段 [TianyangZhang]
|
||||
- ofm 修改 ofm 字段 并重新生成迁移文件 [TianyangZhang]
|
||||
- base workflow添加分类字段 [caoqianming]
|
||||
- ofm-views 修改 车辆字段 [TianyangZhang]
|
||||
- ofm-vehicle 修改车辆审批申请 改完按时间段进行选择 [TianyangZhang]
|
||||
- mioitem添加count_send字段 [caoqianming]
|
||||
- 校验改版时选择的改版物料 [caoqianming]
|
||||
- 导入物料明细支持直接从名称等匹配 [caoqianming]
|
||||
- 增强新批次号校验 [caoqianming]
|
||||
- 提供修改编号的接口 [caoqianming]
|
||||
- supplieraudit采用新工作流挂载方式 [caoqianming]
|
||||
- base 添加ticketmixin可集成到viewset下以支持工作流 [caoqianming]
|
||||
- base 可跳过短信发送 [caoqianming]
|
||||
- 反向操作时忽略明细校验 [caoqianming]
|
||||
- 拦截new_batch的错误 [caoqianming]
|
||||
- fix 修改 srm 的 views [TianyangZhang]
|
||||
- base wfservice创建出工单时处理人为提交人 [caoqianming]
|
||||
- feat:srm fix serializer [TianyangZhang]
|
||||
- base handle_ticket 完善transition校验 [caoqianming]
|
||||
- DatasetRecord添加filter [caoqianming]
|
||||
- handover添加selectfield [caoqianming]
|
||||
- 交接记录返回material_changed_fname [caoqianming]
|
||||
- 改版交接必须为合批操作 [caoqianming]
|
||||
- fix srm serializer [TianyangZhang]
|
||||
- srm-service 去掉 platform belong_dept [TianyangZhang]
|
||||
- add new model platform '平台审批' [TianyangZhang]
|
||||
- base 创建数据时检验不包含id [caoqianming]
|
||||
- 添加供应商审核 [caoqianming]
|
||||
- base 开始编写ticketMixin可自动挂载 [caoqianming]
|
||||
- ResignationSerializer返回employee_id_number [caoqianming]
|
||||
- base 添加EuModelViewSet [caoqianming]
|
||||
- 离职申请支持删除 [caoqianming]
|
||||
- Resignationserializer返回employee_name [caoqianming]
|
||||
- base handle_ticket 默认参数 [caoqianming]
|
||||
- 优化bind_resignation [caoqianming]
|
||||
- base 优化wf create [caoqianming]
|
||||
- ResignationViewSet添加RetrieveModelMixin [caoqianming]
|
||||
- bind_resignation bug [caoqianming]
|
||||
- 返回TicketSimpleSerializer [caoqianming]
|
||||
- fix: 问题修复
|
||||
- fix : srm 修改 paperrecord 字段 cor_author 字段类型 [TianyangZhang]
|
||||
- fix:srm 修改论文审批 反存 论文台账 主要修改model 字段类型 [TianyangZhang]
|
||||
- srm 修改专利台账 [TianyangZhang]
|
||||
- base wfmixin gen_ticket_data保存t_id转为str [caoqianming]
|
||||
- fix : 修改ofm -views -vehicle && services [TianyangZhang]
|
||||
- format_json_with_placeholders 处理decimal [caoqianming]
|
||||
- base wf工作流分类接口detail错误 [caoqianming]
|
||||
- do_in 可直接取用wm [caoqianming]
|
||||
- material get_queryset忘记return qs [caoqianming]
|
||||
- material增加count__gt等查询条件 [caoqianming]
|
||||
- mioitem create时校验是否混批的bug [caoqianming]
|
||||
- base handle_ticket处理ticket_title [caoqianming]
|
||||
- bind_resignation bug [caoqianming]
|
||||
- clean_data关于material的处理 [caoqianming]
|
||||
## 3.0.2025110710
|
||||
- feat: 新增功能
|
||||
- material count字段完全由计算可得 [caoqianming]
|
||||
|
|
|
|||
|
|
@ -35,7 +35,7 @@ sys.path.insert(0, os.path.join(BASE_DIR, 'apps'))
|
|||
ALLOWED_HOSTS = ['*']
|
||||
|
||||
SYS_NAME = '星途工厂综合管理系统'
|
||||
SYS_VERSION = '3.0.2025110710'
|
||||
SYS_VERSION = '3.0.2025120109'
|
||||
X_FRAME_OPTIONS = 'SAMEORIGIN'
|
||||
|
||||
# Application definition
|
||||
|
|
|
|||
Loading…
Reference in New Issue