Merge branch 'tamron' of http://git.xfoto.com.cn/Kodo/kodo into tamron

FFIB 2 gadi atpakaļ
vecāks
revīzija
8f76c30a1e

+ 4 - 3
account/admin.py

@@ -8,7 +8,7 @@ from mch.models import ConsumeInfoSubmitLogInfo
8 8
 
9 9
 
10 10
 class UserInfoAdmin(ChangeOnlyModelAdmin, admin.ModelAdmin):
11
-    list_display = ('user_id', 'nickname', 'phone', 'appid', 'unionid', 'openid', 'openid_miniapp', 'location', 'balance', 'integral', 'freeze_integral', 'user_status', 'test_user', 'integral', 'freeze_integral', 'shots_num', 'level', 'coupon_expire_at', 'is_maintenance', 'status', 'created_at', 'updated_at')
11
+    list_display = ('user_id', 'nickname', 'phone', 'appid', 'unionid', 'openid', 'openid_miniapp', 'location', 'balance', 'user_status', 'test_user', 'integral', 'freeze_integral', 'shots_num', 'level', 'coupon_expire_at', 'is_maintenance', 'status', 'created_at', 'updated_at')
12 12
     list_filter = ('user_from', 'appid', 'subscribe', 'has_membercard', 'test_user', 'is_maintenance', 'sex', 'user_status', 'status', 'code_version', 'new_subscribe', 'created_at', 'integral')
13 13
     readonly_fields = ('user_id', )
14 14
     search_fields = ('user_id', 'username', 'unionid', 'openid', 'openid_miniapp', 'name', 'phone', 'location', 'memberusercardcode')
@@ -20,8 +20,9 @@ class UserInfoAdmin(ChangeOnlyModelAdmin, admin.ModelAdmin):
20 20
 
21 21
 
22 22
 class UserIntegralIncomeExpensesInfoAdmin(ChangeOnlyModelAdmin, admin.ModelAdmin):
23
-    list_display = ('user_id', 'model_id', 'model_name', 'code', 'integral', 'remark', 'updated_at', 'created_at')
24
-    search_fields = ('user_id',)
23
+    list_display = ('user_id', 'brand_id', 'brand_name', 'model_id', 'model_name', 'code', 'integral_from', 'integral', 'final_integral', 'remark', 'updated_at', 'created_at')
24
+    list_filter = ('integral_from', 'status')
25
+    search_fields = ('user_id', )
25 26
 
26 27
 
27 28
 admin.site.register(UserInfo, UserInfoAdmin)

+ 19 - 0
account/migrations/0055_userintegralincomeexpensesinfo_final_integral.py

@@ -0,0 +1,19 @@
1
+# -*- coding: utf-8 -*-
2
+# Generated by Django 3.2.16 on 2022-10-27 10:07
3
+
4
+from django.db import migrations, models
5
+
6
+
7
+class Migration(migrations.Migration):
8
+
9
+    dependencies = [
10
+        ('account', '0054_userinfo_coupon_expire_at'),
11
+    ]
12
+
13
+    operations = [
14
+        migrations.AddField(
15
+            model_name='userintegralincomeexpensesinfo',
16
+            name='final_integral',
17
+            field=models.IntegerField(default=0, help_text='最终积分', verbose_name='final_integral'),
18
+        ),
19
+    ]

+ 19 - 0
account/migrations/0056_alter_userintegralincomeexpensesinfo_integral_from.py

@@ -0,0 +1,19 @@
1
+# -*- coding: utf-8 -*-
2
+# Generated by Django 3.2.16 on 2022-10-27 10:38
3
+
4
+from django.db import migrations, models
5
+
6
+
7
+class Migration(migrations.Migration):
8
+
9
+    dependencies = [
10
+        ('account', '0055_userintegralincomeexpensesinfo_final_integral'),
11
+    ]
12
+
13
+    operations = [
14
+        migrations.AlterField(
15
+            model_name='userintegralincomeexpensesinfo',
16
+            name='integral_from',
17
+            field=models.IntegerField(choices=[(0, '产品'), (1, '分享'), (2, '投稿'), (99, '会员活动投稿福利')], default=0, help_text='积分来源', verbose_name='integral_from'),
18
+        ),
19
+    ]

+ 4 - 2
account/models.py

@@ -331,11 +331,13 @@ class UserIntegralIncomeExpensesInfo(BaseModelMixin):
331 331
     PRODUCT = 0
332 332
     SHARE = 1
333 333
     CONTRIBUTE = 2
334
+    MEMBER_ACTIVITY_CONTRIBUTION_WELFARE = 99
334 335
 
335 336
     INTEGRAL_FROM = (
336 337
         (PRODUCT, u'产品'),
337 338
         (SHARE, u'分享'),
338 339
         (CONTRIBUTE, u'投稿'),
340
+        (MEMBER_ACTIVITY_CONTRIBUTION_WELFARE, u'会员活动投稿福利'),
339 341
     )
340 342
 
341 343
     user_id = models.CharField(_(u'user_id'), max_length=32, blank=True, null=True, help_text=u'用户唯一标识', db_index=True)
@@ -343,14 +345,14 @@ class UserIntegralIncomeExpensesInfo(BaseModelMixin):
343 345
     brand_id = models.CharField(_(u'brand_id'), max_length=32, blank=True, null=True, help_text=u'品牌唯一标识', db_index=True)
344 346
     brand_name = models.CharField(_(u'brand_name'), max_length=255, blank=True, null=True, help_text=u'品牌名称')
345 347
 
346
-    integral_from = models.IntegerField(_(u'integral_from'), choices=INTEGRAL_FROM, default=PRODUCT, help_text=u'积分来源')
347
-
348 348
     model_id = models.CharField(_(u'model_id'), max_length=32, blank=True, null=True, help_text=u'型号唯一标识', db_index=True)
349 349
     model_name = models.CharField(_(u'model_name'), max_length=255, blank=True, null=True, help_text=u'型号名称')
350 350
 
351 351
     code = models.CharField(_(u'code'), max_length=32, blank=True, null=True, help_text=u'机身码', db_index=True)
352 352
 
353
+    integral_from = models.IntegerField(_(u'integral_from'), choices=INTEGRAL_FROM, default=PRODUCT, help_text=u'积分来源')
353 354
     integral = models.IntegerField(_(u'integral'), default=0, help_text=u'增减积分')
355
+    final_integral = models.IntegerField(_(u'final_integral'), default=0, help_text=u'最终积分')
354 356
 
355 357
     remark = models.CharField(_(u'remark'), max_length=255, blank=True, null=True, help_text=u'备注')
356 358
 

+ 23 - 15
api/admin_views.py

