- Add keyFiltersOperation field to EdqsQuery base class
- Update EdqsCountQuery and EdqsDataQuery constructors to accept and propagate ComplexOperation
- Propagate keyFiltersOperationOrDefault in both toNewQuery overloads in RepositoryUtils
- Add sql.query.key-filters-or-conditions.enabled property to thingsboard.yml
- Add allowKeyFiltersOrConditions field to SystemParams
- Wire config value into SystemInfoController for /api/system/params
- Add validateKeyFiltersOperation to DefaultEntityQueryService
- Add throws ThingsboardException to EntityQueryService interface methods
- Reject OR queries with 400 when feature is disabled
- Add keyFiltersOperation field with null-safe getKeyFiltersOperationOrDefault()
- Add 3-arg constructor to EntityCountQuery for explicit operation
- Add 6-arg constructors to AbstractDataQuery and EntityDataQuery
- Add 7-arg constructor to AlarmDataQuery
- Update next() methods to propagate keyFiltersOperation
- Update buildEntityDataQuery methods to pass operation from alarm queries
- Deduplicate forEach iteration over both session maps (HashSet)
- Use null-safe getEdgeId() instead of getEdge().getId() in remove()
- Add defensive null checks on getState() in onConfigurationUpdate and destroyAndMarkAsZombieIfFailed
- Add null check on pendingMsgsMap.get() in onDownlinkResponse
- Move scheduleAtFixedRate to @PostConstruct in DefaultZombieSessionCleanupService
- Fix misleading "kafka sessions" log message to "zombie sessions"
- Chain IOException in GrpcServer RuntimeException
- Guard against race condition on removeByEdgeId in onEdgeDisconnect
- Rename shadowed parameter in shutdownExecutorSafely
Route DataAccessException and PersistenceException (including bare
ConstraintViolationException) to a unified handler that extracts the
constraint name and returns "Constraint violation: <name>" instead of
the raw PSQLException message. Other DB errors continue to return the
generic "Database error" response.
Adds DaoUtil.extractConstraintViolation helper and an integration test
that verifies no SQL details leak when an FK constraint is violated.
Replace stream().filter().collect() in resolveAll with single-pass loop
to avoid allocations on the common path (nothing blocked). Remove
redundant isEnabled() checks inside the resolver since it is only wired
when SSRF protection is enabled. Add resolveAll test coverage.
Keep both save-time validation (Oauth2ClientDataValidator) and runtime
re-validation as defense-in-depth: DNS records can change between config
save and OAuth2 login, creating a TOCTOU gap.