diff --git a/include/caosdb/transaction.h b/include/caosdb/transaction.h index 002a9d3eaca381732b0c0104cb4f076d6eab2fe6..cc889413a3d377c8798dac6cdb471610bb2a6b44 100644 --- a/include/caosdb/transaction.h +++ b/include/caosdb/transaction.h @@ -187,12 +187,19 @@ using google::protobuf::Arena; class ResultTableImpl; +class ResultTableColumnImpl; + class ResultTableColumn { public: /** * Get the name of the column. */ [[nodiscard]] auto GetName() const noexcept -> const std::string &; + + friend class ResultTable; + explicit ResultTableColumn(std::unique_ptr<ResultTableColumnImpl> delegate); +private: + std::unique_ptr<ResultTableColumnImpl> delegate; }; class ResultTable { @@ -216,6 +223,7 @@ private: class HeaderIterator : std::iterator<std::output_iterator_tag, ResultTableColumn> { public: explicit HeaderIterator(const ResultTable *result_table, int index = 0); + HeaderIterator(const HeaderIterator &other); auto operator*() const -> const ResultTableColumn &; auto operator++() -> HeaderIterator &; auto operator++(int) -> HeaderIterator; diff --git a/proto b/proto index 0b301401cf28d7a3edeb2c55e418f072b83cf5a7..fd60795f62335368255797db43eb0429ec1705fc 160000 --- a/proto +++ b/proto @@ -1 +1 @@ -Subproject commit 0b301401cf28d7a3edeb2c55e418f072b83cf5a7 +Subproject commit fd60795f62335368255797db43eb0429ec1705fc diff --git a/src/caosdb/transaction.cpp b/src/caosdb/transaction.cpp index 59c94387558f29813c28ad17c487af4513d22d56..ca8ea2f984f443d0f13dfa50840d85fb03c567bd 100644 --- a/src/caosdb/transaction.cpp +++ b/src/caosdb/transaction.cpp @@ -53,6 +53,7 @@ using RetrieveResponseCase = caosdb::entity::v1::RetrieveResponse::RetrieveRespo using RetrieveResponse = caosdb::entity::v1::RetrieveResponse; using ProtoEntity = caosdb::entity::v1::Entity; using ProtoSelectQueryResult = caosdb::entity::v1::SelectQueryResult; +using ProtoSelectQueryColumn = caosdb::entity::v1::SelectQueryColumn; using caosdb::entity::v1::EntityRequest; using caosdb::utility::ScalarProtoMessageWrapper; @@ -60,13 +61,29 @@ using google::protobuf::Arena; using NextStatus = grpc::CompletionQueue::NextStatus; using RegistrationStatus = caosdb::entity::v1::RegistrationStatus; +class ResultTableColumnImpl : public ScalarProtoMessageWrapper<ProtoSelectQueryColumn> { + explicit ResultTableColumnImpl(ProtoSelectQueryColumn *column); + friend class ResultTableColumn; + friend class ResultTableImpl; +}; + +ResultTableColumnImpl::ResultTableColumnImpl(ProtoSelectQueryColumn *column) : ScalarProtoMessageWrapper<ProtoSelectQueryColumn>(column) {}; + +ResultTableColumn::ResultTableColumn(std::unique_ptr<ResultTableColumnImpl> delegate) : delegate(std::move(delegate)) {} + +auto ResultTableColumn::GetName() const noexcept -> const std::string & { + return this->delegate->wrapped->name(); +} class ResultTableImpl : public ScalarProtoMessageWrapper<ProtoSelectQueryResult> { static auto create(ProtoSelectQueryResult *select_result) -> std::unique_ptr<ResultTable>; ResultTableImpl(); explicit ResultTableImpl(ProtoSelectQueryResult *result_table); + std::vector<ResultTableColumn> columns; friend class ResultTable; + friend class ResultTable::HeaderIterator; + friend class ResultTableColumn; friend auto ProcessSelectResponse(ProtoSelectQueryResult *select_result) -> std::unique_ptr<ResultTable>; }; @@ -74,7 +91,11 @@ auto ResultTableImpl::create(ProtoSelectQueryResult *select_result) -> std::uniq return std::unique_ptr<ResultTable>(new ResultTable(std::unique_ptr<ResultTableImpl>(new ResultTableImpl(select_result)))); } -ResultTableImpl::ResultTableImpl(ProtoSelectQueryResult *result_table) : ScalarProtoMessageWrapper<ProtoSelectQueryResult>(result_table) {} +ResultTableImpl::ResultTableImpl(ProtoSelectQueryResult *result_table) : ScalarProtoMessageWrapper<ProtoSelectQueryResult>(result_table) { + for (auto &column : *this->wrapped->mutable_header()->mutable_columns()) { + this->columns.emplace_back(std::unique_ptr<ResultTableColumnImpl>(new ResultTableColumnImpl(&column))); + } +} ResultTable::ResultTable(std::unique_ptr<ResultTableImpl> delegate) : delegate(std::move(delegate)) {} @@ -83,16 +104,45 @@ auto ResultTable::size() const noexcept -> int { return 0; } -ResultTable::HeaderIterator::HeaderIterator(const ResultTable *result_table_param, int index) : current_index(index), result_table(result_table_param) {} - auto ResultTable::GetHeader() const noexcept -> const HeaderIterator { return HeaderIterator(this, 0); } +ResultTable::HeaderIterator::HeaderIterator(const ResultTable *result_table_param, int index) : current_index(index), result_table(result_table_param) {} + +ResultTable::HeaderIterator::HeaderIterator(const HeaderIterator &other) : current_index(other.current_index), result_table(other.result_table) {} + auto ResultTable::HeaderIterator::size() const noexcept -> int { return this->result_table->delegate->wrapped->header().columns_size(); } +auto ResultTable::HeaderIterator::operator*() const -> const ResultTableColumn & { + return this->result_table->delegate->columns.at(this->current_index); +} + +auto ResultTable::HeaderIterator::operator++() -> HeaderIterator & { + current_index++; + return *this; +} + +auto ResultTable::HeaderIterator::operator++(int) -> HeaderIterator { + HeaderIterator tmp(*this); + operator++(); + return tmp; +} + +auto ResultTable::HeaderIterator::operator!=(const HeaderIterator &rhs) const -> bool { + return this->current_index != rhs.current_index; +} + +auto ResultTable::HeaderIterator::begin() const -> HeaderIterator { + return HeaderIterator(this->result_table); +} + +auto ResultTable::HeaderIterator::end() const -> HeaderIterator { + return HeaderIterator(this->result_table, size()); +} + ResultSet::iterator::iterator(const ResultSet *result_set_param, int index) : current_index(index), result_set(result_set_param) {}