正在显示
8 个修改的文件
包含
92 行增加
和
17 行删除
| 1 | +# Generated by Django 3.1.1 on 2020-10-21 11:40 | ||
| 2 | + | ||
| 3 | +from django.conf import settings | ||
| 4 | +from django.db import migrations, models | ||
| 5 | +import django.db.models.deletion | ||
| 6 | + | ||
| 7 | + | ||
| 8 | +class Migration(migrations.Migration): | ||
| 9 | + | ||
| 10 | + dependencies = [ | ||
| 11 | + migrations.swappable_dependency(settings.AUTH_USER_MODEL), | ||
| 12 | + ('project', '0004_auto_20201014_1513'), | ||
| 13 | + ] | ||
| 14 | + | ||
| 15 | + operations = [ | ||
| 16 | + migrations.AddField( | ||
| 17 | + model_name='auditor', | ||
| 18 | + name='type', | ||
| 19 | + field=models.PositiveSmallIntegerField(choices=[(1, '市场容量小于300万美金'), (2, '市场容量大于等于300万美金')], default=1, verbose_name='项目类型'), | ||
| 20 | + ), | ||
| 21 | + migrations.AddField( | ||
| 22 | + model_name='project', | ||
| 23 | + name='first_orders', | ||
| 24 | + field=models.PositiveIntegerField(default=0, verbose_name='首单数量'), | ||
| 25 | + ), | ||
| 26 | + migrations.AddField( | ||
| 27 | + model_name='project', | ||
| 28 | + name='orders_estimate', | ||
| 29 | + field=models.CharField(default='', max_length=255, verbose_name='月销量预估'), | ||
| 30 | + ), | ||
| 31 | + migrations.AddField( | ||
| 32 | + model_name='project', | ||
| 33 | + name='roi_report', | ||
| 34 | + field=models.CharField(default='', max_length=255, verbose_name='ROI报告'), | ||
| 35 | + ), | ||
| 36 | + migrations.AddField( | ||
| 37 | + model_name='project', | ||
| 38 | + name='type', | ||
| 39 | + field=models.PositiveSmallIntegerField(choices=[(1, '市场容量小于300万美金'), (2, '市场容量大于等于300万美金')], default=1, verbose_name='项目类型'), | ||
| 40 | + ), | ||
| 41 | + migrations.AlterField( | ||
| 42 | + model_name='auditor', | ||
| 43 | + name='user', | ||
| 44 | + field=models.ForeignKey(on_delete=django.db.models.deletion.CASCADE, related_name='aud', to=settings.AUTH_USER_MODEL, verbose_name='审批人员'), | ||
| 45 | + ), | ||
| 46 | + ] |
| 1 | from django.db import models | 1 | from django.db import models |
| 2 | from usercenter.models import User | 2 | from usercenter.models import User |
| 3 | 3 | ||
| 4 | -# users = User.objects.filter(is_active=True).values('username', 'id').all() | ||
| 5 | -# AUDITOR_CHOICE = [(i['id'], i['username']) for i in users] | ||
| 6 | -AUDITOR_CHOICE = [(2, '邓望明'), (3, '杜波')] | 4 | +PROJECT_TYPE = ( |
| 5 | + (1, u"市场容量小于300万美金"), | ||
| 6 | + (2, u"市场容量大于等于300万美金"), | ||
| 7 | + ) | ||
| 7 | 8 | ||
| 8 | 9 | ||
| 9 | class Auditor(models.Model): | 10 | class Auditor(models.Model): |
| @@ -12,7 +13,6 @@ class Auditor(models.Model): | @@ -12,7 +13,6 @@ class Auditor(models.Model): | ||
| 12 | User, | 13 | User, |
| 13 | on_delete=models.CASCADE, | 14 | on_delete=models.CASCADE, |
| 14 | related_name="aud", | 15 | related_name="aud", |
| 15 | - choices=AUDITOR_CHOICE, | ||
| 16 | verbose_name="审批人员") | 16 | verbose_name="审批人员") |
| 17 | leader = models.ForeignKey( | 17 | leader = models.ForeignKey( |
| 18 | 'self', | 18 | 'self', |
| @@ -21,6 +21,7 @@ class Auditor(models.Model): | @@ -21,6 +21,7 @@ class Auditor(models.Model): | ||
| 21 | null=True, | 21 | null=True, |
| 22 | blank=True, | 22 | blank=True, |
| 23 | verbose_name="上级领导") | 23 | verbose_name="上级领导") |
| 24 | + type = models.PositiveSmallIntegerField(default=1, choices=PROJECT_TYPE, verbose_name="项目类型") | ||
| 24 | order = models.PositiveSmallIntegerField(default=0, null=True, blank=True, verbose_name="排序") | 25 | order = models.PositiveSmallIntegerField(default=0, null=True, blank=True, verbose_name="排序") |
| 25 | 26 | ||
| 26 | def __str__(self): | 27 | def __str__(self): |
| @@ -31,13 +32,17 @@ class Auditor(models.Model): | @@ -31,13 +32,17 @@ class Auditor(models.Model): | ||
| 31 | 32 | ||
| 32 | 33 | ||
| 33 | class Project(models.Model): | 34 | class Project(models.Model): |
| 35 | + | ||
| 34 | category = models.CharField(max_length=100, default="", verbose_name="产品类目") | 36 | category = models.CharField(max_length=100, default="", verbose_name="产品类目") |
| 35 | model_type = models.CharField(max_length=50, default="", verbose_name="产品型号") | 37 | model_type = models.CharField(max_length=50, default="", verbose_name="产品型号") |
| 36 | market_share_analysis = models.TextField(default="", verbose_name="产品市场占有率分析") | 38 | market_share_analysis = models.TextField(default="", verbose_name="产品市场占有率分析") |
| 37 | context_analysis = models.TextField(default="", verbose_name="产品场景分析") | 39 | context_analysis = models.TextField(default="", verbose_name="产品场景分析") |
| 38 | attachments = models.CharField(max_length=800, default="", verbose_name="附件地址") | 40 | attachments = models.CharField(max_length=800, default="", verbose_name="附件地址") |
| 41 | + first_orders = models.PositiveIntegerField(default=0, verbose_name="首单数量") | ||
| 42 | + orders_estimate = models.CharField(default="", max_length=255, verbose_name="月销量预估") | ||
| 39 | auditor = models.ManyToManyField(Auditor, related_name="project_auditor", blank=True, verbose_name="审核人员") | 43 | auditor = models.ManyToManyField(Auditor, related_name="project_auditor", blank=True, verbose_name="审核人员") |
| 40 | is_done = models.BooleanField(default=False, blank=True, verbose_name="是否完成") | 44 | is_done = models.BooleanField(default=False, blank=True, verbose_name="是否完成") |
| 45 | + type = models.PositiveSmallIntegerField(default=1, choices=PROJECT_TYPE, verbose_name="项目类型") | ||
| 41 | is_pass = models.BooleanField(null=True, blank=True, verbose_name="是否通过") | 46 | is_pass = models.BooleanField(null=True, blank=True, verbose_name="是否通过") |
| 42 | create_time = models.DateTimeField(auto_now_add=True) | 47 | create_time = models.DateTimeField(auto_now_add=True) |
| 43 | creator = models.ForeignKey(User, related_name="project_creator", on_delete=models.CASCADE, verbose_name="创建人员") | 48 | creator = models.ForeignKey(User, related_name="project_creator", on_delete=models.CASCADE, verbose_name="创建人员") |
| @@ -23,7 +23,7 @@ class ProjectSerializer(serializers.ModelSerializer): | @@ -23,7 +23,7 @@ class ProjectSerializer(serializers.ModelSerializer): | ||
| 23 | model = Project | 23 | model = Project |
| 24 | fields = ( | 24 | fields = ( |
| 25 | 'id', 'result', 'creator_name', 'category', 'model_type', 'market_share_analysis', 'context_analysis', | 25 | 'id', 'result', 'creator_name', 'category', 'model_type', 'market_share_analysis', 'context_analysis', |
| 26 | - 'attachments', 'create_time', "is_done", "is_pass" | 26 | + 'attachments', 'create_time', "is_done", "is_pass", "type", "orders_estimate", "first_orders" |
| 27 | ) | 27 | ) |
| 28 | depth = 1 | 28 | depth = 1 |
| 29 | 29 |
| @@ -35,17 +35,18 @@ class CreateProject(CreateAPIView): | @@ -35,17 +35,18 @@ class CreateProject(CreateAPIView): | ||
| 35 | if not serializer.is_valid(): | 35 | if not serializer.is_valid(): |
| 36 | raise ValidationError(serializer.errors) | 36 | raise ValidationError(serializer.errors) |
| 37 | else: | 37 | else: |
| 38 | - serializer.save(creator=request.user, auditor=Auditor.objects.order_by('-order').all()) | ||
| 39 | - # 企业微信推送 | ||
| 40 | obj_dict = serializer.data | 38 | obj_dict = serializer.data |
| 41 | - for i in AUDITORS: | 39 | + auditors = Auditor.objects.filter(type=obj_dict['type']).order_by('order') |
| 40 | + serializer.save(creator=request.user, auditor=auditors) | ||
| 41 | + # 企业微信推送 | ||
| 42 | + for i in auditors: | ||
| 42 | Result.objects.create( | 43 | Result.objects.create( |
| 43 | - auditor_id=i[0], | 44 | + auditor_id=i.pk, |
| 44 | project_id=obj_dict['id'] | 45 | project_id=obj_dict['id'] |
| 45 | ) | 46 | ) |
| 46 | url = re.sub("PK", str(obj_dict['id']), FRONT_URL['flow_detail']) | 47 | url = re.sub("PK", str(obj_dict['id']), FRONT_URL['flow_detail']) |
| 47 | url = re.sub("REDIRECT_URL", parse.quote(url, safe=''), FRONT_URL['wx_authorize']) | 48 | url = re.sub("REDIRECT_URL", parse.quote(url, safe=''), FRONT_URL['wx_authorize']) |
| 48 | - first_auditor = Auditor.objects.filter(pk=AUDITORS[0][0]).first() | 49 | + first_auditor = auditors[0] |
| 49 | 50 | ||
| 50 | wx_client.push_card(first_auditor.user.wx_token, url, f"{request.user.username}提交了一个产品立项申请") | 51 | wx_client.push_card(first_auditor.user.wx_token, url, f"{request.user.username}提交了一个产品立项申请") |
| 51 | wx_client.push_card(request.user.wx_token, url, u"流程创建成功") | 52 | wx_client.push_card(request.user.wx_token, url, u"流程创建成功") |
| @@ -61,8 +62,7 @@ class ProjectDetail(RetrieveAPIView): | @@ -61,8 +62,7 @@ class ProjectDetail(RetrieveAPIView): | ||
| 61 | obj = self.get_object() | 62 | obj = self.get_object() |
| 62 | obj.creator_name = obj.creator.username | 63 | obj.creator_name = obj.creator.username |
| 63 | obj.result = [] | 64 | obj.result = [] |
| 64 | - auditors = Auditor.objects.all() | ||
| 65 | - # result = Result.objects.filter(project=obj) | 65 | + auditors = Auditor.objects.filter(type=obj.type) |
| 66 | for i in auditors: | 66 | for i in auditors: |
| 67 | res = i.result_auditor.filter(project=obj).values('is_accept', 'memo').first() | 67 | res = i.result_auditor.filter(project=obj).values('is_accept', 'memo').first() |
| 68 | obj.result.append({ | 68 | obj.result.append({ |
| @@ -94,12 +94,14 @@ class AuditProject(UpdateAPIView): | @@ -94,12 +94,14 @@ class AuditProject(UpdateAPIView): | ||
| 94 | ('reject', '否决') | 94 | ('reject', '否决') |
| 95 | ) | 95 | ) |
| 96 | accept_param = accept_choices[0][0] if request.data.get('is_accept') else accept_choices[1][0] | 96 | accept_param = accept_choices[0][0] if request.data.get('is_accept') else accept_choices[1][0] |
| 97 | - target = Project.objects.filter(auditor__user_id=request.user.id, pk=obj.id) | ||
| 98 | - if not target: | 97 | + # target = Project.objects.filter(auditor__user_id=request.user.id, pk=obj.id) |
| 98 | + if not obj: | ||
| 99 | raise PermissionError | 99 | raise PermissionError |
| 100 | else: | 100 | else: |
| 101 | auditor = Auditor.objects.get(user=request.user) | 101 | auditor = Auditor.objects.get(user=request.user) |
| 102 | - result = Result.objects.filter(auditor=auditor, project=obj).first() | 102 | + result = Result.objects.filter(auditor=auditor, project=obj, is_accept__isnull=True).order_by('pk').first() |
| 103 | + if not result: | ||
| 104 | + raise PermissionError("不允许修改已审核的项目") | ||
| 103 | result.is_accept = accept_param | 105 | result.is_accept = accept_param |
| 104 | result.memo = request.data.get('memo', '') | 106 | result.memo = request.data.get('memo', '') |
| 105 | result.save() | 107 | result.save() |
| @@ -117,7 +119,9 @@ class AuditProject(UpdateAPIView): | @@ -117,7 +119,9 @@ class AuditProject(UpdateAPIView): | ||
| 117 | obj.is_done = True | 119 | obj.is_done = True |
| 118 | obj.is_pass = False | 120 | obj.is_pass = False |
| 119 | else: | 121 | else: |
| 120 | - second_auditor = Auditor.objects.filter(pk=AUDITORS[1][0]).first() | 122 | + next_auditor_id = Result.objects.filter(project=obj, is_accept__isnull=True)\ |
| 123 | + .values_list('auditor_id', flat=True).order_by('pk').first() | ||
| 124 | + second_auditor = Auditor.objects.filter(pk=next_auditor_id).first() | ||
| 121 | wx_client.push_card(second_auditor.user.wx_token, url, f"{request.user.username}已审核了一个产品立项申请") | 125 | wx_client.push_card(second_auditor.user.wx_token, url, f"{request.user.username}已审核了一个产品立项申请") |
| 122 | obj.save() | 126 | obj.save() |
| 123 | wx_client.push_card(obj.creator.wx_token, url, desc) | 127 | wx_client.push_card(obj.creator.wx_token, url, desc) |
| 1 | +# Generated by Django 3.1.1 on 2020-10-21 13:10 | ||
| 2 | + | ||
| 3 | +from django.db import migrations, models | ||
| 4 | + | ||
| 5 | + | ||
| 6 | +class Migration(migrations.Migration): | ||
| 7 | + | ||
| 8 | + dependencies = [ | ||
| 9 | + ('usercenter', '0001_initial'), | ||
| 10 | + ] | ||
| 11 | + | ||
| 12 | + operations = [ | ||
| 13 | + migrations.AddField( | ||
| 14 | + model_name='media', | ||
| 15 | + name='file_name', | ||
| 16 | + field=models.CharField(default='', max_length=100, verbose_name='文件名'), | ||
| 17 | + ), | ||
| 18 | + ] |
| @@ -108,6 +108,7 @@ class Media(models.Model): | @@ -108,6 +108,7 @@ class Media(models.Model): | ||
| 108 | file = models.FileField(max_length=200, upload_to="%Y-%m-%d", verbose_name="文件地址") | 108 | file = models.FileField(max_length=200, upload_to="%Y-%m-%d", verbose_name="文件地址") |
| 109 | size = models.PositiveIntegerField(verbose_name="文件大小", null=True, blank=True) | 109 | size = models.PositiveIntegerField(verbose_name="文件大小", null=True, blank=True) |
| 110 | user = models.ForeignKey(User, on_delete=models.CASCADE, null=True, blank=True, related_name="uploader", verbose_name="上传用户") | 110 | user = models.ForeignKey(User, on_delete=models.CASCADE, null=True, blank=True, related_name="uploader", verbose_name="上传用户") |
| 111 | + file_name = models.CharField(max_length=100, default="", verbose_name="文件名") | ||
| 111 | extension = models.CharField(max_length=10, verbose_name="文件扩展名", choices=UPLOAD_MEDIA_CHOICES) | 112 | extension = models.CharField(max_length=10, verbose_name="文件扩展名", choices=UPLOAD_MEDIA_CHOICES) |
| 112 | create_time = models.DateTimeField(auto_now_add=True, verbose_name="创建时间") | 113 | create_time = models.DateTimeField(auto_now_add=True, verbose_name="创建时间") |
| 113 | hash = models.CharField(max_length=200, verbose_name="文件哈希", null=True, blank=True) | 114 | hash = models.CharField(max_length=200, verbose_name="文件哈希", null=True, blank=True) |
| @@ -54,7 +54,7 @@ class GroupSerializer(serializers.ModelSerializer): | @@ -54,7 +54,7 @@ class GroupSerializer(serializers.ModelSerializer): | ||
| 54 | class MediaSerializer(serializers.ModelSerializer): | 54 | class MediaSerializer(serializers.ModelSerializer): |
| 55 | class Meta: | 55 | class Meta: |
| 56 | model = Media | 56 | model = Media |
| 57 | - fields = ('file', 'size', 'create_time') | 57 | + fields = ('file', 'size', 'create_time', 'file_name') |
| 58 | 58 | ||
| 59 | 59 | ||
| 60 | 60 |
| @@ -46,6 +46,7 @@ class UploadMedia(CreateAPIView): | @@ -46,6 +46,7 @@ class UploadMedia(CreateAPIView): | ||
| 46 | if not file: | 46 | if not file: |
| 47 | file = Media.objects.create( | 47 | file = Media.objects.create( |
| 48 | file=uploaded_file, | 48 | file=uploaded_file, |
| 49 | + file_name=uploaded_file.name, | ||
| 49 | hash=file_hash, | 50 | hash=file_hash, |
| 50 | user=request.user, | 51 | user=request.user, |
| 51 | size=file_size, | 52 | size=file_size, |
-
请 注册 或 登录 后发表评论