@@ -29,10 +29,11 @@ from member.models import (GoodsInfo, GoodsOrderInfo, MemberActivityContribution
29 29
                            MemberActivityGroupShareInfo, MemberActivityInfo, MemberActivitySignupInfo)
30 30
 from pre.custom_message import sendtemplatemessage, sendwxasubscribemessage
31 31
 from statistic.models import ConsumeModelSaleStatisticInfo, ConsumeSaleStatisticInfo, ConsumeUserStatisticInfo
32
-from utils.error.errno_utils import (AdministratorStatusCode, ComplementCodeStatusCode,
32
+from utils.error.errno_utils import (AdministratorStatusCode, ComplementCodeStatusCode, CouponStatusCode,
33 33
                                      MemberActivityContributionStatusCode, MemberActivityContributionWelfareStatusCode,
34
-                                     MemberActivityContributionWelfareUnblockingStatusCode, ProductBrandStatusCode,
35
-                                     ProductCouponStatusCode, ProductMachineStatusCode, UserStatusCode)
34
+                                     MemberActivityContributionWelfareUnblockingStatusCode, MemberActivityStatusCode,
35
+                                     MemberGoodStatusCode, ProductCouponStatusCode, ProductMachineStatusCode,
36
+                                     UserStatusCode)
36 37
 
37 38
 
38 39
 WECHAT = settings.WECHAT
@@ -791,7 +792,7 @@ def member_activity_detail(request, administrator):
791 792
     try:
792 793
         log = MemberActivityInfo.objects.get(activity_id=activity_id)
793 794
     except MemberActivityInfo.DoesNotExist:
794
-        return response()
795
+        return response(MemberActivityStatusCode.ACTIVITY_NOT_FOUND)
795 796
 
