Bladeren bron

Merge branch 'dev/lwh' into dev/lh

# Conflicts:
#	pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/TcpDataServiceImpl.java
lh 1 week geleden
bovenliggende
commit
5e898dc385
18 gewijzigde bestanden met toevoegingen van 275 en 189 verwijderingen
  1. 1 61
      docker-compose.yml
  2. 3 0
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/dto/mongo/SaveDeviceInfoDTO.java
  3. 1 1
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/dto/mongo/SaveTcpMessageDTO.java
  4. 1 0
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/MarketingApps.java
  5. 3 2
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/mongo/Device.java
  6. 1 1
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/mongo/Message.java
  7. 21 0
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/feign/RemoteMarketingService.java
  8. 6 0
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/vo/app/PageMarketingAppsVO.java
  9. 3 0
      pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/vo/mongo/PageDeviceInfoVO.java
  10. 5 0
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/config/PushValidationConfig.java
  11. 2 0
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/controller/MarketingAppsController.java
  12. 67 51
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MarketingAppsServiceImpl.java
  13. 100 41
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MarketingConfigServiceImpl.java
  14. 22 22
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MktMgmtHandPushServiceImpl.java
  15. 3 2
      pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/util/DeviceInfoUtil.java
  16. 1 8
      pig-marketing/pig-marketing-biz/src/main/resources/application.yml
  17. 4 0
      pig-visual/pig-quartz/pom.xml
  18. 31 0
      pig-visual/pig-quartz/src/main/java/com/pig4cloud/pig/daemon/quartz/task/MktModeTask.java

+ 1 - 61
docker-compose.yml

@@ -1,45 +1,4 @@
 services:
-  pig-mysql:
-    build:
-      context: ./db
-    environment:
-      MYSQL_ROOT_HOST: "%"
-      MYSQL_ROOT_PASSWORD: root
-    restart: always
-    container_name: pig-mysql
-    image: pig-mysql
-    ports:
-      - 33306:3306
-    networks:
-      - spring_cloud_default
-
-  pig-redis:
-    image: registry.cn-hangzhou.aliyuncs.com/dockerhub_mirror/redis
-    ports:
-      - 36379:6379
-    restart: always
-    container_name: pig-redis
-    hostname: pig-redis
-    networks:
-      - spring_cloud_default
-
-  pig-register:
-    build:
-      context: ./pig-register
-    restart: always
-    ports:
-      - 8848:8848
-      - 9848:9848
-      - 8080:8080
-    environment:
-      MYSQL_HOST: pig-mysql
-      REDIS_HOST: pig-redis
-    container_name: pig-register
-    hostname: pig-register
-    image: pig-register
-    networks:
-      - spring_cloud_default
-
   pig-gateway:
     build:
       context: ./pig-gateway
@@ -49,9 +8,6 @@ services:
     container_name: pig-gateway
     hostname: pig-gateway
     image: pig-gateway
-    environment:
-      REDIS_HOST: pig-redis
-      NACOS_HOST: pig-register
     networks:
       - spring_cloud_default
 
@@ -62,9 +18,6 @@ services:
     container_name: pig-auth
     hostname: pig-auth
     image: pig-auth
-    environment:
-      REDIS_HOST: pig-redis
-      NACOS_HOST: pig-register
     networks:
       - spring_cloud_default
 
@@ -75,10 +28,6 @@ services:
     container_name: pig-upms
     hostname: pig-upms
     image: pig-upms
-    environment:
-      MYSQL_HOST: pig-mysql
-      REDIS_HOST: pig-redis
-      NACOS_HOST: pig-register
     networks:
       - spring_cloud_default
 
@@ -91,8 +40,7 @@ services:
     container_name: pig-monitor
     hostname: pig-monitor
     image: pig-monitor
-    environment:
-      NACOS_HOST: pig-register
+
     networks:
       - spring_cloud_default
 
@@ -103,10 +51,6 @@ services:
     container_name: pig-codegen
     hostname: pig-codegen
     image: pig-codegen
-    environment:
-      MYSQL_HOST: pig-mysql
-      REDIS_HOST: pig-redis
-      NACOS_HOST: pig-register
     networks:
       - spring_cloud_default
 
@@ -116,10 +60,6 @@ services:
     restart: always
     image: pig-quartz
     container_name: pig-quartz
