Эх сурвалжийг харах

1.开屏广告增加pad图片 2.轮播广告增加tag字段 3.添加设备筛选功能

linhaohong 1 жил өмнө
parent
commit
5cad128345

+ 46 - 27
AdminController/CampaignController.py

@@ -69,13 +69,10 @@ class CampaignView(View):
         unknown_country = 0
 
         try:
-            # 连接并获取国家和设备类型
+            # 连接并获取国家
             country_prefetch = Prefetch('country', queryset=CountryModel.objects.only('country_name'),
                                         to_attr='country_list')
-            device_type_prefetch = Prefetch('device_type', queryset=DeviceTypeModel.objects.only('name'),
-                                            to_attr='device_type_list')
-            app_advertise_campaign_qs = AppAdvertiseCampaign.objects.prefetch_related(country_prefetch,
-                                                                                      device_type_prefetch)
+            app_advertise_campaign_qs = AppAdvertiseCampaign.objects.prefetch_related(country_prefetch)
 
             # 过滤
             if campaign_name:
@@ -128,7 +125,8 @@ class CampaignView(View):
                     'campaign_show_etime': campaign.campaign_show_etime,
                     'app_bundle_type': campaign.app_bundle_type,
                     'countries': countries,
-                    'device_types': ",".join([device.name for device in campaign.device_type_list]),
+                    'device_types': campaign.device_type,
+                    'ex_device_types': campaign.ex_device_type
                 }
                 if campaign.image_url == "":
                     del campaign_data['image_url']
@@ -163,14 +161,16 @@ class CampaignView(View):
             campaign_show_etime = request_dict.get('campaign_show_etime', 86399)
             app_bundle_type = request_dict.get('app_bundle_type', None)
             poster_file = request.FILES.get('posterFile', None)
+            poster_pad_file = request.FILES.get('posterPadFile', None)
             banner_files = request.FILES.getlist('bannerFiles', None)
-            banner_campaign_urls = json.loads(request_dict.get('banner_campaign_url', "[]"))
+            banner_fields = json.loads(request_dict.get('banner_fields', "[]"))  # 轮播字段
             device_type_names = json.loads(request_dict.get('device_type_list', "[]"))  # 设备类型名称列表
+            ex_device_type_names = json.loads(request_dict.get('ex_device_type_list', "[]"))
             country_name_list = json.loads(request_dict.get('country_name_list', "[]"))  # 地区列表
 
-            required_fields = [campaign_name, campaign_start_time, campaign_end_time,
-                               app_bundle_type]
-            list_fields = [device_type_names, country_name_list]
+            required_fields = [campaign_name, campaign_start_time, campaign_end_time, app_bundle_type]
+
+            list_fields = [country_name_list]
 
             # 检查基本字段是否为None
             if any(field is None for field in required_fields):
@@ -184,6 +184,12 @@ class CampaignView(View):
             if not poster_file and not banner_files:
                 return response.json(444)
 
+            # 不包含设备和包含设备不能重复
+            if device_type_names and ex_device_type_names:
+                intersection = list(set(device_type_names).intersection(set(ex_device_type_names)))
+                if intersection:
+                    return response.json(10, "设备包含和设备不包含不能重复")
+
             # 针对特殊地区的处理,表没设计好用这个处理挽救一下
             unknown_country = 0
             if "未知地区" in country_name_list:
@@ -195,14 +201,16 @@ class CampaignView(View):
                                                         "BannerAdvertise") if banner_files is not None else []
             poster_image_url = self.upload_files_to_s3(poster_file,
                                                        "OpenScreenAdvertise")[0] if poster_file is not None else ""
+            pad_image_url = self.upload_files_to_s3(poster_file,
+                                                    "OpenScreenAdvertise")[0] if poster_pad_file is not None else ""
             campaign_type = []
             if poster_image_url != "":
                 campaign_type.append(1)
 
             if banner_image_urls:
                 campaign_type.append(2)
-                banner_campaign = [{"image": image_url, "url": campaign_url}
-                                   for image_url, campaign_url in zip(banner_image_urls, banner_campaign_urls)]
+                banner_campaign = [{"image": image_url, "url": cam_field["url"], "tag": int(cam_field["tag"])}
+                                   for image_url, cam_field in zip(banner_image_urls, banner_fields)]
             else:
                 banner_campaign = []
 
@@ -211,6 +219,7 @@ class CampaignView(View):
             # 创建 AppAdvertiseCampaign 实例
             new_campaign = AppAdvertiseCampaign.objects.create(
                 image_url=poster_image_url,
+                pad_image_url=pad_image_url,
                 campaign_name=campaign_name,
                 campaign_url=campaign_url,
                 banner_campaign=banner_campaign,
@@ -224,13 +233,10 @@ class CampaignView(View):
                 campaign_show_etime=campaign_show_etime,
                 create_time=create_time,
                 update_time=update_time,
+                ex_device_type=ex_device_type_names,
+                device_type=device_type_names
             )
 