796 797
     return response(200, 'Get Member Activity Record Details Success', u'获取会员活动详情成功', data={
797 798
         'log': log.admindetails,
@@ -804,10 +805,10 @@ def member_activity_update(request, administrator):
804 805
     activity_type = int(request.POST.get('activity_type', 0))
805 806
     title = request.POST.get('title', '')
806 807
     subtitle = request.POST.get('subtitle', '')
807
-    start_date = request.POST.get('start_date', '') or settings.DEFAULT_START_DATE
808
-    end_date = date = request.POST.get('date', '') or request.POST.get('end_date', '') or settings.DEFAULT_END_DATE
809
-    start_display_date = request.POST.get('start_display_date', '') or settings.DEFAULT_START_DATE
810
-    end_display_date = request.POST.get('end_display_date', '') or settings.DEFAULT_END_DATE
808
+    start_date = tc.to_date(request.POST.get('start_date', '') or settings.DEFAULT_START_DATE)
809
+    end_date = date = tc.to_date(request.POST.get('date', '') or request.POST.get('end_date', '') or settings.DEFAULT_END_DATE)
810
+    start_display_date = tc.to_date(request.POST.get('start_display_date', '') or settings.DEFAULT_START_DATE)
811
+    end_display_date = tc.to_date(request.POST.get('end_display_date', '') or settings.DEFAULT_END_DATE)
811 812
     city = request.POST.get('city', '')
812 813
     location = request.POST.get('location', '')
813 814
     integral = int(request.POST.get('integral', 0))
@@ -828,7 +829,7 @@ def member_activity_update(request, administrator):
828 829
     try:
829 830
         log = MemberActivityInfo.objects.get(activity_id=activity_id, status=True)
830 831
     except MemberActivityInfo.DoesNotExist:
831
-        return response()
832
+        return response(MemberActivityStatusCode.ACTIVITY_NOT_FOUND)
832 833
 
833 834
     log.activity_type = activity_type
834 835
     log.title = title
@@ -1110,6 +1111,11 @@ def member_activity_contribute_welfare_unlock(request, administrator):
1110 1111
     except MemberActivityContributionInfo.DoesNotExist:
1111 1112
         return response(MemberActivityContributionStatusCode.ACTIVITY_CONTRIBUTION_NOT_FOUND)
1112 1113
 
1114
+    try:
1115
+        welfare = MemberActivityContributionWelfareInfo.objects.get(welfare_id=welfare_id, status=True)
1116
+    except MemberActivityContributionWelfareInfo.DoesNotExist:
1117
+        return response(MemberActivityContributionWelfareStatusCode.ACTIVITY_CONTRIBUTION_WELFARE_NOT_FOUND)
1118
+
1113 1119
     MemberActivityContributionWelfareUnlockingInfo.objects.create(
1114 1120
         brand_id=administrator.brand_id,
1115 1121
         admin_id=admin_id,
@@ -1117,6 +1123,8 @@ def member_activity_contribute_welfare_unlock(request, administrator):
1117 1123
         activity_id=contribution.activity_id,
1118 1124
         contribution_id=contribution_id,
1119 1125
         welfare_id=welfare_id,
1126
+        welfare_type=welfare.welfare_type,
1127
+        welfare_value=welfare.welfare_value,
1120 1128
     )
1121 1129
 
1122 1130
     return response(200, 'Unlock Member Activity Contribute Welfare Success', u'解锁会员活动投稿福利成功')
@@ -1246,7 +1254,7 @@ def coupon_detail(request, administrator):
1246 1254
     try:
1247 1255
         log = CouponInfo.objects.get(coupon_id=coupon_id)
1248 1256
     except CouponInfo.DoesNotExist:
1249
-        return response()
1257
+        return response(CouponStatusCode.COUPON_NOT_FOUND)
1250 1258
 
1251 1259
     log = log.admindetails
1252 1260
 
@@ -1299,7 +1307,7 @@ def coupon_update(request, administrator):
1299 1307
     try:
1300 1308
         log = CouponInfo.objects.get(coupon_id=coupon_id, status=True)
1301 1309
     except CouponInfo.DoesNotExist:
1302
-        return response()
1310
+        return response(CouponStatusCode.COUPON_NOT_FOUND)
1303 1311
 
1304 1312
     log.brand_id = administrator.brand_id
1305 1313
     log.coupon_title = coupon_title
@@ -1323,7 +1331,7 @@ def coupon_delete(request, administrator):
1323 1331
     try:
1324 1332
         log = CouponInfo.objects.get(coupon_id=coupon_id, status=True)
1325 1333
     except CouponInfo.DoesNotExist:
1326
-        return response()
1334
+        return response(CouponStatusCode.COUPON_NOT_FOUND)
1327 1335
 
1328 1336
     log.status = False
1329 1337
     log.save()
@@ -1357,7 +1365,7 @@ def member_goods_detail(request, administrator):
1357 1365
     try:
1358 1366
         log = GoodsInfo.objects.get(good_id=good_id)
1359 1367
     except GoodsInfo.DoesNotExist:
1360
-        return response()
1368
+        return response(MemberGoodStatusCode.GOOD_NOT_FOUND)
1361 1369
 
1362 1370
     log = log.admindetails
1363 1371
 
@@ -1382,7 +1390,7 @@ def member_goods_update(request, administrator):
1382 1390
     try:
1383 1391
         log = GoodsInfo.objects.get(good_id=good_id, status=True)
1384 1392
     except GoodsInfo.DoesNotExist:
1385
-        return response()
1393
+        return response(MemberGoodStatusCode.GOOD_NOT_FOUND)
1386 1394
 
1387 1395
     log.title = title
1388 1396
     log.desc = desc
@@ -1519,7 +1527,7 @@ def complement_code_audit(request, administrator):
1519 1527
         try:
1520 1528
             user = UserInfo.objects.get(user_id=log.user_id, status=True)
1521 1529
         except UserInfo.DoesNotExist:
1522
-            return response()
1530
+            return response(UserStatusCode.USER_NOT_FOUND)
1523 1531
 
1524 1532
         # Send template_message
1525 1533
         data = {

+ 23 - 4
api/member_views.py

@@ -13,7 +13,7 @@ from pywe_miniapp import get_shareinfo
13 13
 from pywe_storage import RedisStorage
14 14
 from TimeConvert import TimeConvert as tc
15 15
 
16
-from account.models import UserInfo
16
+from account.models import UserInfo, UserIntegralIncomeExpensesInfo
17 17
 from coupon.models import UserCouponInfo
18 18
 from member.models import (GoodsInfo, GoodsOrderInfo, MemberActivityContributionInfo,
19 19
                            MemberActivityContributionWelfareUnlockingInfo, MemberActivityGroupShareInfo,
@@ -422,7 +422,7 @@ def activity_signup_info(request):
422 422
     try:
423 423
         contribution = MemberActivityContributionInfo.objects.get(user_id=user_id, activity_id=activity_id, content_type=0, status=True)
424 424
     except MemberActivityContributionInfo.DoesNotExist:
425
-        return response()
425
+        return response(MemberActivityContributionStatusCode.ACTIVITY_CONTRIBUTION_NOT_FOUND)
426 426
 
427 427
     return response(data={
428 428
         'signup_info': signup_info.data,
@@ -501,7 +501,7 @@ def activity_group_share(request):
501 501
         return response()
502 502
 
503 503
     try:
504
-        user = UserInfo.objects.get(user_id=share_user_id, status=True)
504
+        user = UserInfo.objects.select_for_update().get(user_id=share_user_id, status=True)
505 505
     except UserInfo.DoesNotExist:
506 506
         return response(UserStatusCode.USER_NOT_FOUND)
507 507
 
@@ -746,12 +746,31 @@ def activity_contribute_welfare_unlocking_handled(request):
746 746
     except MemberActivityContributionWelfareUnlockingInfo.DoesNotExist:
747 747
         return response(MemberActivityContributionWelfareUnblockingStatusCode.ACTIVITY_CONTRIBUTION_WELFARE_UNBLOCKING_NOT_FOUND)
748 748
 
749
+    if unlocking.is_handled:
750
+        return response(MemberActivityContributionWelfareUnblockingStatusCode.ACTIVITY_CONTRIBUTION_WELFARE_UNBLOCKING_HAS_HANDLED)
751
+
749 752
     if user_id != unlocking.user_id:
750 753
         return response(PermissionStatusCode.PERMISSION_DENIED)
751 754
 
752 755
     unlocking.is_handled = True
753 756
     unlocking.save()
754 757
 
755
-    # TODO: 积分相关逻辑在这里处理?
758
+    if unlocking.welfare_type == MemberActivityContributionWelfareUnlockingInfo.WELFARE_INTEGRAL:
759
+        try:
760
+            user = UserInfo.objects.select_for_update().get(user_id=user_id, status=True)
761
+        except UserInfo.DoesNotExist:
762
+            return response(UserStatusCode.USER_NOT_FOUND)
763
+
764
+        user.integral += unlocking.welfare_value
765
+        user.save()
766
+
767
+        UserIntegralIncomeExpensesInfo.objects.create(
768
+            brand_id=brand_id,
769
+            user_id=user_id,
770
+            integral_from=UserIntegralIncomeExpensesInfo.MEMBER_ACTIVITY_CONTRIBUTION_WELFARE,
771
+            integral=unlocking.welfare_value,
772
+            final_integral=user.integral,
773
+            remark=unlocking.id,
774
+        )
756 775
 
757 776
     return response(200, 'Update Member Activity Contribute Welfare Unblocking Success', u'处理会员活动投稿福利解锁成功')

+ 9 - 8
api/staff_views.py

@@ -16,7 +16,8 @@ from staff.models import StaffDeleteClerkSaleSubmitLogInfo, StaffDeleteConsumerS
16 16
 from statistic.models import (ConsumeModelSaleStatisticInfo, ConsumeSaleStatisticInfo, ConsumeUserStatisticInfo,
17 17
                               DistributorSaleStatisticInfo, ModelSaleStatisticInfo, ProvinceSaleStatisticInfo,
18 18
                               SaleclerkSaleStatisticInfo, SaleStatisticInfo)
19
-from utils.error.errno_utils import AdministratorStatusCode
19
+from utils.error.errno_utils import (AdministratorStatusCode, ProductBrandStatusCode, ProductDistributorStatusCode,
20
+                                     ProductModelStatusCode, SaleclerkStatusCode, UserStatusCode)
20 21
 
21 22
 
22 23
 def exec_del_clerk_sale_submit(pk, admin_id):
@@ -35,22 +36,22 @@ def exec_del_clerk_sale_submit(pk, admin_id):
35 36
     try:
36 37
         brand = BrandInfo.objects.get(pk=ssli.brand_pk)
37 38
     except BrandInfo.DoesNotExist:
38
-        return response()
39
+        return response(ProductBrandStatusCode)
39 40
 
40 41
     try:
41 42
         model = ModelInfo.objects.get(pk=ssli.model_pk)
42 43
     except ModelInfo.DoesNotExist:
43
-        return response()
44
+        return response(ProductModelStatusCode)
44 45
 
45 46
     try:
46 47
         clerk = SaleclerkInfo.objects.select_for_update().get(clerk_id=ssli.clerk_id, status=True)
47 48
     except SaleclerkInfo.DoesNotExist:
48
-        return response()
49
+        return response(SaleclerkStatusCode.CLERK_NOT_FOUND)
49 50
 
50 51
     try:
51 52
         distributor = DistributorInfo.objects.get(distributor_id=clerk.distributor_id)
52 53
     except DistributorInfo.DoesNotExist:
53
-        return response()
54
+        return response(ProductDistributorStatusCode.DISTRIBUTOR_NOT_FOUND)
54 55
 
55 56
     ymd = str(ssli.ymd)
56 57
 
@@ -280,17 +281,17 @@ def exec_del_consumer_submit(pk, admin_id):
280 281
     try:
281 282
         brand = BrandInfo.objects.get(brand_id=ssli.brand_id)
282 283
     except BrandInfo.DoesNotExist:
283
-        return response()
284
+        return response(ProductBrandStatusCode.BRAND_NOT_FOUND)
284 285
 
285 286
     try:
286 287
         model = ModelInfo.objects.get(model_id=ssli.model_id)
287 288
     except ModelInfo.DoesNotExist:
288
-        return response()
289
+        return response(ProductModelStatusCode.MODEL_NOT_FOUND)
289 290
 
290 291
     try:
291 292
         user = UserInfo.objects.select_for_update().get(user_id=ssli.user_id)
292 293
     except UserInfo.DoesNotExist:
293
-        return response()
294
+        return response(UserStatusCode.USER_NOT_FOUND)
294 295
 
295 296
     # 记录删除日志
296 297
     StaffDeleteConsumerSubmitLogInfo.objects.create(

+ 72 - 70
commands/management/commands/cpon.py

@@ -3,6 +3,7 @@
3 3
 import logging
4 4
 import time
5 5
 
6
+from django.db import transaction
6 7
 from django_six import CompatibilityBaseCommand, close_old_connections
7 8
 from TimeConvert import TimeConvert as tc
8 9
 
@@ -42,83 +43,84 @@ class Command(CompatibilityBaseCommand):
42 43
             # TODO: Opt by delay execute
43 44
             time.sleep(5)
44 45
 
45
-            try:
46
-                user = UserInfo.objects.get(user_id=user_id)
47
-            except UserInfo.DoesNotExist:
48
-                continue
49
-
50
-            if coupon_id:
51
-                # 发放商城兑换券
46
+            with transaction.atomic():
52 47
                 try:
53
-                    coupon = CouponInfo.objects.get(coupon_id=coupon_id)
54
-                except CouponInfo.DoesNotExist:
48
+                    user = UserInfo.objects.get(user_id=user_id)
49
+                except UserInfo.DoesNotExist:
55 50
                     continue
56 51
 
57
-                UserCouponInfo.objects.create(
58
-                    brand_id=coupon.brand_id,
59
-                    brand_name=coupon.brand_name,
60
-                    coupon_id=coupon_id,
61
-                    user_id=user_id,
62
-                    coupon_title=coupon.coupon_title,
63
-                    coupon_detail=coupon.coupon_detail,
64
-                    coupon_value=coupon.coupon_value,
65
-                    coupon_image=coupon.coupon_image,
66
-                    coupon_from='INTEGRAL_MALL',
67
-                    active_at=tc.utc_datetime(),
68
-                    expire_at=tc.utc_datetime(days=coupon.coupon_valid_period) if coupon.coupon_expire_type == CouponInfo.CHANGED_EXPIRED_TIME else coupon.coupon_expire_at,
69
-                    coupon_valid_period=coupon.coupon_valid_period,
70
-                    coupon_limit_model_ids=coupon.coupon_limit_model_ids,
71
-                    is_coupon_admin_writeoff=coupon.is_coupon_admin_writeoff,
72
-                )
73
-
74
-            else:
75
-                # 发放会员权益
76
-                active_at = tc.utc_datetime()
77
-                expire_at = tc.utc_datetime(days=365)
78
-
79
-                rights = RightInfo.objects.filter(is_send_coupon=True, status=True)
80
-                for right in rights:
81
-                    if user.level == UserInfo.MEMBER_LRC:
82
-                        coupon_id = right.coupon_level1_id
83
-                        coupon_num = right.coupon_level1_num
84
-                    elif user.level == UserInfo.MEMBER_SILVER:
85
-                        coupon_id = right.coupon_level2_id
86
-                        coupon_num = right.coupon_level2_num
87
-                    elif user.level == UserInfo.MEMBER_GOLD:
88
-                        coupon_id = right.coupon_level3_id
89
-                        coupon_num = right.coupon_level3_num
90
-                    elif user.level == UserInfo.MEMBER_WHITE_GOLD:
91
-                        coupon_id = right.coupon_level4_id
92
-                        coupon_num = right.coupon_level4_num
93
-                    elif user.level == UserInfo.MEMBER_BLACK_GOLD:
94
-                        coupon_id = right.coupon_level5_id
95
-                        coupon_num = right.coupon_level5_num
96
-
97
-                    if not coupon_id:
98
-                        continue
99
-
52
+                if coupon_id:
53
+                    # 发放商城兑换券
100 54
                     try:
101 55
                         coupon = CouponInfo.objects.get(coupon_id=coupon_id)
102 56
                     except CouponInfo.DoesNotExist:
103 57
                         continue
104 58
 
105
-                    for _ in range(right.coupon_num or coupon_num):
106
-                        UserCouponInfo.objects.create(
107
-                            brand_id=coupon.brand_id,
108
-                            brand_name=coupon.brand_name,
109
-                            coupon_id=coupon_id,
110
-                            user_id=user_id,
111
-                            coupon_title=coupon.coupon_title,
112
-                            coupon_detail=coupon.coupon_detail,
113
-                            coupon_value=coupon.coupon_value,
114
-                            coupon_image=coupon.coupon_image,
115
-                            active_at=active_at,
116
-                            expire_at=expire_at,
117
-                            coupon_valid_period=coupon.coupon_valid_period,
118
-                            coupon_limit_model_ids=coupon.coupon_limit_model_ids,
119
-                        )
120
-
121
-                user.coupon_expire_at = expire_at
122
-                user.save()
59
+                    UserCouponInfo.objects.create(
60
+                        brand_id=coupon.brand_id,
61
+                        brand_name=coupon.brand_name,
62
+                        coupon_id=coupon_id,
63
+                        user_id=user_id,
64
+                        coupon_title=coupon.coupon_title,
65
+                        coupon_detail=coupon.coupon_detail,
66
+                        coupon_value=coupon.coupon_value,
67
+                        coupon_image=coupon.coupon_image,
68
+                        coupon_from='INTEGRAL_MALL',
69
+                        active_at=tc.utc_datetime(),
70
+                        expire_at=tc.utc_datetime(days=coupon.coupon_valid_period) if coupon.coupon_expire_type == CouponInfo.CHANGED_EXPIRED_TIME else coupon.coupon_expire_at,
71
+                        coupon_valid_period=coupon.coupon_valid_period,
72
+                        coupon_limit_model_ids=coupon.coupon_limit_model_ids,
73
+                        is_coupon_admin_writeoff=coupon.is_coupon_admin_writeoff,
74
+                    )
75
+
76
+                else:
77
+                    # 发放会员权益
78
+                    active_at = tc.utc_datetime()
79
+                    expire_at = tc.utc_datetime(days=365)
80
+
81
+                    rights = RightInfo.objects.filter(is_send_coupon=True, status=True)
82
+                    for right in rights:
83
+                        if user.level == UserInfo.MEMBER_LRC:
84
+                            coupon_id = right.coupon_level1_id
85
+                            coupon_num = right.coupon_level1_num
86
+                        elif user.level == UserInfo.MEMBER_SILVER:
87
+                            coupon_id = right.coupon_level2_id
88
+                            coupon_num = right.coupon_level2_num
89
+                        elif user.level == UserInfo.MEMBER_GOLD:
90
+                            coupon_id = right.coupon_level3_id
91
+                            coupon_num = right.coupon_level3_num
92
+                        elif user.level == UserInfo.MEMBER_WHITE_GOLD:
93
+                            coupon_id = right.coupon_level4_id
94
+                            coupon_num = right.coupon_level4_num
95
+                        elif user.level == UserInfo.MEMBER_BLACK_GOLD:
96
+                            coupon_id = right.coupon_level5_id
97
+                            coupon_num = right.coupon_level5_num
98
+
99
+                        if not coupon_id:
100
+                            continue
101
+
102
+                        try:
103
+                            coupon = CouponInfo.objects.get(coupon_id=coupon_id)
104
+                        except CouponInfo.DoesNotExist:
105
+                            continue
106
+
107
+                        for _ in range(right.coupon_num or coupon_num):
108
+                            UserCouponInfo.objects.create(
109
+                                brand_id=coupon.brand_id,
110
+                                brand_name=coupon.brand_name,
111
+                                coupon_id=coupon_id,
112
+                                user_id=user_id,
113
+                                coupon_title=coupon.coupon_title,
114
+                                coupon_detail=coupon.coupon_detail,
115
+                                coupon_value=coupon.coupon_value,
116
+                                coupon_image=coupon.coupon_image,
117
+                                active_at=active_at,
118
+                                expire_at=expire_at,
119
+                                coupon_valid_period=coupon.coupon_valid_period,
120
+                                coupon_limit_model_ids=coupon.coupon_limit_model_ids,
121
+                            )
122
+
123
+                    user.coupon_expire_at = expire_at
124
+                    user.save()
123 125
 
124 126
             close_old_connections()

+ 52 - 50
commands/management/commands/cpon2.py

@@ -2,6 +2,7 @@
2 2
 
3 3
 import logging
4 4
 
5
+from django.db import transaction
5 6
 from django_six import CompatibilityBaseCommand, close_old_connections
6 7
 from TimeConvert import TimeConvert as tc
7 8
 
@@ -37,58 +38,59 @@ class Command(CompatibilityBaseCommand):
37 38
             brand_id = v.get('brand_id', '')
38 39
             user_id = v.get('user_id', '')
39 40
 
40
-            try:
41
-                user = UserInfo.objects.get(user_id=user_id)
42
-            except UserInfo.DoesNotExist:
43
-                continue
44
-
45
-            active_at = user.coupon_expire_at
46
-            expire_at = tc.utc_datetime(user.coupon_expire_at, days=365)
47
-
48
-            # 发放会员权益
49
-            rights = RightInfo.objects.filter(is_send_coupon=True, is_continue_send_coupon=True, status=True)
50
-            for right in rights:
51
-                if user.level == UserInfo.MEMBER_LRC:
52
-                    coupon_id = right.coupon_level1_id
53
-                    coupon_num = right.coupon_level1_num
54
-                elif user.level == UserInfo.MEMBER_SILVER:
55
-                    coupon_id = right.coupon_level2_id
56
-                    coupon_num = right.coupon_level2_num
57
-                elif user.level == UserInfo.MEMBER_GOLD:
58
-                    coupon_id = right.coupon_level3_id
59
-                    coupon_num = right.coupon_level3_num
60
-                elif user.level == UserInfo.MEMBER_WHITE_GOLD:
61
-                    coupon_id = right.coupon_level4_id
62
-                    coupon_num = right.coupon_level4_num
63
-                elif user.level == UserInfo.MEMBER_BLACK_GOLD:
64
-                    coupon_id = right.coupon_level5_id
65
-                    coupon_num = right.coupon_level5_num
66
-
67
-                if not coupon_id:
68
-                    continue
69
-
41
+            with transaction.atomic():
70 42
                 try:
71
-                    coupon = CouponInfo.objects.get(coupon_id=coupon_id)
72
-                except CouponInfo.DoesNotExist:
43
+                    user = UserInfo.objects.get(user_id=user_id)
44
+                except UserInfo.DoesNotExist:
73 45
                     continue
74 46
 
75
-                for _ in range(right.coupon_num or coupon_num):
76
-                    UserCouponInfo.objects.create(
77
-                        brand_id=coupon.brand_id,
78
-                        brand_name=coupon.brand_name,
79
-                        coupon_id=coupon_id,
80
-                        user_id=user_id,
81
-                        coupon_title=coupon.coupon_title,
82
-                        coupon_detail=coupon.coupon_detail,
83
-                        coupon_value=coupon.coupon_value,
84
-                        coupon_image=coupon.coupon_image,
85
-                        active_at=active_at,
86
-                        expire_at=expire_at,
87
-                        coupon_valid_period=coupon.coupon_valid_period,
88
-                        coupon_limit_model_ids=coupon.coupon_limit_model_ids,
89
-                    )
90
-
91
-            user.coupon_expire_at = expire_at
92
-            user.save()
47
+                active_at = user.coupon_expire_at
48
+                expire_at = tc.utc_datetime(user.coupon_expire_at, days=365)
49
+
50
+                # 发放会员权益
51
+                rights = RightInfo.objects.filter(is_send_coupon=True, is_continue_send_coupon=True, status=True)
52
+                for right in rights:
53
+                    if user.level == UserInfo.MEMBER_LRC:
54
+                        coupon_id = right.coupon_level1_id
55
+                        coupon_num = right.coupon_level1_num
56
+                    elif user.level == UserInfo.MEMBER_SILVER:
57
+                        coupon_id = right.coupon_level2_id
58
+                        coupon_num = right.coupon_level2_num
59
+                    elif user.level == UserInfo.MEMBER_GOLD:
60
+                        coupon_id = right.coupon_level3_id
61
+                        coupon_num = right.coupon_level3_num
62
+                    elif user.level == UserInfo.MEMBER_WHITE_GOLD:
63
+                        coupon_id = right.coupon_level4_id
64
+                        coupon_num = right.coupon_level4_num
65
+                    elif user.level == UserInfo.MEMBER_BLACK_GOLD:
66
+                        coupon_id = right.coupon_level5_id
67
+                        coupon_num = right.coupon_level5_num
68
+
69
+                    if not coupon_id:
70
+                        continue
71
+
72
+                    try:
73
+                        coupon = CouponInfo.objects.get(coupon_id=coupon_id)
74
+                    except CouponInfo.DoesNotExist:
75
+                        continue
76
+
77
+                    for _ in range(right.coupon_num or coupon_num):
78
+                        UserCouponInfo.objects.create(
79
+                            brand_id=coupon.brand_id,
80
+                            brand_name=coupon.brand_name,
81
+                            coupon_id=coupon_id,
82
+                            user_id=user_id,
83
+                            coupon_title=coupon.coupon_title,
84
+                            coupon_detail=coupon.coupon_detail,
85
+                            coupon_value=coupon.coupon_value,
86
+                            coupon_image=coupon.coupon_image,
87
+                            active_at=active_at,
88
+                            expire_at=expire_at,
89
+                            coupon_valid_period=coupon.coupon_valid_period,
90
+                            coupon_limit_model_ids=coupon.coupon_limit_model_ids,
91
+                        )
92
+
93
+                user.coupon_expire_at = expire_at
94
+                user.save()
93 95
 
94 96
             close_old_connections()

+ 1 - 1
member/admin.py

@@ -110,7 +110,7 @@ class MemberActivityContributionWelfareInfoAdmin(admin.ModelAdmin):
110 110
 
111 111
 
112 112
 class MemberActivityContributionWelfareUnlockingInfoAdmin(admin.ModelAdmin):
113
-    list_display = ('unlocking_id', 'admin_id', 'user_id', 'activity_id', 'contribution_id', 'welfare_id', 'name', 'phone', 'address', 'tracking_number', 'is_handled', 'status', 'created_at', 'updated_at')
113
+    list_display = ('unlocking_id', 'admin_id', 'user_id', 'activity_id', 'contribution_id', 'welfare_id', 'welfare_type', 'welfare_value', 'name', 'phone', 'address', 'tracking_number', 'is_handled', 'status', 'created_at', 'updated_at')
114 114
     list_filter = ('admin_id', 'activity_id', 'welfare_id', 'is_handled', 'status')
115 115
 
116 116
 

+ 19 - 0
member/migrations/0046_memberactivitycontributionwelfareunlockinginfo_welfare_value.py

@@ -0,0 +1,19 @@
1
+# -*- coding: utf-8 -*-
2
+# Generated by Django 3.2.16 on 2022-10-27 10:38
3
+
4
+from django.db import migrations, models
5
+
6
+
7
+class Migration(migrations.Migration):
8
+
9
+    dependencies = [
10
+        ('member', '0045_auto_20221026_2102'),
11
+    ]
12
+
13
+    operations = [
14
+        migrations.AddField(
15
+            model_name='memberactivitycontributionwelfareunlockinginfo',
16
+            name='welfare_value',
17
+            field=models.IntegerField(default=0, help_text='福利数量', verbose_name='welfare_value'),
18
+        ),
19
+    ]

+ 19 - 0
member/migrations/0047_memberactivitycontributionwelfareunlockinginfo_welfare_type.py

@@ -0,0 +1,19 @@
1
+# -*- coding: utf-8 -*-
2
+# Generated by Django 3.2.16 on 2022-10-27 10:46
3
+
4
+from django.db import migrations, models
5
+
6
+
7
+class Migration(migrations.Migration):
8
+
9
+    dependencies = [
10
+        ('member', '0046_memberactivitycontributionwelfareunlockinginfo_welfare_value'),
11
+    ]
12
+
13
+    operations = [
14
+        migrations.AddField(
15
+            model_name='memberactivitycontributionwelfareunlockinginfo',
16
+            name='welfare_type',
17
+            field=models.IntegerField(choices=[(0, '实物'), (1, '积分'), (2, '虚拟')], db_index=True, default=0, help_text='福利类型', verbose_name='welfare_type'),
18
+        ),
19
+    ]

+ 3 - 0
member/models.py

@@ -795,6 +795,7 @@ class MemberActivityContributionWelfareInfo(BaseModelMixin, BrandInfoMixin):
795 795
 
796 796
 
797 797
 class MemberActivityContributionWelfareUnlockingInfo(BaseModelMixin, BrandInfoMixin):
798
+    WELFARE_INTEGRAL = 1
798 799
     WELFARE_TYPE = (
799 800
         (0, u'实物'),
800 801
         (1, u'积分'),
@@ -811,6 +812,8 @@ class MemberActivityContributionWelfareUnlockingInfo(BaseModelMixin, BrandInfoMi
811 812
     contribution_id = models.CharField(_(u'contribution_id'), max_length=32, blank=True, null=True, help_text=u'投稿唯一标识', db_index=True)
812 813
 
813 814
     welfare_id = models.CharField(_(u'welfare_id'), max_length=32, blank=True, null=True, help_text=u'福利唯一标识', db_index=True)
815
+    welfare_type = models.IntegerField(_(u'welfare_type'), choices=WELFARE_TYPE, default=0, help_text=u'福利类型', db_index=True)
816
+    welfare_value = models.IntegerField(_(u'welfare_value'), default=0, help_text=_(u'福利数量'))
814 817
 
815 818
     name = models.CharField(_(u'name'), max_length=255, blank=True, null=True, help_text=u'姓名')
816 819
     phone = models.CharField(_(u'phone'), max_length=255, blank=True, null=True, help_text=u'电话')

+ 6 - 5
miniapp/views.py

@@ -318,19 +318,20 @@ def user_integral_add(request):
318 318
         return response(ProductBrandStatusCode.BRAND_NOT_MATCH)
319 319
 
320 320
     try:
321
-        user = UserInfo.objects.get(user_id=user_id, status=True)
321
+        user = UserInfo.objects.select_for_update().get(user_id=user_id, status=True)
322 322
     except UserInfo.DoesNotExist:
323 323
         return response(UserStatusCode.USER_NOT_FOUND)
324 324
 
325
+    user.integral += integral
326
+    user.save()
327
+
325 328
     UserIntegralIncomeExpensesInfo.objects.create(
326 329
         brand_id=brand_id,
327 330
         user_id=user_id,
328 331
         integral_from=UserIntegralIncomeExpensesInfo.CONTRIBUTE,
329 332
         integral=integral,
330
-        remark=remark
333
+        final_integral=user.integral,
334
+        remark=remark,
331 335
     )
332 336
 
333
-    user.integral += integral
334
-    user.save()
335
-
336 337
     return response(200, 'Add User Integral Success', u'添加用户投稿积分成功')

+ 74 - 73
utils/error/errno_utils.py

@@ -8,6 +8,78 @@ class ParamStatusCode(BaseStatusCode):
8 8
     PARAM_NOT_FOUND = StatusCodeField(400000, 'Param Not Found', description=u'参数不存在')
9 9
 
10 10
 
11
+class PermissionStatusCode(BaseStatusCode):
12
+    """ 4099xx 权限相关错误码 """
13
+    PERMISSION_DENIED = StatusCodeField(409900, 'Permission Denied', description=u'权限不足')
14
+
15
+
16
+class AdministratorStatusCode(BaseStatusCode):
17
+    """ 操作员相关错误码 4002xx """
18
+    ADMINISTRATOR_NOT_FOUND = StatusCodeField(400201, 'Administrator Not Found', description=u'管理员不存在')
19
+    ADMINISTRATOR_PERMISSION_DENIED = StatusCodeField(508002, 'Administrator Permission Denied', description=u'管理员权限不足')
20
+
21
+    # 密码
22
+    ADMINISTRATOR_PASSWORD_ERROR = StatusCodeField(400202, 'Administrator Password Error', description=u'管理员密码错误')
23
+    # 手机号
24
+    ADMINISTRATOR_PHONE_ALREADY_EXISTS = StatusCodeField(400205, 'Administrator Phone Already Exists', description=u'管理员手机号已经存在')
25
+    # 状态
26
+    ADMINISTRATOR_NOT_ACTIVATED = StatusCodeField(400215, 'Administrator Not Activated', description=u'管理员未激活')
27
+    ADMINISTRATOR_HAS_DISABLED = StatusCodeField(400216, 'Administrator Has Disabled', description=u'管理员已禁用')
28
+    ADMINISTRATOR_HAS_DELETED = StatusCodeField(400217, 'Administrator Has Deleted', description=u'管理员已删除')
29
+    # 管理员
30
+    MAINTENANCE_NOT_FOUND = StatusCodeField(400251, 'Maintenance Not Found', description=u'核销员不存在')
31
+
32
+
33
+class OperatorStatusCode(BaseStatusCode):
34
+    """ 操作员相关错误码 4003xx """
35
+    OPERATOR_NOT_FOUND = StatusCodeField(400301, 'Operator Not Found', description=u'操作员不存在')
36
+    # 密码
37
+    OPERATOR_PASSWORD_ERROR = StatusCodeField(400302, 'Operator Password Error', description=u'操作员密码错误')
38
+    # 手机号
39
+    OPERATOR_PHONE_ALREADY_EXISTS = StatusCodeField(400305, 'Operator Phone Already Exists', description=u'操作员手机号已经存在')
40
+    # 状态
41
+    OPERATOR_NOT_ACTIVATED = StatusCodeField(400315, 'Operator Not Activated', description=u'操作员未激活')
42
+    OPERATOR_HAS_DISABLED = StatusCodeField(400316, 'Operator Has Disabled', description=u'操作员已禁用')
43
+    OPERATOR_HAS_DELETED = StatusCodeField(400317, 'Operator Has Deleted', description=u'操作员已删除')
44
+
45
+
46
+class UserStatusCode(BaseStatusCode):
47
+    """ 用户相关错误码  4005xx """
48
+    USER_NOT_FOUND = StatusCodeField(400501, 'User Not Found', description=u'用户不存在')
49
+    USER_PASSWORD_ERROR = StatusCodeField(400502, 'User Password Error', description=u'用户密码错误')
50
+    USERNAME_HAS_REGISTERED = StatusCodeField(400503, 'Username Has Registered', description=u'用户名已注册')
51
+    # 游客
52
+    GUEST_NOT_ALLOWED = StatusCodeField(400511, 'Guest Not ALLOWED', description=u'游客登录未开启')
53
+    # 身份
54
+    USER_NOT_LENSMAN = StatusCodeField(400521, 'User Not Lensman', description=u'用户非摄影师')
55
+    USER_NOT_TOURGUIDE = StatusCodeField(400522, 'User Not Tourguide', description=u'用户非导游')
56
+
57
+
58
+class PhoneStatusCode(BaseStatusCode):
59
+    """ 手机相关错误码  4006xx """
60
+    PHONE_NOT_FOUND = StatusCodeField(400601, 'Phone Not Found', description=u'手机不存在')
61
+
62
+
63
+class WechatStatusCode(BaseStatusCode):
64
+    """ 微信相关错误码  4007xx """
65
+    WECHAT_NOT_FOUND = StatusCodeField(400701, 'Wechat Not Found', description=u'微信不存在')
66
+    UNIONID_NOT_FOUND = StatusCodeField(400702, 'Unionid Not Found', description=u'微信 UNIONID 不存在')
67
+    OPENID_NOT_FOUND = StatusCodeField(400703, 'OPENID Not Found', description=u'微信 OPENID 不存在')
68
+
69
+
70
+class ScreenStatusCode(BaseStatusCode):
71
+    """ 群组/团相关错误码 4030xx """
72
+    QRCODE_NOT_SCAN = StatusCodeField(403001, 'QRCode Not Scan', description=u'二维码未扫描')
73
+
74
+
75
+class CouponStatusCode(BaseStatusCode):
76
+    """ 4050xx 优惠劵相关错误码 """
77
+    COUPON_NOT_FOUND = StatusCodeField(405001, 'Coupon Not Found', description=u'劵不存在')
78
+    COUPON_EXPIRED = StatusCodeField(405002, 'Coupon Expired', description=u'劵已过期')
79
+    COUPON_PERMISSION_DENIED = StatusCodeField(405003, 'Permission Denied', description=u'核销劵权限不足')
80
+    COUPON_HAS_USED = StatusCodeField(405004, 'Coupon Has Used', description=u'劵已核销')
81
+
82
+
11 83
 class SaleclerkStatusCode(BaseStatusCode):
12 84
     """ 店员相关错误码 5001xx """
13 85
     CLERK_NOT_FOUND = StatusCodeField(500101, 'Clerk Not Found', description=u'店员不存在')
@@ -107,7 +179,8 @@ class MemberActivityContributionWelfareStatusCode(BaseStatusCode):
107 179
 
108 180
 class MemberActivityContributionWelfareUnblockingStatusCode(BaseStatusCode):
109 181
     """ 会员活动投稿福利相关错误码 5039xx """
110
-    ACTIVITY_CONTRIBUTION_WELFARE_UNBLOCKING_NOT_FOUND = StatusCodeField(503999, 'Activity Contribution Welfare Unblocking Not Found', description=u'活动投稿福利解锁不存在')
182
+    ACTIVITY_CONTRIBUTION_WELFARE_UNBLOCKING_NOT_FOUND = StatusCodeField(503901, 'Activity Contribution Welfare Unblocking Not Found', description=u'活动投稿福利解锁不存在')
183
+    ACTIVITY_CONTRIBUTION_WELFARE_UNBLOCKING_HAS_HANDLED = StatusCodeField(503902, 'Activity Contribution Welfare Unblocking Has Handled', description=u'活动投稿福利解锁已处理')
111 184
 
112 185
 
113 186
 class MemberCouponStatusCode(BaseStatusCode):
@@ -138,75 +211,3 @@ class MaintenanceStatusCode(BaseStatusCode):
138 211
     """ 维修相关错误码 5080xx """
139 212
     MAINTENACE_NOT_FOUND = StatusCodeField(508001, 'Maintenance Not Found', description=u'维修不存在')
140 213
     MAINTENACE_PERMISSION_DENIED = StatusCodeField(508002, 'Maintenance Permission Denied', description=u'维修权限不足')
141
-
142
-
143
-class AdministratorStatusCode(BaseStatusCode):
144
-    """ 操作员相关错误码 4002xx """
145
-    ADMINISTRATOR_NOT_FOUND = StatusCodeField(400201, 'Administrator Not Found', description=u'管理员不存在')
146
-    ADMINISTRATOR_PERMISSION_DENIED = StatusCodeField(508002, 'Administrator Permission Denied', description=u'管理员权限不足')
147
-
148
-    # 密码
149
-    ADMINISTRATOR_PASSWORD_ERROR = StatusCodeField(400202, 'Administrator Password Error', description=u'管理员密码错误')
150
-    # 手机号
151
-    ADMINISTRATOR_PHONE_ALREADY_EXISTS = StatusCodeField(400205, 'Administrator Phone Already Exists', description=u'管理员手机号已经存在')
152
-    # 状态
153
-    ADMINISTRATOR_NOT_ACTIVATED = StatusCodeField(400215, 'Administrator Not Activated', description=u'管理员未激活')
154
-    ADMINISTRATOR_HAS_DISABLED = StatusCodeField(400216, 'Administrator Has Disabled', description=u'管理员已禁用')
155
-    ADMINISTRATOR_HAS_DELETED = StatusCodeField(400217, 'Administrator Has Deleted', description=u'管理员已删除')
156
-    # 管理员
157
-    MAINTENANCE_NOT_FOUND = StatusCodeField(400251, 'Maintenance Not Found', description=u'核销员不存在')
158
-
159
-
160
-class OperatorStatusCode(BaseStatusCode):
161
-    """ 操作员相关错误码 4003xx """
162
-    OPERATOR_NOT_FOUND = StatusCodeField(400301, 'Operator Not Found', description=u'操作员不存在')
163
-    # 密码
164
-    OPERATOR_PASSWORD_ERROR = StatusCodeField(400302, 'Operator Password Error', description=u'操作员密码错误')
165
-    # 手机号
166
-    OPERATOR_PHONE_ALREADY_EXISTS = StatusCodeField(400305, 'Operator Phone Already Exists', description=u'操作员手机号已经存在')
167
-    # 状态
168
-    OPERATOR_NOT_ACTIVATED = StatusCodeField(400315, 'Operator Not Activated', description=u'操作员未激活')
169
-    OPERATOR_HAS_DISABLED = StatusCodeField(400316, 'Operator Has Disabled', description=u'操作员已禁用')
170
-    OPERATOR_HAS_DELETED = StatusCodeField(400317, 'Operator Has Deleted', description=u'操作员已删除')
171
-
172
-
173
-class UserStatusCode(BaseStatusCode):
174
-    """ 用户相关错误码  4005xx """
175
-    USER_NOT_FOUND = StatusCodeField(400501, 'User Not Found', description=u'用户不存在')
176
-    USER_PASSWORD_ERROR = StatusCodeField(400502, 'User Password Error', description=u'用户密码错误')
177
-    USERNAME_HAS_REGISTERED = StatusCodeField(400503, 'Username Has Registered', description=u'用户名已注册')
178
-    # 游客
179
-    GUEST_NOT_ALLOWED = StatusCodeField(400511, 'Guest Not ALLOWED', description=u'游客登录未开启')
180
-    # 身份
181
-    USER_NOT_LENSMAN = StatusCodeField(400521, 'User Not Lensman', description=u'用户非摄影师')
182
-    USER_NOT_TOURGUIDE = StatusCodeField(400522, 'User Not Tourguide', description=u'用户非导游')
183
-
184
-
185
-class PhoneStatusCode(BaseStatusCode):
186
-    """ 手机相关错误码  4006xx """
187
-    PHONE_NOT_FOUND = StatusCodeField(400601, 'Phone Not Found', description=u'手机不存在')
188
-
189
-
190
-class WechatStatusCode(BaseStatusCode):
191
-    """ 微信相关错误码  4007xx """
192
-    WECHAT_NOT_FOUND = StatusCodeField(400701, 'Wechat Not Found', description=u'微信不存在')
193
-    UNIONID_NOT_FOUND = StatusCodeField(400702, 'Unionid Not Found', description=u'微信 UNIONID 不存在')
194
-    OPENID_NOT_FOUND = StatusCodeField(400703, 'OPENID Not Found', description=u'微信 OPENID 不存在')
195
-
196
-
197
-class ScreenStatusCode(BaseStatusCode):
198
-    """ 群组/团相关错误码 4030xx """
199
-    QRCODE_NOT_SCAN = StatusCodeField(403001, 'QRCode Not Scan', description=u'二维码未扫描')
200
-
201
-
202
-class PermissionStatusCode(BaseStatusCode):
203
-    """ 4099xx 权限相关错误码 """
204
-    PERMISSION_DENIED = StatusCodeField(409900, 'Permission Denied', description=u'权限不足')
205
-
206
-
207
-class CouponStatusCode(BaseStatusCode):
208
-    """ 4050xx 优惠劵相关错误码 """
209
-    COUPON_NOT_FOUND = StatusCodeField(405001, 'Coupon Not Found', description=u'劵不存在')
210
-    COUPON_EXPIRED = StatusCodeField(405002, 'Coupon Expired', description=u'劵已过期')
211
-    COUPON_PERMISSION_DENIED = StatusCodeField(405003, 'Permission Denied', description=u'核销劵权限不足')
212
-    COUPON_HAS_USED = StatusCodeField(405004, 'Coupon Has Used', description=u'劵已核销')