diff --git a/include/matador/query/abstract_pk_generator.hpp b/include/matador/query/abstract_pk_generator.hpp new file mode 100644 index 0000000..1f9fd29 --- /dev/null +++ b/include/matador/query/abstract_pk_generator.hpp @@ -0,0 +1,19 @@ +#ifndef MATADOR_ABSTRACT_PK_GENERATOR_HPP +#define MATADOR_ABSTRACT_PK_GENERATOR_HPP + +#include "matador/utils/error.hpp" +#include "matador/utils/result.hpp" + +#include + +namespace matador::sql { +class executor; +} +namespace matador::query { +class abstract_pk_generator { +public: + virtual ~abstract_pk_generator() = default; + virtual utils::result next_id(const sql::executor& exec) = 0; +}; +} +#endif //MATADOR_ABSTRACT_PK_GENERATOR_HPP \ No newline at end of file diff --git a/include/matador/query/intermediates/fetchable_query.hpp b/include/matador/query/intermediates/fetchable_query.hpp index 4e4a963..807ff69 100644 --- a/include/matador/query/intermediates/fetchable_query.hpp +++ b/include/matador/query/intermediates/fetchable_query.hpp @@ -61,8 +61,7 @@ public: [[nodiscard]] utils::result, utils::error> fetch_one(const sql::executor &exec) const; template - utils::result, utils::error> fetch_value(const sql::executor &exec) - { + utils::result, utils::error> fetch_value(const sql::executor &exec) { const auto result = fetch_one(exec); if (!result.is_ok()) { return utils::failure(result.err()); diff --git a/include/matador/query/sequence_pk_generator.hpp b/include/matador/query/sequence_pk_generator.hpp new file mode 100644 index 0000000..1cea571 --- /dev/null +++ b/include/matador/query/sequence_pk_generator.hpp @@ -0,0 +1,20 @@ +#ifndef MATADOR_SEQUENCE_PK_GENERATOR_H +#define MATADOR_SEQUENCE_PK_GENERATOR_H + +#include "matador/query/abstract_pk_generator.hpp" +#include "matador/query/intermediates/fetchable_query.hpp" + +#include + +namespace matador::query { +class sequence_pk_generator : public abstract_pk_generator { +public: + explicit sequence_pk_generator(const std::string& sequence_name); + + utils::result next_id(const sql::executor& exec) override; + +private: + fetchable_query query_; +}; +} +#endif //MATADOR_SEQUENCE_PK_GENERATOR_H \ No newline at end of file diff --git a/source/orm/CMakeLists.txt b/source/orm/CMakeLists.txt index f01d7ff..25e9159 100644 --- a/source/orm/CMakeLists.txt +++ b/source/orm/CMakeLists.txt @@ -1,6 +1,7 @@ add_library(matador-orm STATIC ../../include/matador/orm/error_code.hpp ../../include/matador/orm/session.hpp + ../../include/matador/query/abstract_pk_generator.hpp ../../include/matador/query/attribute_string_writer.hpp ../../include/matador/query/basic_schema.hpp ../../include/matador/query/builder.hpp @@ -19,6 +20,7 @@ add_library(matador-orm STATIC ../../include/matador/query/fk_value_extractor.hpp ../../include/matador/query/generator.hpp ../../include/matador/query/insert_query_builder.hpp + ../../include/matador/query/insert_query_builder.hpp ../../include/matador/query/intermediates/executable_query.hpp ../../include/matador/query/intermediates/fetchable_query.hpp ../../include/matador/query/intermediates/query_alter_intermediate.hpp @@ -64,6 +66,7 @@ add_library(matador-orm STATIC ../../include/matador/query/query_utils.hpp ../../include/matador/query/schema.hpp ../../include/matador/query/select_query_builder.hpp + ../../include/matador/query/sequence_pk_generator.hpp ../../include/matador/query/table.hpp ../../include/matador/query/table_column.hpp ../../include/matador/query/table_constraint.hpp @@ -159,6 +162,7 @@ add_library(matador-orm STATIC query/query_utils.cpp query/schema.cpp query/select_query_builder.cpp + query/sequence_pk_generator.cpp query/table.cpp query/table_column.cpp query/table_constraint.cpp @@ -188,9 +192,7 @@ add_library(matador-orm STATIC sql/resolver_service.cpp sql/statement.cpp sql/statement_cache.cpp - ../../include/matador/query/insert_query_builder.hpp - query/abstract_pk_generator.hpp - ) +) target_include_directories(matador-orm PUBLIC diff --git a/source/orm/query/abstract_pk_generator.hpp b/source/orm/query/abstract_pk_generator.hpp deleted file mode 100644 index 9241872..0000000 --- a/source/orm/query/abstract_pk_generator.hpp +++ /dev/null @@ -1,11 +0,0 @@ -#ifndef MATADOR_ABSTRACT_PK_GENERATOR_HPP -#define MATADOR_ABSTRACT_PK_GENERATOR_HPP - -namespace matador::query { -class abstract_pk_generator { -public: - virtual ~abstract_pk_generator() = default; - virtual unsigned int generate() = 0; -}; -} -#endif //MATADOR_ABSTRACT_PK_GENERATOR_HPP \ No newline at end of file diff --git a/source/orm/query/sequence_pk_generator.cpp b/source/orm/query/sequence_pk_generator.cpp new file mode 100644 index 0000000..7f529eb --- /dev/null +++ b/source/orm/query/sequence_pk_generator.cpp @@ -0,0 +1,19 @@ +#include "matador/query/sequence_pk_generator.hpp" +#include "matador/query/query.hpp" + +#include "matador/sql/error_code.hpp" + +namespace matador::query { +sequence_pk_generator::sequence_pk_generator(const std::string& sequence_name) +: query_(query::select().nextval(sequence_name)) { +} + +utils::result sequence_pk_generator::next_id(const sql::executor& exec) { + return query_.fetch_value(exec).and_then([](std::optional id) -> utils::result { + if (!id) { + return utils::failure(utils::error(sql::error_code::RETRIEVE_DATA_FAILED, "Sequence returned no value")); + } + return utils::ok(*id); + }); +} +} diff --git a/todo.md b/todo.md index 5c88955..1eedf22 100644 --- a/todo.md +++ b/todo.md @@ -17,7 +17,33 @@ 6. Add `manual_pk_generator` class 7. Extend `session::insert` logic to use pk generator 8. Add generator to `schema_node` or `table` class when attaching type -9. add `make_object`function + +```cpp +struct abstract_pk_generator { + virtual ~abstract_pk_generator() = default; + virtual int64_t next_id() = 0; + virtual std::vector next_ids(int count) = 0; +}; + +struct sequence_pk_generator : abstract_pk_generator { + explicit sequence_pk_generator(const std::string& sequence_name) + : query_(query::query::select().nextval(sequence_name)) {} + int64_t next_id(sql::executor& exec) override { + return query_.fetch_value(exec); + } + std::vector next_ids(int count) override; +private: + query::fetchable_query query_; +}; + +struct table_pk_generator : abstract_pk_generator { + explicit table_pk_generator(const std::string& table_name); + int64_t next_id() override; + std::vector next_ids(int count) override; +private: + std::string table_name_; +}; +``` __Proposal for polymorphic classes:__ @@ -32,8 +58,10 @@ If all checks succeed, the requested is fetched from the database. ```cpp schema.attach("payloads", make_polymorph("type")); -schema.attach("id_list_payloads", make_polymorph_type("IdPayload")); -schema.attach("id_payloads", make_polymorph_type("IdListPayload")); +schema.attach("id_list_payloads", {"IdPayload"}); +schema.attach("id_payloads", {"IdListPayload"}); +//schema.attach("id_list_payloads", make_polymorph_type("IdPayload")); +//schema.attach("id_payloads", make_polymorph_type("IdListPayload")); object::object_ptr payload; auto result = payload.as(); if (result.is_ok()) {