-            # 根据名称查找 DeviceTypeModel 的实例并建立关系
-            device_type_instances = DeviceTypeModel.objects.filter(name__in=device_type_names)
-            for device_type_instance in device_type_instances:
-                new_campaign.device_type.add(device_type_instance)
-
             # 根据 ID 关联 CountryModel 实例
             country_instances = CountryModel.objects.filter(country_name__in=country_name_list)
             for country_instance in country_instances:
@@ -260,6 +266,7 @@ class CampaignView(View):
             campaign_show_etime = request_dict.get('campaign_show_etime', None)
             app_bundle_type = request_dict.get('app_bundle_type', None)
             device_type_names = json.loads(request_dict.get('device_type_list', "[]"))  # 设备类型名称列表
+            ex_device_type_names = json.loads(request_dict.get('ex_device_type_list', "[]"))
             country_name_list = json.loads(request_dict.get('country_name_list', "[]"))  # 地区列表
             poster_file = request.FILES.get('posterFile', None)
 
@@ -267,9 +274,9 @@ class CampaignView(View):
             sort_files = json.loads(request_dict.get('sort_files', "[]"))
             banner_files = request.FILES.getlist('bannerFiles', None)
 
-            # 更改轮播图链接
+            # 更改轮播图 字段
             sort_urls = json.loads(request_dict.get('sort_url', "[]"))
-            banner_urls = json.loads(request_dict.get('banner_urls', "[]"))
+            banner_fields = json.loads(request_dict.get('banner_fields', "[]"))
 
             # 删除轮播图广告
             sort_banner_del = json.loads(request_dict.get('sort_banner_del', "[]"))
@@ -319,14 +326,15 @@ class CampaignView(View):
                     campaign.campaign_type.append(2)
 
             # 更改轮播广告链接
-            if banner_urls:
+            if banner_fields:
                 url_num = 0
                 for sort in sort_urls:
                     if sort > len(campaign.banner_campaign):
                         campaign.banner_campaign.append({})
                         if sort not in sort_files:
                             return response.json(10, "图片需要和链接对应")
-                    campaign.banner_campaign[sort - 1]["url"] = banner_urls[url_num]
+                    campaign.banner_campaign[sort - 1]["url"] = banner_fields[url_num]["url"]
+                    campaign.banner_campaign[sort - 1]["tag"] = banner_fields[url_num]["tag"]
                     url_num = url_num + 1
 
             # 添加删除轮播图列表
@@ -363,11 +371,12 @@ class CampaignView(View):
                 campaign.campaign_show_stime = campaign_show_stime
             if campaign_show_etime is not None:
                 campaign.campaign_show_etime = campaign_show_etime
-
-            # 更新多对多字段 - 设备类型
-            if device_type_names:
-                device_types = DeviceTypeModel.objects.filter(name__in=device_type_names)
-                campaign.device_type.set(device_types)
+            if campaign_show_etime is not None:
+                campaign.campaign_show_etime = campaign_show_etime
+            if device_type_names is not None:
+                campaign.device_type = device_type_names
+            if ex_device_type_names is not None:
+                campaign.ex_device_type = ex_device_type_names
 
             # 更新多对多字段 - 国家/地区
             if country_name_list:
@@ -405,7 +414,6 @@ class CampaignView(View):
                     banner_campaign_list.append(banner)
                 self.del_file_to_s3(banner_campaign_list)
             # 清除多对多关系
-            campaign.device_type.clear()
             campaign.country.clear()
             # 保留在广告表中
             campaign.status = 2
@@ -437,6 +445,12 @@ class CampaignView(View):
             return response.json(500, 'error_line:{}, error_msg:{}'.format(e.__traceback__.tb_lineno, repr(e)))
 
     def get_user_behavior_log(self, request_dict, response):
+        """
+        记录日志
+        @param request_dict: dict
+        @param response:
+        @return:
+        """
         campaign_ids = json.loads(request_dict.get('campaign_id', '[]'))
         start_time = request_dict.get('start_time', None)
         end_time = request_dict.get('end_time', None)
@@ -485,6 +499,11 @@ class CampaignView(View):
             return response.json(500, 'error_line:{}, error_msg:{}'.format(e.__traceback__.tb_lineno, repr(e)))
 
     def get_country_list(self, response):
+        """
+        获取国家列表
+        @param response:
+        @return:
+        """
         try:
             if SERVER_TYPE == 'Ansjer.us_config.formal_settings':
                 region_api = 'https://www.dvema.com/'

+ 24 - 9
Controller/CampaignController/AppCampaignController.py

@@ -3,11 +3,12 @@ import pytz
 from datetime import datetime
 from datetime import time as Time
 