-    environment:
-      MYSQL_HOST: pig-mysql
-      REDIS_HOST: pig-redis
-      NACOS_HOST: pig-register
     networks:
       - spring_cloud_default
 

+ 3 - 0
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/dto/mongo/SaveDeviceInfoDTO.java

@@ -24,6 +24,9 @@ public class SaveDeviceInfoDTO implements Serializable {
 	@NotBlank(message = "客户端ID不能为空")
 	private String clientID;
 
+	@Schema(description = "客户端IP")
+	private String clientIp;
+
 	@Schema(description = "设备信息")
 	private String deviceInfo;
 

+ 1 - 1
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/dto/mongo/SaveTcpMessageDTO.java

@@ -28,7 +28,7 @@ public class SaveTcpMessageDTO implements Serializable {
 	private String msgData;
 
 	@Schema(description = "上报IP", example = "127.0.0.1")
-	private String clientIP;
+	private String clientIp;
 
 	@Schema(description = "上报域名报域名", example = "www.baidu.com")
 	private String clientDomain;;

+ 1 - 0
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/MarketingApps.java

@@ -40,6 +40,7 @@ public class MarketingApps extends Model<MarketingApps> {
 	/**
 	 * 应用包名
 	 */
+	@Schema(description = "应用包名")
 	private String bundle;
 
 	/**

+ 3 - 2
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/mongo/Device.java

@@ -5,8 +5,6 @@ import lombok.Data;
 import org.springframework.data.annotation.Id;
 import org.springframework.data.mongodb.core.mapping.Document;
 
-import java.time.LocalDateTime;
-import java.util.Date;
 
 /**
  * @author: lwh
@@ -21,6 +19,9 @@ public class Device {
 	@Schema(description = "设备ID")
 	private String id; // MongoDB自动生成的ObjectId
 
+	@Schema(description = "客户端IP")
+	private String clientIp;
+
 	@Schema(description = "客户端ID")
 	private String clientID; // 客户端唯一标识
 

+ 1 - 1
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/entity/mongo/Message.java

@@ -4,7 +4,6 @@ import lombok.Data;
 import org.springframework.data.annotation.Id;
 import org.springframework.data.mongodb.core.mapping.Document;
 
-import java.time.LocalDateTime;
 
 /**
  * @author: lwh
@@ -17,6 +16,7 @@ public class Message {
 	@Id
 	private String id; // MongoDB自动生成的ObjectId
 
+	private String clientIp;
 	private String clientID; // 客户端唯一标识
 	private String msgData; // 消息内容字符串
 	private String reportTime; // 上报时间

+ 21 - 0
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/feign/RemoteMarketingService.java

@@ -0,0 +1,21 @@
+package com.pig4cloud.pig.marketing.api.feign;
+
+
+import com.pig4cloud.pig.common.core.constant.ServiceNameConstants;
+import com.pig4cloud.pig.common.core.util.R;
+import com.pig4cloud.pig.common.feign.annotation.NoToken;
+import org.springframework.cloud.openfeign.FeignClient;
+import org.springframework.web.bind.annotation.PostMapping;
+
+/**
+ * @author: lwh
+ * @date: 2025-09-07
+ * @description: 远程营销模块服务接口
+ */
+@FeignClient(contextId = "remoteMarketingService", value = ServiceNameConstants.MARKETING_SERVICE)
+public interface RemoteMarketingService {
+
+	@NoToken
+	@PostMapping("/app/synced")
+	R syncedAppList();
+}

+ 6 - 0
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/vo/app/PageMarketingAppsVO.java

@@ -32,6 +32,12 @@ public class PageMarketingAppsVO implements Serializable {
 	@Schema(description = "应用ID")
 	String appId;
 
+	/**
+	 * 应用包名
+	 */
+	@Schema(description = "应用包名")
+	String bundle;
+
 	/**
 	 * 应用名称
 	 */

+ 3 - 0
pig-marketing/pig-marketing-api/src/main/java/com/pig4cloud/pig/marketing/api/vo/mongo/PageDeviceInfoVO.java

@@ -22,6 +22,9 @@ public class PageDeviceInfoVO implements Serializable {
 	@Schema(description = "设备ID")
 	private String id;
 
+	@Schema(description = "客户端IP")
+	private String clientIp;
+
 	@Schema(description = "客户端ID")
 	private String clientID;
 

+ 5 - 0
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/config/PushValidationConfig.java

@@ -33,6 +33,11 @@ public class PushValidationConfig {
      */
     private Boolean enableAppCheck = true;
 
+	/**
+	 * 是否启用应用校验
+	 */
+	private Boolean enableBundleCheck = true;
+
     /**
      * 是否启用域名校验
      */

+ 2 - 0
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/controller/MarketingAppsController.java

@@ -4,6 +4,7 @@ package com.pig4cloud.pig.marketing.controller;
 import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
 import com.pig4cloud.pig.common.core.exception.BusinessException;
 import com.pig4cloud.pig.common.core.util.R;
+import com.pig4cloud.pig.common.security.annotation.Inner;
 import com.pig4cloud.pig.marketing.api.dto.app.*;
 import com.pig4cloud.pig.marketing.api.vo.app.MarketingAppsVO;
 import com.pig4cloud.pig.marketing.api.vo.app.PageMarketingAppsVO;
@@ -120,6 +121,7 @@ public class MarketingAppsController {
 		return res?R.ok():R.failed();
 	}
 
+	@Inner
 	@PostMapping("/synced")
 	@Operation(summary = "同步应用列表")
 	public R syncedAppList() {

+ 67 - 51
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MarketingAppsServiceImpl.java

@@ -18,10 +18,11 @@ import com.pig4cloud.pig.marketing.api.entity.*;
 import com.pig4cloud.pig.marketing.api.vo.app.*;
 import com.pig4cloud.pig.marketing.mapper.*;
 import com.pig4cloud.pig.marketing.service.MarketingAppsService;
-import lombok.AllArgsConstructor;
+import lombok.RequiredArgsConstructor;
 import lombok.extern.slf4j.Slf4j;
 import okhttp3.*;
 import org.springframework.beans.BeanUtils;
+import org.springframework.beans.factory.annotation.Value;
 import org.springframework.stereotype.Service;
 import org.springframework.transaction.annotation.Transactional;
 
@@ -41,17 +42,17 @@ import static com.pig4cloud.pig.marketing.api.MarketingConfigConstants.TRIGGER_R
  */
 @Slf4j
 @Service
-@AllArgsConstructor
+@RequiredArgsConstructor
 public class MarketingAppsServiceImpl implements MarketingAppsService {
 
 
 	// 从配置文件读取URL
-//	@Value("${marketing.app.url}")
-	private static final String getAppListUrl = "http://192.168.3.17:8000/ipa/getApps";
+	@Value("${marketing.app.url}")
+	private String getAppListUrl;
 
 	// 从配置文件读取accessKey
-//	@Value("${marketing.app.access-key}")
-	private static final String accessKey = "4ea5ba93-d222-45dc-862a-1c7fc7789d11";
+	@Value("${marketing.app.access-key}")
+	private String accessKey;
 
 	private final MarketingAppsMapper appsMapper;
 
@@ -281,10 +282,13 @@ public class MarketingAppsServiceImpl implements MarketingAppsService {
 		int deleteCount = 0;
 
 		// 1. 获取lafa服务应用的appId集合
-		Set<String> lafaAppIds = appList.stream()
-				.map(MarketingApps::getAppId)
-				.collect(Collectors.toSet());
-
+		// 1. 获取lafa服务应用的appId集合 - 添加空值检查
+		Set<String> lafaAppIds = new HashSet<>();
+		if (appList != null && !appList.isEmpty()) {
+			lafaAppIds = appList.stream()
+					.map(MarketingApps::getAppId)
+					.collect(Collectors.toSet());
+		}
 		// 2. 查询本地数据库中所有未删除的应用
 		List<MarketingApps> localApps = appsMapper.selectList(new QueryWrapper<>());
 
@@ -293,52 +297,63 @@ public class MarketingAppsServiceImpl implements MarketingAppsService {
 				.collect(Collectors.toMap(MarketingApps::getAppId, app -> app));
 
 		// 4. 获取全局配置
-		AtomicReference<Integer> triggerRule = new AtomicReference<>();
-		AtomicReference<String> triggerNum = new AtomicReference<>("");
+		AtomicReference<Integer> triggerRule = new AtomicReference<>(1);
+		AtomicReference<String> triggerNum = new AtomicReference<>("1");
 		R<ArrayList<SysPublicParamDTO>> ParamDTO = remoteParamService.getParamList(Arrays.asList(TRIGGER_RULE, TRIGGER_NUM));
 
-		ParamDTO.getData().forEach(param -> {
-			if (TRIGGER_RULE.equals(param.getPublicKey())) {
-				triggerRule.set(Integer.valueOf(param.getPublicValue()));
-			} else if (TRIGGER_NUM.equals(param.getPublicKey())) {
-				triggerNum.set(param.getPublicValue());
-			}
-		});
+		// 添加空值检查,防止空指针异常
+		if (ParamDTO != null && ParamDTO.getData() != null) {
+			ParamDTO.getData().forEach(param -> {
+				if (TRIGGER_RULE.equals(param.getPublicKey())) {
+					triggerRule.set(Integer.valueOf(param.getPublicValue()));
+				} else if (TRIGGER_NUM.equals(param.getPublicKey())) {
+					triggerNum.set(param.getPublicValue());
+				}
+			});
+		}
+		if (appList != null) {
+			// 5. 处理新增和更新
+			for (MarketingApps app : appList) {
+				MarketingApps localApp = localAppMap.get(app.getAppId());
 
-		// 5. 处理新增和更新
-		for (MarketingApps app : appList) {
-			MarketingApps localApp = localAppMap.get(app.getAppId());
-
-			if (localApp == null) {
-				// 4.1 本地不存在,新增
-				app.setStatus( true);
-				app.setDomainLimit(false);
-				app.setLaunch( true);
-				app.setTriggerRule(triggerRule.get());
-				app.setTriggerNum(triggerNum.get());
-				appsMapper.insert(app);
-				addCount++;
-			} else {
-				// 4.2 本地存在,判断是否需要更新
-				// 复制ID(本地自增ID)和创建时间(保留原始创建时间)
-				app.setId(localApp.getId());
-
-				// 对比是否有变化
-				if (!isSameApp(app, localApp)) {
-					appsMapper.updateById(app);
-					updateCount++;
+				if (localApp == null) {
+
+					MarketingApps existingApp = appsMapper.selectOne(
+							new QueryWrapper<MarketingApps>().eq("app_id", app.getAppId())
+					);
+
+					if (existingApp == null) {
+						// 4.1 本地不存在,新增
+						app.setStatus(true);
+						app.setDomainLimit(false);
+						app.setLaunch(true);
+						app.setTriggerRule(triggerRule.get());
+						app.setTriggerNum(triggerNum.get());
+						appsMapper.insert(app);
+						addCount++;
+					}
+				} else {
+					// 4.2 本地存在,判断是否需要更新
+					// 复制ID(本地自增ID)和创建时间(保留原始创建时间)
+					app.setId(localApp.getId());
+
+					// 对比是否有变化
+					if (!isSameApp(app, localApp)) {
+						appsMapper.updateById(app);
+						updateCount++;
+					}
 				}
 			}
-		}
 
-		// 5. 处理删除:本地存在但A服务不存在的应用,标记为删除
-		for (MarketingApps localApp : localApps) {
-			if (!lafaAppIds.contains(localApp.getAppId())) {
-				appsMapper.deleteById(localApp);
-				// 删除应用关联的IP、域名
-				appsIpMapper.delete(Wrappers.<MarketingAppsIp>lambdaQuery().eq(MarketingAppsIp::getAppId, localApp.getId()));
-				appsDomainMapper.delete(Wrappers.<MarketingAppsDomain>lambdaQuery().eq(MarketingAppsDomain::getAppId, localApp.getId()));
-				deleteCount++;
+			// 6. 处理删除:本地存在但A服务不存在的应用,标记为删除
+			for (MarketingApps localApp : localApps) {
+				if (!lafaAppIds.contains(localApp.getAppId())) {
+					appsMapper.deleteById(localApp);
+					// 删除应用关联的IP、域名
+					appsIpMapper.delete(Wrappers.<MarketingAppsIp>lambdaQuery().eq(MarketingAppsIp::getAppId, localApp.getId()));
+					appsDomainMapper.delete(Wrappers.<MarketingAppsDomain>lambdaQuery().eq(MarketingAppsDomain::getAppId, localApp.getId()));
+					deleteCount++;
+				}
 			}
 		}
 
@@ -515,7 +530,8 @@ public class MarketingAppsServiceImpl implements MarketingAppsService {
 				Objects.equals(newApp.getAppImg(), oldApp.getAppImg()) &&
 				Objects.equals(newApp.getAppUrl(), oldApp.getAppUrl()) &&
 				Objects.equals(newApp.getBackupUrl(), oldApp.getBackupUrl()) &&
-				Objects.equals(newApp.getDomainType(), oldApp.getDomainType());
+				Objects.equals(newApp.getDomainType(), oldApp.getDomainType()) &&
+				Objects.equals(newApp.getBundle(), oldApp.getBundle());
 	}
 
 	/**

+ 100 - 41
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MarketingConfigServiceImpl.java

@@ -654,52 +654,84 @@ public class MarketingConfigServiceImpl implements MarketingConfigService {
 					break;
 				case PUSH_IP:
 					if (StringUtils.isNotBlank(item.getPublicValue())) {
-						String[] ip = item.getPublicValue().split("&&");
-						res.setIp(List.of(ip));
+						if (item.getPublicValue().contains("&&")) {
+							String[] ip = item.getPublicValue().split("&&");
+							res.setIp(List.of(ip));
+						}else {
+							res.setIp(List.of(item.getPublicValue()));
+						}
+
 					} else {
 						res.setIp(new ArrayList<>());
 					}
 					break;
 				case PUSH_DOMAIN:
 					if (StringUtils.isNotBlank(item.getPublicValue())) {
-						String[] domain = item.getPublicValue().split("&&");
-						res.setDomain(List.of(domain));
+						if (item.getPublicValue().contains("&&")) {
+							String[] domain = item.getPublicValue().split("&&");
+							res.setDomain(List.of(domain));
+						}else {
+							res.setDomain(List.of(item.getPublicValue()));
+						}
 					} else {
 						res.setDomain(new ArrayList<>());
 					}
 					break;
 				case PUSH_ADDR:
 					if (StringUtils.isNotBlank(item.getPublicValue())) {
-						String[] addr = item.getPublicValue().split("&&");
-						res.setPushAddr(List.of(addr));
+						if (item.getPublicValue().contains("&&")) {
+							String[] addr = item.getPublicValue().split("&&");
+							res.setPushAddr(List.of(addr));
+						}else {
+							res.setPushAddr(List.of(item.getPublicValue()));
+						}
 					} else {
 						res.setPushAddr(new ArrayList<>());
 					}
 					break;
 				case PUSH_APP:
 					if (StringUtils.isNotBlank(item.getPublicValue())) {
-						String[] appArray = item.getPublicValue().split("&&");
-						List<PushAPPDTO> pushAppList = new ArrayList<>();
-						for (String appStr : appArray) {
-							if (appStr.contains("@")) {
+						if (item.getPublicValue().contains("&&")) {
+							String[] appArray = item.getPublicValue().split("&&");
+							List<PushAPPDTO> pushAppList = new ArrayList<>();
+							for (String appStr : appArray) {
+								if (appStr.contains("@")) {
+									String[] parts = appStr.split("@", 2);
+									if (parts.length == 2) {
+										PushAPPDTO pushApp = new PushAPPDTO();
+										pushApp.setId(parts[0]);
+										pushApp.setAppId(parts[1]);
+										pushAppList.add(pushApp);
+									}
+								}
+							}
+							res.setPushApp(pushAppList);
+						}else {
+						 	PushAPPDTO pushApp = new PushAPPDTO();
+							List<PushAPPDTO> pushAppList = new ArrayList<>();
+							String appStr = item.getPublicValue();
+							if (appStr.contains("@")){
 								String[] parts = appStr.split("@", 2);
 								if (parts.length == 2) {
-									PushAPPDTO pushApp = new PushAPPDTO();
 									pushApp.setId(parts[0]);
 									pushApp.setAppId(parts[1]);
 									pushAppList.add(pushApp);
+									res.setPushApp(pushAppList);
 								}
 							}
 						}
-						res.setPushApp(pushAppList);
 					} else {
 						res.setPushApp(new ArrayList<>());
 					}
 					break;
 				case PUSH_BUNDLE:
 					if (StringUtils.isNotBlank(item.getPublicValue())) {
-						String[] bundle = item.getPublicValue().split("&&");
-						res.setPushBundle(List.of(bundle));
+						if (item.getPublicValue().contains("&&")) {
+							String[] bundle = item.getPublicValue().split("&&");
+							res.setPushBundle(List.of(bundle));
+						}else {
+							res.setPushBundle(List.of(item.getPublicValue()));
+						}
 					} else {
 						res.setPushBundle(new ArrayList<>());
 					}
@@ -723,21 +755,30 @@ public class MarketingConfigServiceImpl implements MarketingConfigService {
 		StringBuilder ipBuilder = new StringBuilder();
 		if (reqDto.getIp() != null && !reqDto.getIp().isEmpty()){
 			IPUtils.validateIpList(reqDto.getIp());
-			for (String ip : reqDto.getIp()){
-				ipBuilder.append( ip);
-				ipBuilder.append("&&");
+			if (reqDto.getIp().size()>1){
+				for (String ip : reqDto.getIp()){
+					ipBuilder.append( ip);
+					ipBuilder.append("&&");
+				}
+				ipBuilder.delete(ipBuilder.length()-2, ipBuilder.length());
+			} else if (reqDto.getIp().size() == 1) {
+				ipBuilder.append(reqDto.getIp().get(0));
 			}
-			ipBuilder.delete(ipBuilder.length()-2, ipBuilder.length());
+
 		}
 		// 处理域名列表
 		StringBuilder domainBuilder = new StringBuilder();
 		if (reqDto.getDomain() != null && !reqDto.getDomain().isEmpty()){
 			DomainValidationUtil.validateDomainList(reqDto.getDomain());
-			for (String domain : reqDto.getDomain()){
-				domainBuilder.append( domain);
-				domainBuilder.append("&&");
+			if (reqDto.getDomain().size()>1){
+				for (String domain : reqDto.getDomain()){
+					domainBuilder.append( domain);
+					domainBuilder.append("&&");
+				}
+				domainBuilder.delete(domainBuilder.length()-2, domainBuilder.length());
+			} else if (reqDto.getDomain().size() == 1) {
+				domainBuilder.append(reqDto.getDomain().get(0));
 			}
-			domainBuilder.delete(domainBuilder.length()-2, domainBuilder.length());
 		}
 		// 添加IP
 		sysParam = new SysPublicParamDTO();
@@ -810,15 +851,21 @@ public class MarketingConfigServiceImpl implements MarketingConfigService {
 		if (reqDto.getPushApp() != null && !reqDto.getPushApp().isEmpty()){
 			StringBuilder appBuilder = new StringBuilder();
 
-			for (PushAPPDTO app : reqDto.getPushApp()){
-				if (app != null && app.getId() != null && app.getAppId() != null) {
-					appBuilder.append(app.getId()).append("@").append(app.getAppId());
-					appBuilder.append("&&");
-				}
+			if (reqDto.getPushApp().size() == 1){
+				appBuilder.append(reqDto.getPushApp().get(0).getId()).append("@").append(reqDto.getPushApp().get(0).getAppId());
 			}
-			if (appBuilder.length() > 2) {
-				appBuilder.delete(appBuilder.length()-2, appBuilder.length());
+			if (reqDto.getPushApp().size() > 1){
+				for (PushAPPDTO app : reqDto.getPushApp()){
+					if (app != null && app.getId() != null && app.getAppId() != null) {
+						appBuilder.append(app.getId()).append("@").append(app.getAppId());
+						appBuilder.append("&&");
+					}
+				}
+				if (appBuilder.length() > 2) {
+					appBuilder.delete(appBuilder.length()-2, appBuilder.length());
+				}
 			}
+
 			sysParam = new SysPublicParamDTO();
 			sysParam.setPublicKey(PUSH_APP);
 			sysParam.setPublicValue(appBuilder.toString());
@@ -829,15 +876,21 @@ public class MarketingConfigServiceImpl implements MarketingConfigService {
 		//处理推送地址
 		if (reqDto.getPushAddr() != null && !reqDto.getPushAddr().isEmpty()){
 			StringBuilder addrBuilder = new StringBuilder();
-			for (String addr : reqDto.getPushAddr()){
-				if ("All".equals(addr)){
+			if (reqDto.getPushAddr().size()>1){
+				for (String addr : reqDto.getPushAddr()){
+					addrBuilder.append(addr);
+					addrBuilder.append("&&");
+				}
+				addrBuilder.delete(addrBuilder.length()-2, addrBuilder.length());
+
+			} else {
+				if ("All".equals(reqDto.getPushAddr().get(0))){
 					addrBuilder.append("All");
-					break;
+				} else {
+					addrBuilder.append(reqDto.getPushAddr().get(0));
 				}
-				addrBuilder.append(addr);
-				addrBuilder.append("&&");
 			}
-			addrBuilder.delete(addrBuilder.length()-2, addrBuilder.length());
+
 			sysParam = new SysPublicParamDTO();
 			sysParam.setPublicKey(PUSH_ADDR);
 			sysParam.setPublicValue(addrBuilder.toString());
@@ -848,15 +901,21 @@ public class MarketingConfigServiceImpl implements MarketingConfigService {
 		//处理推送包名
 		StringBuilder bundleBuilder = new StringBuilder();
 		if (reqDto.getPushAddr() != null && !reqDto.getPushAddr().isEmpty()){
-			for (String bundle : reqDto.getPushBundle()){
-				if ("All".equals(bundle)){
+			if (reqDto.getPushBundle().size()>1){
+				for (String bundle : reqDto.getPushBundle()){
+
+					bundleBuilder.append(bundle);
+					bundleBuilder.append("&&");
+				}
+				bundleBuilder.delete(bundleBuilder.length()-2, bundleBuilder.length());
+			} else if ( reqDto.getPushBundle().size() == 1) {
+				if ("All".equals(reqDto.getPushBundle().get(0))){
 					bundleBuilder.append("All");
-					break;
+				}else {
+					bundleBuilder.append(reqDto.getPushBundle().get(0));
 				}
-				bundleBuilder.append(bundle);
-				bundleBuilder.append("&&");
 			}
-			bundleBuilder.delete(bundleBuilder.length()-2, bundleBuilder.length());
+
 			sysParam = new SysPublicParamDTO();
 			sysParam.setPublicKey(PUSH_BUNDLE);
 			sysParam.setPublicValue(bundleBuilder.toString());

+ 22 - 22
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/service/impl/MktMgmtHandPushServiceImpl.java

@@ -110,28 +110,28 @@ public class MktMgmtHandPushServiceImpl implements MktMgmtHandPushService {
             if (pushValidationConfig.getEnableAddressCheck() && 
                 globalRule.getPushAddr() != null && !globalRule.getPushAddr().isEmpty()) {
 
-				if ("All".equals(globalRule.getPushAddr().get(0))){
-					return "推送地址【All】";
+				if (!"All".equals(globalRule.getPushAddr().get(0))){
+					String fullAddress = ipLocationUtil.getCityByIP(saveDTO.getPushIP());
+					if (fullAddress == null) {
+						return "无法解析推送IP【" + saveDTO.getPushIP() + "】的地址信息";
+					}
+
+					// 检查是否匹配pushAddr中的任一地址
+					boolean addressMatched = false;
+					for (String allowedAddr : globalRule.getPushAddr()) {
+						if (isAddressMatched(fullAddress, allowedAddr)) {
+							addressMatched = true;
+							break;
+						}
+					}
+
+					if (!addressMatched) {
+						return "推送地址【" + fullAddress + "】不在允许的地址范围内,允许的地址:" + globalRule.getPushAddr();
+					}
+					log.info("地址校验通过,IP:{},地址:{}", saveDTO.getPushIP(), fullAddress);
 				}
 
-                String fullAddress = ipLocationUtil.getCityByIP(saveDTO.getPushIP());
-                if (fullAddress == null) {
-                    return "无法解析推送IP【" + saveDTO.getPushIP() + "】的地址信息";
-                }
-                
-                // 检查是否匹配pushAddr中的任一地址
-                boolean addressMatched = false;
-                for (String allowedAddr : globalRule.getPushAddr()) {
-                    if (isAddressMatched(fullAddress, allowedAddr)) {
-                        addressMatched = true;
-                        break;
-                    }
-                }
-                
-                if (!addressMatched) {
-                    return "推送地址【" + fullAddress + "】不在允许的地址范围内,允许的地址:" + globalRule.getPushAddr();
-                }
-                log.info("地址校验通过,IP:{},地址:{}", saveDTO.getPushIP(), fullAddress);
+				log.info("地址校验通过,ALL-----");
             }
             
             // 4. 应用校验 - 根据客户端ID获取设备信息并匹配pushApp和pushBundle
@@ -149,7 +149,7 @@ public class MktMgmtHandPushServiceImpl implements MktMgmtHandPushService {
                 String matchedType = "";
                 
                 // 检查pushApp(appId匹配)
-                if (globalRule.getPushApp() != null && !globalRule.getPushApp().isEmpty() && appId != null) {
+                if (!pushValidationConfig.getEnableBundleCheck() && globalRule.getPushApp() != null && !globalRule.getPushApp().isEmpty() && appId != null) {
                     // 检查是否为All
                     if (globalRule.getPushApp().stream()
                             .anyMatch(pushApp -> pushApp != null && "All".equals(pushApp.getAppId()))) {
@@ -166,7 +166,7 @@ public class MktMgmtHandPushServiceImpl implements MktMgmtHandPushService {
                 }
                 
                 // 检查pushBundle(bundle匹配)
-                if (!appMatched && globalRule.getPushBundle() != null && !globalRule.getPushBundle().isEmpty() && bundle != null) {
+                if ( !appMatched && pushValidationConfig.getEnableBundleCheck() && globalRule.getPushBundle() != null && !globalRule.getPushBundle().isEmpty() && bundle != null) {
                     if (globalRule.getPushBundle().contains(bundle)) {
                         appMatched = true;
                         matchedType = "bundle";

+ 3 - 2
pig-marketing/pig-marketing-biz/src/main/java/com/pig4cloud/pig/marketing/util/DeviceInfoUtil.java

@@ -74,8 +74,9 @@ public class DeviceInfoUtil {
      */
     public String[] extractBundleAndAppId(String deviceInfoJson) {
         String[] result = new String[2];
-        result[0] = extractBundle(deviceInfoJson);
-        result[1] = extractAppId(deviceInfoJson);
+		String str = deviceInfoJson.substring(deviceInfoJson.indexOf("{"));
+        result[0] = extractBundle(str);
+        result[1] = extractAppId(str);
         return result;
     }
 }

+ 1 - 8
pig-marketing/pig-marketing-biz/src/main/resources/application.yml

@@ -20,11 +20,4 @@ spring:
   config:
     import:
       - nacos:application.yml
-      - nacos:${spring.application.name}.yml
-
-marketing:
-  app:
-    url: http://192.168.3.17:2888/ipa/getApps
-    access-key: 4ea5ba93-d222-45dc-862a-1c7fc7789d11
-
-
+      - nacos:${spring.application.name}.yml

+ 4 - 0
pig-visual/pig-quartz/pom.xml

@@ -74,6 +74,10 @@
             <groupId>org.springframework.boot</groupId>
             <artifactId>spring-boot-starter-undertow</artifactId>
         </dependency>
+        <dependency>
+            <groupId>com.pig4cloud</groupId>
+            <artifactId>pig-marketing-api</artifactId>
+        </dependency>
     </dependencies>
 
     <profiles>

+ 31 - 0
pig-visual/pig-quartz/src/main/java/com/pig4cloud/pig/daemon/quartz/task/MktModeTask.java

@@ -0,0 +1,31 @@
+package com.pig4cloud.pig.daemon.quartz.task;
+
+
+import com.pig4cloud.pig.common.core.util.R;
+import com.pig4cloud.pig.daemon.quartz.constants.PigQuartzEnum;
+import com.pig4cloud.pig.marketing.api.feign.RemoteMarketingService;
+import lombok.SneakyThrows;
+import lombok.extern.slf4j.Slf4j;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.stereotype.Component;
+
+
+/**
+ * @author: lwh
+ * @date: 2025-09-07
+ * @description: 营销模块定时任务
+ */
+@Slf4j
+@Component("marketing")
+public class MktModeTask {
+
+	@Autowired
+	private RemoteMarketingService marketingAppsService;
+
+	// 同步应用列表
+	@SneakyThrows
+	public String asyncAppList() {
+		R r = marketingAppsService.syncedAppList();
+		return PigQuartzEnum.JOB_LOG_STATUS_SUCCESS.getType();
+	}
+}