Files
starRiverProperty/docs/superpowers/specs/2026-05-06-tenant-visitor-policy-logging-design.md
T
hpd840321 7b2bd307f1 Initial commit: reorganized source tree
- backend/: 13 Maven modules (cw-elevator-application, cloudwalk-cloud, intelligent-cwoscomponent, ninca-crk, etc.)
- frontend/: 4 Vue projects (elevator-front, cwos-portal, alarm-front, front_acs) + decompiled + scripts
- scripts/: build, test-env, tools (Docker Compose, service templates, API parity)
- docs/: AGENTS.md, superpowers specs, architecture docs
- .gitignore: standard Java/Maven exclusions

Moved from legacy maven-*/ root layout to backend/ organized structure.
2026-05-09 09:56:45 +08:00

4.7 KiB

租户访客默认楼层策略 — 日志完善方案

日期: 2026-05-06 方案: 统一 [POLICY] 日志前缀,确保部署后可通过单次 grep 判定策略是否生效


日志格式约定

前缀 含义 级别
[POLICY] 策略入口被调用 INFO
[POLICY-HIT] 策略命中,返回 allow_zone_ids INFO
[POLICY-MISS] 策略未命中(无策略/未启用/allow为空) DEBUG
[POLICY-DETAIL] detail() 方法中的策略结果 INFO
[POLICY-LIST] listByPage() 方法中的策略结果 INFO

grep 速查

# 查看所有策略调用
grep "\[POLICY\]" component-organization.info.log

# 只看策略命中
grep "\[POLICY-HIT\]" component-organization.info.log

# 统计调用次数
grep -c "\[POLICY\]" component-organization.info.log

修改清单

1. TenantVisitorFloorPolicyService.java — 3 处修改

L68-74 (replacementZoneIdsIfPolicyActive — 多 orgIds 入口):

public Optional<List<String>> replacementZoneIdsIfPolicyActive(List<String> orgIds) {
    if (CollectionUtils.isEmpty(orgIds)) {
        return Optional.empty();
    }
    log.info("[POLICY] entry orgIds={}", orgIds);  // ← 新增
    for (String id : orgIds) {
        Optional<List<String>> zones = replacementZoneIdsIfPolicyActive(id);
        if (zones.isPresent()) {
            return zones;
        }
    }
    log.debug("[POLICY-MISS] no enabled policy for any org in {}", orgIds);  // ← 新增
    return Optional.empty();
}

L83-98 (replacementZoneIdsIfPolicyActive — 单 orgId 查询):

public Optional<List<String>> replacementZoneIdsIfPolicyActive(String orgId) {
    try {
        Optional<TenantVisitorFloorPolicy> policy = findEnabledPolicyByOrgId(orgId);
        if (!policy.isPresent()) {
            log.debug("[POLICY-MISS] orgId={} no policy row", orgId);  // ← 新增
            return Optional.empty();
        }
        List<String> allow = parseAllowZoneIds(policy.get().getAllowZoneIds());
        if (allow.isEmpty()) {
            log.info("[POLICY-MISS] orgId={} allow_zone_ids empty", orgId);  // ← 新增
            return Optional.empty();
        }
        log.info("[POLICY-HIT] orgId={} policyId={} zones={} count={}",  // ← 新增
            orgId, policy.get().getId(), allow, allow.size());
        return Optional.of(new ArrayList<>(allow));
    } catch (Exception e) {
        log.warn("[POLICY-ERR] orgId={} query failed, fallback: {}",  // ← 修改
            orgId, e.toString());
        return Optional.empty();
    }
}

L39-57 (parseAllowZoneIds):

public List<String> parseAllowZoneIds(String allowZoneIdsJson) {
    if (StringUtils.isBlank(allowZoneIdsJson)) {
        return Collections.emptyList();
    }
    try {
        // ... 原有逻辑不变 ...
    } catch (Exception e) {
        log.warn("[POLICY-ERR] allow_zone_ids JSON invalid: {}", e.getMessage());  // ← 修改前缀
        return Collections.emptyList();
    }
}

2. ImgPersonServiceImpl.java — 2 处修改

L322-334 (listByPage — isVisitor 场景):

if (policyZones.isPresent()) {
    log.info("[POLICY-LIST] hit personId={} orgIds={} zones={}",  // ← 新增
        imgStorePersonResult.getId(),
        imgStorePersonResult.getOrganizationIds(),
        policyZones.get());
    List<AcsPassRuleImageResultDto> policyFloorInfo =
        buildFloorInfoListFromOrderedZoneIds(businessId, policyZones.get());
    // ... 原有逻辑不变 ...

L643-651 (detail — 详情场景):

Optional<List<String>> replacementFloors =
    this.tenantVisitorFloorPolicyService.replacementZoneIdsIfPolicyActive(
        result.getOrganizationIds());
if (replacementFloors.isPresent()) {
    log.info("[POLICY-DETAIL] hit personId={} orgIds={} zones={}",  // ← 新增
        result.getId(),
        result.getOrganizationIds(),
        replacementFloors.get());
    floorList = new ArrayList<>(replacementFloors.get());
    // ... 原有逻辑不变 ...

预期日志输出示例

# 策略命中(detail 场景)
[POLICY] entry orgIds=[605560545117995008, 605560541473144832]
[POLICY-HIT] orgId=605560545117995008 policyId=gf_vstr_xxx zones=[zone_28f, zone_6f] count=2
[POLICY-DETAIL] hit personId=1072908835884208128 orgIds=[605560545117995008, 605560541473144832] zones=[zone_28f, zone_6f]

# 策略未命中
[POLICY] entry orgIds=[some_org_id]
[POLICY-MISS] orgId=some_org_id no policy row
[POLICY-MISS] no enabled policy for any org in [some_org_id]

# 策略命中(listByPage 场景)
[POLICY] entry orgIds=[605560545117995008]
[POLICY-HIT] orgId=605560545117995008 policyId=gf_vstr_xxx zones=[zone_28f, zone_6f] count=2
[POLICY-LIST] hit personId=xxx orgIds=[605560545117995008] zones=[zone_28f, zone_6f]