Browse Source

修改多国家上传逻辑

YPZ 3 tuần trước cách đây
mục cha
commit
e0d531e0dd

+ 81 - 0
java/storlead-sasa/storlead-trade/src/main/java/com/storlead/trade/service/impl/MarketingCampaignServiceImpl.java

@@ -5,6 +5,7 @@ import com.storlead.framework.common.constant.DSConstants;
 
 
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
@@ -35,6 +36,7 @@ import java.util.Date;
 import java.util.HashMap;
 import java.util.List;
 import java.util.Map;
+import java.util.function.Consumer;
 import java.util.stream.Collectors;
 import java.time.LocalDate;
 import java.time.ZoneId;
@@ -125,9 +127,88 @@ public class MarketingCampaignServiceImpl
             marketingCampaignVOList.get(i).setCustomerList(customerListI);
         }
 
+        // ===== 营销活动维度统计(基于 market_emails 表)=====
+        if (!CollectionUtils.isEmpty(marketingCampaignIdList)) {
+            Map<Long, Long> openedMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(distinct customer_id) as cnt", qw -> qw.eq("has_reader", 1));
+            Map<Long, Long> repliedMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(distinct customer_id) as cnt", qw -> qw.eq("has_reply", 1));
+            Map<Long, Long> protectMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(distinct customer_id) as cnt", qw -> qw.eq("has_protect", 1));
+            Map<Long, Long> pendingMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(*) as cnt", qw -> qw.eq("status", -1));
+            Map<Long, Long> sentMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(*) as cnt", qw -> qw.eq("status", 1));
+            Map<Long, Long> sentCustomerMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(distinct customer_id) as cnt", qw -> qw.eq("status", 1));
+            Map<Long, Long> cancelledMap = countEmailsByCampaign(marketingCampaignIdList,
+                    "count(*) as cnt", qw -> qw.eq("status", -3));
+            for (MarketingCampaignVO vo : marketingCampaignVOList) {
+                Long id = vo.getId();
+                vo.setOpenedCustomerCount(toInt(openedMap.get(id)));
+                vo.setRepliedCustomerCount(toInt(repliedMap.get(id)));
+                vo.setProtectWhitelistCount(toInt(protectMap.get(id)));
+                vo.setPendingEmailCount(toInt(pendingMap.get(id)));
+                vo.setSentEmailCount(toInt(sentMap.get(id)));
+                vo.setCancelledEmailCount(toInt(cancelledMap.get(id)));
+                int sentCustomer = toInt(sentCustomerMap.get(id));
+                vo.setSentCustomerCount(sentCustomer);
+                vo.setOpenRateText(buildRate(toInt(openedMap.get(id)), sentCustomer));
+                vo.setReplyRateText(buildRate(toInt(repliedMap.get(id)), sentCustomer));
+            }
+        }
+
         return Result.result(pageVO);
     }
 
+    /**
+     * 按营销活动分组统计 market_emails 数量。
+     *
+     * @param campaignIds 营销活动 id 列表
+     * @param selectExpr  聚合表达式,例如 "count(distinct customer_id) as cnt" 或 "count(*) as cnt"
+     * @param extra       额外过滤条件(如 has_reader=1 / status=-1)
+     * @return key=marketing_campaign_id, value=聚合结果
+     */
+    private Map<Long, Long> countEmailsByCampaign(List<Long> campaignIds, String selectExpr,
+            Consumer<QueryWrapper<MarketEmailsEntity>> extra) {
+        QueryWrapper<MarketEmailsEntity> qw = new QueryWrapper<>();
+        qw.select("marketing_campaign_id, " + selectExpr);
+        qw.in("marketing_campaign_id", campaignIds);
+        qw.eq("is_delete", CommonConstant.DEL_FLAG_0);
+        if (extra != null) {
+            extra.accept(qw);
+        }
+        qw.groupBy("marketing_campaign_id");
+        List<Map<String, Object>> maps = marketEmailsService.listMaps(qw);
+        Map<Long, Long> result = new HashMap<>(maps == null ? 1 : maps.size());
+        if (maps != null) {
+            for (Map<String, Object> m : maps) {
+                Object cid = m.get("marketing_campaign_id");
+                Object cnt = m.get("cnt");
+                if (cid == null || cnt == null) {
+                    continue;
+                }
+                result.put(((Number) cid).longValue(), ((Number) cnt).longValue());
+            }
+        }
+        return result;
+    }
+
+    private Integer toInt(Long v) {
+        return v == null ? 0 : v.intValue();
+    }
+
+    /**
+     * 计算百分比并带 % 返回。denominator <= 0 时返回 "0%"。
+     */
+    private String buildRate(int numerator, int denominator) {
+        if (denominator <= 0) {
+            return "0%";
+        }
+        int pct = (int) Math.round(numerator * 100.0 / denominator);
+        return pct + "%";
+    }
+
     @Override
     public Result<Object> getDetailById(Long id) {
         if (id == null) {

+ 27 - 0
java/storlead-sasa/storlead-trade/src/main/java/com/storlead/trade/vo/MarketingCampaignVO.java

@@ -157,4 +157,31 @@ public class MarketingCampaignVO extends SysBaseField {
 
     @ApiModelProperty(value = "关联客户信息")
     private List<CustomerEntity> customerList;
+
+    @ApiModelProperty(value = "统计:打开邮件的客户数(去重 customer_id, has_reader=1)")
+    private Integer openedCustomerCount;
+
+    @ApiModelProperty(value = "统计:回复邮件的客户数(去重 customer_id, has_reply=1)")
+    private Integer repliedCustomerCount;
+
+    @ApiModelProperty(value = "统计:客户保护白名单数(去重 customer_id, has_protect=1)")
+    private Integer protectWhitelistCount;
+
+    @ApiModelProperty(value = "统计:待发送邮件数(status=-1)")
+    private Integer pendingEmailCount;
+
+    @ApiModelProperty(value = "统计:已发送邮件数(status=1)")
+    private Integer sentEmailCount;
+
+    @ApiModelProperty(value = "统计:已取消邮件数(status=-3)")
+    private Integer cancelledEmailCount;
+
+    @ApiModelProperty(value = "统计:已发送客户数(去重 customer_id, status=1)")
+    private Integer sentCustomerCount;
+
+    @ApiModelProperty(value = "统计:打开率(百分比字符串,如 45%,客户维度)")
+    private String openRateText;
+
+    @ApiModelProperty(value = "统计:回复率(百分比字符串,如 8%,客户维度)")
+    private String replyRateText;
 }