Skip to content

Filter all-null FIELD columns before tablet insert in Java/C++/Python… - #18533

Open
hongzhi-gao wants to merge 5 commits into
apache:masterfrom
hongzhi-gao:feature/client-filter-null-col
Open

Filter all-null FIELD columns before tablet insert in Java/C++/Python…#18533
hongzhi-gao wants to merge 5 commits into
apache:masterfrom
hongzhi-gao:feature/client-filter-null-col

Conversation

@hongzhi-gao

Copy link
Copy Markdown
Contributor

Description

Before inserting a Tablet, drop FIELD columns that are entirely null within [0, rowSize). TAG / ATTRIBUTE columns are always kept. This avoids shipping unused measurement columns when the client schema is wide but each batch only fills a subset of fields.

Behavior

  • If nothing needs to be dropped, return the original Tablet (no copy).
  • If some FIELD columns are dropped, return a new Tablet with only the kept columns.
  • If every FIELD column is null, skip the insert (return null / empty and log a warning where applicable).
  • Does not mutate the caller-owned Tablet.

Multi-language clients

Aligned the same logic in Java / C++ / Python Session insert tablet paths (insertTablet / insertTablets / aligned / relational where applicable). C API goes through the C++ Session, so no separate implementation.

Design notes

  • Logic lives in SessionUtils.filterNullColumns (Java / C++) and filter_null_columns (Python), and is invoked when building insert requests after sort.
  • C++ returns std::shared_ptr<const Tablet> (non-owning empty deleter for the original tablet; owning shared_ptr for a filtered copy) instead of a raw pointer + out-parameter.

This PR has:

  • been self-reviewed.
  • added unit tests or modified existing tests to cover new code paths, ensuring the threshold for code coverage.
  • added documentation for new or modified features or behaviors.
  • added integration tests.
  • been tested in a test IoTDB cluster.

Key changed/added classes (or packages if there are too many classes) in this PR
  • org.apache.iotdb.session.util.SessionUtils
  • org.apache.iotdb.session.Session
  • iotdb-client/client-cpp SessionUtils::filterNullColumns / Session
  • iotdb.utils.SessionUtils (Python)
  • Unit tests: SessionUtilsTest (Java), sessionUtilsTest (C++), test_session_utils.py (Python)

… clients

Skip or shrink tablets that only contain null FIELD values so insert paths
avoid shipping unused measurement columns across languages.
Comment thread iotdb-client/client-cpp/src/rpc/SessionImpl.h Outdated
Comment on lines +416 to +429
static bool isColumnAllNull(const BitMap& bitMap, size_t rowSize) {
if (rowSize == 0) {
return false;
}
if (bitMap.getSize() == rowSize && bitMap.isAllMarked()) {
return true;
}
for (size_t row = 0; row < rowSize; row++) {
if (!bitMap.isMarked(row)) {
return false;
}
}
return true;
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is bitMap.isAllMarked not enough?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

BitMap is sized to maxRowNumber, not rowSize. When rowSize < maxRowNumber, tail bits are unmarked, so isAllMarked() returns false even if all active rows are null. We only use it when getSize() == rowSize.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is it possible to add BitMap.isAllMarked(int start, int end) to accelerate this iteration?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done

Comment on lines +479 to +481
auto filteredOut = std::make_shared<Tablet>(tablet.deviceId, keptSchemas, keptColumnTypes,
tablet.maxRowNumber, tablet.isAligned);
filteredOut->deleteColumns();

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not create-and-delete or copy. May add a constructor for this.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

fixed

Table-model tablet inserts may carry only time and tag/attribute columns.
Do not treat all-null FIELD columns as an empty tablet when non-FIELD
columns remain, and clarify buildInsertTabletReq skip semantics.
…olumns.

Add a private constructor and createWithoutValueColumns to build tablets without pre-allocating value columns, fix bitmap null-check bounds, and update the Java table-model test constructor.
BitMap is sized to maxRowNumber, so a full-map isAllMarked() can miss
all-null FIELD columns when rowSize is smaller. Use isRangeAllMarked on
[0, rowSize) in the Java, C++, and Python clients.
A never-written column is treated as all-null; dropping it skipped the
existing measurement-name check and omitted timeseries that tests expect.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants