iflytek/astron-agent · error · IllegalArgumentException

User UID cannot be null

Error message

User UID cannot be null

What it means

createOrGetUser validates its input before doing any lookup: a null UserInfo or a UserInfo with null uid throws IllegalArgumentException('User UID cannot be null'). It's a fail-fast guard that prevents downstream lock contention and DB queries with a null key.

Solutions

  1. Populate userInfo.setUid(...) from the authenticated principal before calling createOrGetUser
  2. Validate the incoming DTO (e.g. @NotNull on uid, or Objects.requireNonNull) at the controller layer
  3. Fix the field mapping if a converter silently drops uid
  4. Return a clear 400 to clients when uid is missing instead of reaching the service

Example fix

// before
userInfoService.createOrGetUser(new UserInfo()); // uid null -> IllegalArgumentException
// after
UserInfo u = new UserInfo();
u.setUid(currentPrincipal.getUid());
if (u.getUid() == null) throw new BadRequestException("uid is required");
userInfoService.createOrGetUser(u);
Defensive patterns

Strategy: validation

Validate before calling

if (userInfo == null || userInfo.getUid() == null) {
    throw new ResponseStatusException(HttpStatus.BAD_REQUEST, "uid is required");
}

Type guard

// Java: validate before the service call
boolean hasUid = Optional.ofNullable(userInfo).map(UserInfo::getUid).isPresent();

Try / catch

try {
    userInfoService.createOrGetUser(userInfo);
} catch (IllegalArgumentException e) {
    log.warn("invalid user payload: {}", e.getMessage());
    throw new BadRequestException(e.getMessage());
}

Prevention

When it happens

Trigger: Calling createOrGetUser with a UserInfo built without setting uid — e.g. constructing UserInfo from a request/SSO payload where the uid field is absent, or mapping code that drops the uid during conversion.

Common situations: Auth/SSO token missing the uid claim; API caller omitting uid in the request body; a mapper (MapStruct/BeanUtils) skipping the uid property due to a name mismatch; upstream service returning a partial user object.

Related errors


AI-assisted analysis of iflytek/astron-agent@5e758547a8 (2026-09-12). Data as JSON: /api/errors/7708d1964478aa66. Report an issue: GitHub.

Appendix: source

Thrown at console/backend/commons/src/main/java/com/iflytek/astron/console/commons/data/impl/UserInfoDataServiceImpl.java:160

        wrapper.eq(UserInfo::getAccountStatus, accountStatus);
        return userInfoMapper.selectList(wrapper);
    }

    @Override
    public List<UserInfo> findActiveUsers() {
        LambdaQueryWrapper<UserInfo> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(UserInfo::getAccountStatus, 1);
        return userInfoMapper.selectList(wrapper);
    }

    @Override
    public UserInfo createOrGetUser(UserInfo userInfo) {
        if (userInfo == null) {
            throw new IllegalArgumentException("User information cannot be null");
        }

        if (userInfo.getUid() == null) {
            throw new IllegalArgumentException("User UID cannot be null");
        }

        // First check: fail fast to avoid unnecessary lock contention
        Optional<UserInfo> existingUser = findByUid(userInfo.getUid());
        if (existingUser.isPresent()) {
            return existingUser.get();
        }

        String lockKey = "user:create:uid:" + userInfo.getUid();
        RLock lock = redissonClient.getLock(lockKey);

        try {
            // Attempt to acquire the lock: wait up to 5s, hold up to 10s
            boolean acquired = lock.tryLock(5, 10, TimeUnit.SECONDS);

            if (!acquired) {
                throw new IllegalStateException("Timed out acquiring distributed lock, please try again later");
            }

View on GitHub (pinned to 5e758547a8)