-from Model.models import AppAdvertiseCampaign, DeviceTypeModel, CountryModel, Device_User, OpenScreenCampaign
+from Model.models import AppAdvertiseCampaign, DeviceTypeModel, CountryModel, Device_User, OpenScreenCampaign, \
+    Device_Info
 from Ansjer.config import SERVER_TYPE
 
 from django.views import View
-from django.db.models import Prefetch
+from django.db.models import Prefetch, Q
 
 from Object.ResponseObject import ResponseObject
 from Object.TokenObject import TokenObject
@@ -68,19 +69,32 @@ class AppCampaignView(View):
                                               create_time=int(time.time()))
         try:
             country_prefetch = Prefetch('country', queryset=CountryModel.objects.only('id'), to_attr='country_list')
-            device_type_prefetch = Prefetch('device_type', queryset=DeviceTypeModel.objects.only('type'),
-                                            to_attr='device_type_list')
-            app_advertise_campaign_qs = AppAdvertiseCampaign.objects.prefetch_related(country_prefetch,
-                                                                                      device_type_prefetch)
 
-            device_info_qs = Device_User.objects.filter(userID=userID).values("region_country").first()
-            country_id = device_info_qs.get('region_country')
+            app_advertise_campaign_qs = AppAdvertiseCampaign.objects.all().prefetch_related(country_prefetch)
+
+            device_user_qs = Device_User.objects.filter(userID=userID).values("region_country").first()
+
+            device_info = Device_Info.objects.filter(userID=userID).values("Type")
+            device_type = DeviceTypeModel.objects.filter(type__in=device_info).values_list('name')
+
+            country_id = device_user_qs.get('region_country')
             if country_id != 0:
                 app_advertise_campaign_qs = app_advertise_campaign_qs.filter(country__id=country_id, status=1)
             else:
                 app_advertise_campaign_qs = app_advertise_campaign_qs.filter(status=1, unknown_country=1)
+
             if app_type is not None:
                 app_advertise_campaign_qs = app_advertise_campaign_qs.filter(app_bundle_type=app_type)
+
+            # 筛选和排除用户拥有的设备
+            q = Q()
+            q_ex = ~Q()
+            for device in device_type:
+                q.add(Q(device_type__contains=device), q.AND)
+                q_ex.add(Q(ex_device_type__contains=device), q.AND)
+            app_advertise_campaign_qs = app_advertise_campaign_qs.filter(
+                (q & q_ex) | (Q(device_type=[]) & Q(ex_device_type=[])))
+
             # 返回 广告名称、广告类型、开始时间、结束时间、广告图片、活动链接
             campaigns_list = []
 
@@ -113,6 +127,7 @@ class AppCampaignView(View):
                 campaigns_list.append({
                     'campaign_id': campaign.id,
                     'image_url': s3_url + campaign.image_url,
+                    'pad_image_url': s3_url + campaign.pad_image_url,
                     'banner_campaign': banner_campaign,
                     'campaign_url': campaign.campaign_url,
                     'campaign_name': campaign.campaign_name,
@@ -121,8 +136,8 @@ class AppCampaignView(View):
                     'end_date': campaign_end_date,
                     'start_time': campaign_start_firstday,
                     'end_time': campaign_end_firstday,
-                    'device_types': [device.type for device in campaign.device_type_list],
                 })
+
             return response.json(0, {
                 'interval_time': 86400,
                 'campaigns': campaigns_list

+ 3 - 1
Model/models.py

@@ -4802,11 +4802,13 @@ class DailyReconciliation(models.Model):
 class AppAdvertiseCampaign(models.Model):
     id = models.AutoField(primary_key=True, verbose_name='主键')
     image_url = models.CharField(default='', max_length=256, verbose_name='开屏广告图片url')
+    pad_image_url = models.CharField(default='', max_length=256, verbose_name='开屏广告pad端图片url')
     banner_campaign = models.JSONField(default=list, verbose_name='轮播广告')
     campaign_url = models.CharField(default='', max_length=256, verbose_name='活动链接')
     campaign_name = models.CharField(default='', max_length=32, verbose_name='广告名称')
     campaign_type = models.JSONField(default=list, verbose_name='广告类型')  # 1:开屏广告 # 2:轮播广告
-    device_type = models.ManyToManyField(to="DeviceTypeModel", verbose_name='设备类型')
+    device_type = models.JSONField(default=list, verbose_name='设备类型')
+    ex_device_type = models.JSONField(default=list, verbose_name='排除设备类型')
     status = models.SmallIntegerField(default=0, verbose_name='广告状态')  # 0:关闭 1:开启 2:删除
     country = models.ManyToManyField(to="CountryModel", verbose_name='广告地区')
     unknown_country = models.SmallIntegerField(default=0, verbose_name='未知地区')  # 0表示不包括 1表示包括