Compare commits
4 Commits
59e1533cca
...
a34a3dc266
| Author | SHA1 | Date |
|---|---|---|
|
|
a34a3dc266 | |
|
|
b6456356b4 | |
|
|
9b25f7f556 | |
|
|
78eb5d04cd |
|
|
@ -281,7 +281,7 @@ utils::result<std::vector<object::attribute>, utils::error> postgres_connection:
|
||||||
null_opt = object::null_option_type::NotNull;
|
null_opt = object::null_option_type::NotNull;
|
||||||
}
|
}
|
||||||
// f.default_value(res->column(4));
|
// f.default_value(res->column(4));
|
||||||
prototype.emplace_back(name, type, utils::NullAttributes, null_opt);
|
prototype.emplace_back(name, type, NullAttributes, null_opt);
|
||||||
}
|
}
|
||||||
|
|
||||||
return utils::ok(prototype);
|
return utils::ok(prototype);
|
||||||
|
|
|
||||||
|
|
@ -20,14 +20,15 @@ struct author {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key( op, "id", id );
|
field::primary_key( op, "id", id );
|
||||||
field::attribute( op, "first_name", first_name, 63 );
|
field::attribute( op, "first_name", first_name, VarChar63 );
|
||||||
field::attribute( op, "last_name", last_name, 63 );
|
field::attribute( op, "last_name", last_name, VarChar63 );
|
||||||
field::attribute( op, "date_of_birth", date_of_birth, 31 );
|
field::attribute( op, "date_of_birth", date_of_birth, VarChar63 );
|
||||||
field::attribute( op, "year_of_birth", year_of_birth );
|
field::attribute( op, "year_of_birth", year_of_birth );
|
||||||
field::attribute( op, "distinguished", distinguished );
|
field::attribute( op, "distinguished", distinguished );
|
||||||
field::has_many( op, "books", books, "author_id", matador::utils::CascadeNoneFetchLazy );
|
field::has_many( op, "books", books, "author_id", utils::CascadeNoneFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -15,10 +15,11 @@ struct book {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key( op, "id", id );
|
field::primary_key( op, "id", id );
|
||||||
field::attribute( op, "title", title, 511 );
|
field::attribute( op, "title", title, VarChar511 );
|
||||||
field::belongs_to( op, "author_id", book_author, matador::utils::CascadeNoneFetchLazy );
|
field::belongs_to( op, "author_id", book_author, utils::CascadeNoneFetchLazy );
|
||||||
field::attribute( op, "published_in", published_in );
|
field::attribute( op, "published_in", published_in );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -29,7 +29,7 @@ public:
|
||||||
attribute() = default;
|
attribute() = default;
|
||||||
attribute(std::string name,
|
attribute(std::string name,
|
||||||
utils::basic_type type,
|
utils::basic_type type,
|
||||||
const utils::field_attributes& opts = utils::NullAttributes,
|
const utils::field_attributes& opts = matador::NullAttributes,
|
||||||
null_option_type null_opt = null_option_type::NotNull)
|
null_option_type null_opt = null_option_type::NotNull)
|
||||||
: name_(std::move(name)), type_(type), options_(opts), null_option_type_(null_opt) {}
|
: name_(std::move(name)), type_(type), options_(opts), null_option_type_(null_opt) {}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -13,8 +13,7 @@
|
||||||
namespace demo {
|
namespace demo {
|
||||||
|
|
||||||
struct recipe;
|
struct recipe;
|
||||||
struct ingredient
|
struct ingredient {
|
||||||
{
|
|
||||||
unsigned int id{};
|
unsigned int id{};
|
||||||
std::string name;
|
std::string name;
|
||||||
matador::object::collection<matador::object::object_ptr<demo::recipe>> recipes{};
|
matador::object::collection<matador::object::object_ptr<demo::recipe>> recipes{};
|
||||||
|
|
@ -25,15 +24,15 @@ struct ingredient
|
||||||
|
|
||||||
template<class Operator>
|
template<class Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, VarChar255);
|
||||||
field::has_many_to_many(op, "recipe_ingredients", recipes, "ingredient_id", "recipe_id", matador::utils::fetch_type::Eager);
|
field::has_many_to_many(op, "recipe_ingredients", recipes, "ingredient_id", "recipe_id", utils::CascadeAllFetchEager);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct recipe
|
struct recipe {
|
||||||
{
|
|
||||||
unsigned int id{};
|
unsigned int id{};
|
||||||
std::string name;
|
std::string name;
|
||||||
matador::object::collection<matador::object::object_ptr<demo::ingredient>> ingredients{};
|
matador::object::collection<matador::object::object_ptr<demo::ingredient>> ingredients{};
|
||||||
|
|
@ -44,10 +43,11 @@ struct recipe
|
||||||
|
|
||||||
template<class Operator>
|
template<class Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, VarChar255);
|
||||||
field::has_many_to_many(op, "recipe_ingredients", ingredients, matador::utils::fetch_type::Lazy);
|
field::has_many_to_many(op, "recipe_ingredients", ingredients, utils::CascadeAllFetchLazy);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -81,11 +81,12 @@ struct profile {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key( op, "id", id );
|
field::primary_key( op, "id", id );
|
||||||
field::attribute( op, "first_name", first_name, 255 );
|
field::attribute( op, "first_name", first_name, VarChar255 );
|
||||||
field::attribute( op, "last_name", last_name, 255 );
|
field::attribute( op, "last_name", last_name, VarChar255 );
|
||||||
field::belongs_to( op, "user_id", user, matador::utils::CascadeNoneFetchLazy );
|
field::belongs_to( op, "user_id", user, utils::CascadeNoneFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
struct user {
|
struct user {
|
||||||
|
|
@ -95,10 +96,11 @@ struct user {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::primary_key( op, "id", id );
|
field::primary_key( op, "id", id );
|
||||||
field::attribute( op, "username", username, 255 );
|
field::attribute( op, "username", username, VarChar255 );
|
||||||
field::has_one(op, "profile_id", profile, matador::utils::CascadeNoneFetchLazy );
|
field::has_one(op, "profile_id", profile, utils::CascadeNoneFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
@ -108,9 +110,10 @@ struct person {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
|
using namespace matador;
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key( op, "id", id );
|
field::primary_key( op, "id", id );
|
||||||
field::attribute( op, "name", name, 255 );
|
field::attribute( op, "name", name, VarChar255 );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -36,12 +36,13 @@ struct CollectionCenter : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
|
using namespace matador;
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, UniqueVarChar511 );
|
||||||
field::attribute( op, "symbol", symbol );
|
field::attribute( op, "symbol", symbol );
|
||||||
field::attribute( op, "type", type );
|
field::attribute( op, "type", type );
|
||||||
field::has_many( op, "collection_center_users", users, "users_id", matador::utils::fetch_type::Lazy );
|
field::has_many( op, "collection_center_users", users, "users_id", utils::CascadeAllFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -15,4 +15,4 @@ struct InternalUserDirectory : UserDirectory {
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif //INTERNALUSERDIRECTORY_HPP
|
#endif //INTERNAL_USER_DIRECTORY_HPP
|
||||||
|
|
|
||||||
|
|
@ -16,11 +16,12 @@ struct LdapGroupSchemaSettings : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::has_one(op, "ldap_user_directory", ldap_user_directory, matador::utils::CascadeAllFetchLazy);
|
field::has_one(op, "ldap_user_directory", ldap_user_directory, utils::CascadeAllFetchLazy);
|
||||||
field::attribute( op, "group_object_filter", group_object_filter, 511 );
|
field::attribute( op, "group_object_filter", group_object_filter, VarChar511 );
|
||||||
field::attribute( op, "user_member_attribute", user_member_attribute, 511 );
|
field::attribute( op, "user_member_attribute", user_member_attribute, VarChar511 );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -17,10 +17,11 @@ struct LdapImportSettings : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::has_one(op, "ldap_user_directory", ldap_user_directory, matador::utils::CascadeAllFetchLazy);
|
field::has_one(op, "ldap_user_directory", ldap_user_directory, utils::CascadeAllFetchLazy);
|
||||||
field::attribute( op, "default_role", default_role, 511 );
|
field::attribute( op, "default_role", default_role, VarChar511 );
|
||||||
field::attribute( op, "sync_interval", sync_interval );
|
field::attribute( op, "sync_interval", sync_interval );
|
||||||
field::attribute( op, "network_timeout", network_timeout );
|
field::attribute( op, "network_timeout", network_timeout );
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -25,16 +25,17 @@ struct LdapUserDirectory : UserDirectory {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<UserDirectory>( this ) );
|
field::process( op, *matador::base_class<UserDirectory>( this ) );
|
||||||
field::attribute( op, "schema_base_dn", schema_base_dn, 511 );
|
field::attribute( op, "schema_base_dn", schema_base_dn, VarChar511 );
|
||||||
field::attribute( op, "additional_user_base_dn", additional_user_base_dn, 511 );
|
field::attribute( op, "additional_user_base_dn", additional_user_base_dn, VarChar511 );
|
||||||
field::attribute( op, "additional_group_base_dn", additional_group_base_dn, 511 );
|
field::attribute( op, "additional_group_base_dn", additional_group_base_dn, VarChar511 );
|
||||||
field::belongs_to( op, "user_schema_settings", user_schema_settings, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "user_schema_settings", user_schema_settings, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "group_schema_settings", group_schema_settings, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "group_schema_settings", group_schema_settings, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "import_settings", import_settings, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "import_settings", import_settings, utils::CascadeAllFetchLazy );
|
||||||
field::has_many( op, "ldap_users", users, "users_id", matador::utils::CascadeAllFetchEager );
|
field::has_many( op, "ldap_users", users, "users_id", utils::CascadeAllFetchEager );
|
||||||
field::has_many( op, "ldap_groups", groups, "groups_id", matador::utils::CascadeAllFetchEager );
|
field::has_many( op, "ldap_groups", groups, "groups_id", utils::CascadeAllFetchEager );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -18,13 +18,14 @@ struct LdapUserSchemaSettings : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process(op, *matador::base_class<Model>( this ));
|
field::process(op, *matador::base_class<Model>( this ));
|
||||||
field::has_one(op, "ldap_user_directory", ldap_user_directory, matador::utils::CascadeAllFetchLazy);
|
field::has_one(op, "ldap_user_directory", ldap_user_directory, utils::CascadeAllFetchLazy);
|
||||||
field::attribute(op, "user_object_filter", user_object_filter, 511);
|
field::attribute(op, "user_object_filter", user_object_filter, VarChar511);
|
||||||
field::attribute(op, "user_unique_id_attribute", user_unique_id_attribute, 511);
|
field::attribute(op, "user_unique_id_attribute", user_unique_id_attribute, VarChar511);
|
||||||
field::attribute(op, "user_member_of_attribute", user_member_of_attribute, 511);
|
field::attribute(op, "user_member_of_attribute", user_member_of_attribute, VarChar511);
|
||||||
field::attribute(op, "user_name_attribute", user_name_attribute, 511);
|
field::attribute(op, "user_name_attribute", user_name_attribute, VarChar511);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -51,13 +51,14 @@ struct LoginHistory : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process_base<Model>( op, *this );
|
field::process_base<Model>( op, *this );
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::belongs_to( op, "client", client, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "client", client, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "scenario", scenario, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "scenario", scenario, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "collection_center", collection_center, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "collection_center", collection_center, utils::CascadeAllFetchLazy );
|
||||||
field::attribute( op, "login_name", login_name, 511 );
|
field::attribute( op, "login_name", login_name, VarChar511 );
|
||||||
field::attribute( op, "fail_reason", fail_reason );
|
field::attribute( op, "fail_reason", fail_reason );
|
||||||
field::attribute( op, "login_time", login_time );
|
field::attribute( op, "login_time", login_time );
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -46,14 +46,15 @@ struct Scenario : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, UniqueVarChar511 );
|
||||||
field::attribute( op, "mode", mode );
|
field::attribute( op, "mode", mode );
|
||||||
field::attribute( op, "description", description, 511 );
|
field::attribute( op, "description", description, VarChar511 );
|
||||||
field::attribute( op, "symbol", symbol );
|
field::attribute( op, "symbol", symbol );
|
||||||
field::attribute( op, "state", state );
|
field::attribute( op, "state", state );
|
||||||
field::has_many( op, "collection_center", collection_center, "scenario_id", matador::utils::fetch_type::Lazy );
|
field::has_many( op, "collection_center", collection_center, "scenario_id", utils::CascadeAllFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -29,17 +29,18 @@ struct User : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, UniqueVarChar511 );
|
||||||
field::attribute( op, "symbol", symbol );
|
field::attribute( op, "symbol", symbol );
|
||||||
field::attribute( op, "salt", salt, 511 );
|
field::attribute( op, "salt", salt, VarChar511 );
|
||||||
field::attribute( op, "password", password, 511 );
|
field::attribute( op, "password", password, VarChar511 );
|
||||||
field::attribute( op, "lock_type", lock_type );
|
field::attribute( op, "lock_type", lock_type );
|
||||||
field::attribute( op, "locked_at", locked_at );
|
field::attribute( op, "locked_at", locked_at );
|
||||||
field::attribute( op, "lock_reason", lock_reason, 511 );
|
field::attribute( op, "lock_reason", lock_reason, VarChar511 );
|
||||||
field::attribute( op, "role", role, 63 );
|
field::attribute( op, "role", role, VarChar63 );
|
||||||
field::belongs_to( op, "user_directory", user_directory, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "user_directory", user_directory, utils::CascadeAllFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -13,7 +13,7 @@ struct UserDirectory : core::Model {
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, matador::VarChar511 );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -21,11 +21,12 @@ struct UserSession : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
using namespace matador;
|
||||||
|
namespace field = access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::belongs_to( op, "client", client, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "client", client, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "scenario", scenario, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "scenario", scenario, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "collection_center", collection_center, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "collection_center", collection_center, utils::CascadeAllFetchLazy );
|
||||||
field::attribute( op, "offline_since", offline_since );
|
field::attribute( op, "offline_since", offline_since );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@
|
||||||
#define USERINFO_HPP
|
#define USERINFO_HPP
|
||||||
|
|
||||||
#include "matador/utils/access.hpp"
|
#include "matador/utils/access.hpp"
|
||||||
|
#include "matador/utils/field_attributes.hpp"
|
||||||
|
|
||||||
namespace work::core {
|
namespace work::core {
|
||||||
struct UserInfo {
|
struct UserInfo {
|
||||||
|
|
@ -12,9 +13,10 @@ struct UserInfo {
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
|
using namespace matador;
|
||||||
field::attribute( op, "user_session_id", user_session_id );
|
field::attribute( op, "user_session_id", user_session_id );
|
||||||
field::attribute( op, "user_role", user_role, 255 );
|
field::attribute( op, "user_role", user_role, VarChar255 );
|
||||||
field::attribute( op, "database_name", database_name, 255 );
|
field::attribute( op, "database_name", database_name, VarChar255 );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -30,15 +30,16 @@ struct Job : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
|
using namespace matador;
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, UniqueVarChar511 );
|
||||||
field::attribute( op, "description", description, 511 );
|
field::attribute( op, "description", description, VarChar1023 );
|
||||||
field::attribute( op, "state", state );
|
field::attribute( op, "state", state );
|
||||||
field::attribute( op, "mode", mode );
|
field::attribute( op, "mode", mode );
|
||||||
field::attribute( op, "created_at", created_at );
|
field::attribute( op, "created_at", created_at );
|
||||||
field::has_one(op, "payload", payload, matador::utils::CascadeAllFetchLazy );
|
field::has_one(op, "payload", payload, utils::CascadeAllFetchLazy );
|
||||||
field::belongs_to( op, "task", task, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "task", task, utils::CascadeAllFetchLazy );
|
||||||
field::attribute( op, "user_info", user_info );
|
field::attribute( op, "user_info", user_info );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -16,10 +16,11 @@ struct Payload : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
|
using namespace matador;
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "type", type, 255 );
|
field::attribute( op, "type", type, VarChar255 );
|
||||||
field::belongs_to( op, "job", job, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "job", job, utils::CascadeAllFetchLazy );
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,13 +26,14 @@ struct Task : core::Model {
|
||||||
|
|
||||||
template<typename Operator>
|
template<typename Operator>
|
||||||
void process( Operator& op ) {
|
void process( Operator& op ) {
|
||||||
|
using namespace matador;
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::process( op, *matador::base_class<Model>( this ) );
|
field::process( op, *matador::base_class<Model>( this ) );
|
||||||
field::attribute( op, "name", name, 511 );
|
field::attribute( op, "name", name, UniqueVarChar511 );
|
||||||
field::attribute( op, "description", description, 511 );
|
field::attribute( op, "description", description, VarChar1023 );
|
||||||
field::attribute( op, "job_name", job_name, 511 );
|
field::attribute( op, "job_name", job_name, VarChar511 );
|
||||||
field::attribute( op, "state", state );
|
field::attribute( op, "state", state );
|
||||||
field::belongs_to( op, "payload", payload, matador::utils::CascadeAllFetchLazy );
|
field::belongs_to( op, "payload", payload, utils::CascadeAllFetchLazy );
|
||||||
field::attribute( op, "job_mode", job_mode );
|
field::attribute( op, "job_mode", job_mode );
|
||||||
field::attribute( op, "start_delay", start_delay );
|
field::attribute( op, "start_delay", start_delay );
|
||||||
field::attribute( op, "interval", interval );
|
field::attribute( op, "interval", interval );
|
||||||
|
|
|
||||||
|
|
@ -28,7 +28,7 @@ public:
|
||||||
attribute() = default;
|
attribute() = default;
|
||||||
attribute(std::string name,
|
attribute(std::string name,
|
||||||
utils::basic_type type,
|
utils::basic_type type,
|
||||||
const utils::field_attributes &attr = utils::NullAttributes,
|
const utils::field_attributes &attr = NullAttributes,
|
||||||
null_option_type null_opt = null_option_type::NotNull);
|
null_option_type null_opt = null_option_type::NotNull);
|
||||||
|
|
||||||
[[nodiscard]] const std::string& name() const;
|
[[nodiscard]] const std::string& name() const;
|
||||||
|
|
@ -39,9 +39,9 @@ public:
|
||||||
[[nodiscard]] bool is_nullable() const;
|
[[nodiscard]] bool is_nullable() const;
|
||||||
[[nodiscard]] utils::basic_type type() const;
|
[[nodiscard]] utils::basic_type type() const;
|
||||||
[[nodiscard]] std::shared_ptr<object> owner() const;
|
[[nodiscard]] std::shared_ptr<object> owner() const;
|
||||||
void change_type(utils::basic_type type, const utils::field_attributes &attr = utils::NullAttributes);
|
void change_type(utils::basic_type type, const utils::field_attributes &attr = NullAttributes);
|
||||||
template < typename Type >
|
template < typename Type >
|
||||||
void change_type(const utils::field_attributes &attr = utils::NullAttributes) {
|
void change_type(const utils::field_attributes &attr = NullAttributes) {
|
||||||
type_ = utils::data_type_traits<Type>::type(attr.size());
|
type_ = utils::data_type_traits<Type>::type(attr.size());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -38,6 +38,8 @@ public:
|
||||||
completer.complete_node(node);
|
completer.complete_node(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class PrimaryKeyType>
|
template<class PrimaryKeyType>
|
||||||
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute & /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute & /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
|
||||||
|
|
@ -24,6 +24,8 @@ public:
|
||||||
|
|
||||||
return join_columns_;
|
return join_columns_;
|
||||||
}
|
}
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
static void on_primary_key(const char * /*id*/, V &, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, V &, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
|
||||||
|
|
@ -74,6 +74,8 @@ public:
|
||||||
return obj;
|
return obj;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class Type >
|
template < class Type >
|
||||||
void on_primary_key(const char *, Type &x, const utils::primary_key_attribute& attr);
|
void on_primary_key(const char *, Type &x, const utils::primary_key_attribute& attr);
|
||||||
void on_revision(const char *id, uint64_t &rev);
|
void on_revision(const char *id, uint64_t &rev);
|
||||||
|
|
|
||||||
|
|
@ -8,11 +8,18 @@
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|
||||||
namespace matador::object {
|
namespace matador::object {
|
||||||
|
struct null_object_ptr_t {
|
||||||
|
constexpr null_object_ptr_t() = default;
|
||||||
|
};
|
||||||
|
|
||||||
|
inline constexpr null_object_ptr_t nullobj{};
|
||||||
|
|
||||||
template <typename Type>
|
template <typename Type>
|
||||||
class object_ptr {
|
class object_ptr {
|
||||||
public:
|
public:
|
||||||
object_ptr()
|
object_ptr()
|
||||||
: proxy_(std::make_shared<object_proxy<Type>>()) {}
|
: proxy_(std::make_shared<object_proxy<Type>>()) {}
|
||||||
|
object_ptr(null_object_ptr_t) {}
|
||||||
explicit object_ptr(std::shared_ptr<Type> obj)
|
explicit object_ptr(std::shared_ptr<Type> obj)
|
||||||
: proxy_(std::make_shared<object_proxy<Type>>(obj)) {}
|
: proxy_(std::make_shared<object_proxy<Type>>(obj)) {}
|
||||||
explicit object_ptr(std::shared_ptr<object_proxy<Type>> obj)
|
explicit object_ptr(std::shared_ptr<object_proxy<Type>> obj)
|
||||||
|
|
@ -21,11 +28,19 @@ public:
|
||||||
object_ptr(object_ptr &&other) noexcept = default;
|
object_ptr(object_ptr &&other) noexcept = default;
|
||||||
object_ptr& operator=(const object_ptr &other) = default;
|
object_ptr& operator=(const object_ptr &other) = default;
|
||||||
object_ptr& operator=(object_ptr &&other) = default;
|
object_ptr& operator=(object_ptr &&other) = default;
|
||||||
|
object_ptr& operator=(null_object_ptr_t) {
|
||||||
|
proxy_.reset();
|
||||||
|
return *this;
|
||||||
|
}
|
||||||
|
|
||||||
bool operator==(const object_ptr &other) const {
|
bool operator==(const object_ptr &other) const {
|
||||||
return get() == other.get();
|
return get() == other.get();
|
||||||
}
|
}
|
||||||
|
bool operator==(null_object_ptr_t) const {
|
||||||
|
return empty();
|
||||||
|
}
|
||||||
bool operator!=(const object_ptr &other) const { return !operator==(other); }
|
bool operator!=(const object_ptr &other) const { return !operator==(other); }
|
||||||
|
bool operator!=(null_object_ptr_t) const { return !empty(); }
|
||||||
|
|
||||||
using value_type = Type;
|
using value_type = Type;
|
||||||
|
|
||||||
|
|
@ -53,7 +68,7 @@ public:
|
||||||
[[nodiscard]] bool is_detached() const { return proxy_->is_detached(); }
|
[[nodiscard]] bool is_detached() const { return proxy_->is_detached(); }
|
||||||
[[nodiscard]] bool is_removed() const { return proxy_->is_removed(); }
|
[[nodiscard]] bool is_removed() const { return proxy_->is_removed(); }
|
||||||
|
|
||||||
void change_state(object_state s) {
|
void change_state(object_state s) const {
|
||||||
if (proxy_) {
|
if (proxy_) {
|
||||||
proxy_->change_state(s);
|
proxy_->change_state(s);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -34,6 +34,8 @@ struct pk_field_locator {
|
||||||
explicit pk_field_locator (Type &obj)
|
explicit pk_field_locator (Type &obj)
|
||||||
: base(&obj) {}
|
: base(&obj) {}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template <typename PrimaryKeyType>
|
template <typename PrimaryKeyType>
|
||||||
void on_primary_key(const char *, PrimaryKeyType &pk, const utils::primary_key_attribute & /*attr*/) {
|
void on_primary_key(const char *, PrimaryKeyType &pk, const utils::primary_key_attribute & /*attr*/) {
|
||||||
// Offset bestimmen
|
// Offset bestimmen
|
||||||
|
|
|
||||||
|
|
@ -43,6 +43,8 @@ public:
|
||||||
return resolver.resolve(obj);
|
return resolver.resolve(obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class Type >
|
template < class Type >
|
||||||
void on_primary_key(const char *id, Type &pk, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *id, Type &pk, const utils::primary_key_attribute& attr) {
|
||||||
primary_key_info_.pk_column_name = id;
|
primary_key_info_.pk_column_name = id;
|
||||||
|
|
|
||||||
|
|
@ -28,6 +28,8 @@ public:
|
||||||
return finder.found_;
|
return finder.found_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class PrimaryKeyType>
|
template<class PrimaryKeyType>
|
||||||
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
@ -102,6 +104,8 @@ public:
|
||||||
completer.complete_node_relations(node);
|
completer.complete_node_relations(node);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class PrimaryKeyType>
|
template<class PrimaryKeyType>
|
||||||
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, PrimaryKeyType &/*pk*/, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
|
||||||
|
|
@ -65,16 +65,6 @@ public:
|
||||||
template<typename Type>
|
template<typename Type>
|
||||||
utils::result<sql::query_result<Type>, utils::error> find(query::criteria_ptr clause = {});
|
utils::result<sql::query_result<Type>, utils::error> find(query::criteria_ptr clause = {});
|
||||||
|
|
||||||
template<typename Type>
|
|
||||||
utils::result<void, utils::error> drop_table() const;
|
|
||||||
utils::result<void, utils::error> drop_table(const std::string &table_name) const;
|
|
||||||
|
|
||||||
[[nodiscard]] utils::result<sql::query_result<sql::record>, utils::error> fetch_all(const sql::query_context &q) const;
|
|
||||||
[[nodiscard]] utils::result<sql::execute_result, utils::error> execute(const std::string &sql) const;
|
|
||||||
|
|
||||||
[[nodiscard]] std::vector<object::attribute> describe_table(const std::string &table_name) const;
|
|
||||||
[[nodiscard]] bool table_exists(const std::string &table_name) const;
|
|
||||||
|
|
||||||
[[nodiscard]] utils::result<std::unique_ptr<sql::query_result_impl>, utils::error> fetch(const sql::query_context &ctx) const override;
|
[[nodiscard]] utils::result<std::unique_ptr<sql::query_result_impl>, utils::error> fetch(const sql::query_context &ctx) const override;
|
||||||
[[nodiscard]] utils::result<sql::execute_result, utils::error> execute(const sql::query_context &ctx) const override;
|
[[nodiscard]] utils::result<sql::execute_result, utils::error> execute(const sql::query_context &ctx) const override;
|
||||||
[[nodiscard]] utils::result<sql::statement, utils::error> prepare(const sql::query_context &ctx) override;
|
[[nodiscard]] utils::result<sql::statement, utils::error> prepare(const sql::query_context &ctx) override;
|
||||||
|
|
@ -145,6 +135,7 @@ utils::result<object::object_ptr<Type>, utils::error> session::insert(object::ob
|
||||||
} else if (const auto exec_result = result->execute(); !exec_result.is_ok()) {
|
} else if (const auto exec_result = result->execute(); !exec_result.is_ok()) {
|
||||||
return utils::failure(exec_result.err());
|
return utils::failure(exec_result.err());
|
||||||
}
|
}
|
||||||
|
step.make_object_persistent();
|
||||||
}
|
}
|
||||||
|
|
||||||
obj.change_state(object::object_state::Persistent);
|
obj.change_state(object::object_state::Persistent);
|
||||||
|
|
@ -164,6 +155,8 @@ public:
|
||||||
return stmt_;
|
return stmt_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class Type>
|
template<class Type>
|
||||||
void on_primary_key(const char * /*id*/, Type &x, const utils::primary_key_attribute & /*attr*/) {
|
void on_primary_key(const char * /*id*/, Type &x, const utils::primary_key_attribute & /*attr*/) {
|
||||||
stmt_.bind(binding_position_, x);
|
stmt_.bind(binding_position_, x);
|
||||||
|
|
@ -310,15 +303,5 @@ utils::result<sql::query_result<Type>, utils::error> session::find(query::criter
|
||||||
|
|
||||||
return result->template fetch<Type>();
|
return result->template fetch<Type>();
|
||||||
}
|
}
|
||||||
|
|
||||||
template<typename Type>
|
|
||||||
utils::result<void, utils::error> session::drop_table() const {
|
|
||||||
const auto it = schema_.find(typeid(Type));
|
|
||||||
if (it == schema_.end()) {
|
|
||||||
return utils::failure(make_error(error_code::UnknownType, "Failed to determine requested type."));
|
|
||||||
}
|
|
||||||
return drop_table(it->second.name());
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
#endif //QUERY_SESSION_HPP
|
#endif //QUERY_SESSION_HPP
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,8 @@ public:
|
||||||
|
|
||||||
return generator_type_;
|
return generator_type_;
|
||||||
}
|
}
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class V>
|
template<class V>
|
||||||
void on_primary_key(const char * /*id*/, V &/*pk*/, const utils::primary_key_attribute &attr) {
|
void on_primary_key(const char * /*id*/, V &/*pk*/, const utils::primary_key_attribute &attr) {
|
||||||
generator_type_ = attr.generator();
|
generator_type_ = attr.generator();
|
||||||
|
|
|
||||||
|
|
@ -59,6 +59,8 @@ struct meta_registry {
|
||||||
struct dependency_collector {
|
struct dependency_collector {
|
||||||
std::vector<fk_ref> refs;
|
std::vector<fk_ref> refs;
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class V>
|
template<class V>
|
||||||
static void on_primary_key(const char*, V&, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char*, V&, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -24,6 +24,8 @@ public:
|
||||||
return value_;
|
return value_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *, ValueType &pk, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *, ValueType &pk, const utils::primary_key_attribute& /*attr*/) {
|
||||||
value_ = pk;
|
value_ = pk;
|
||||||
|
|
|
||||||
|
|
@ -63,6 +63,8 @@ public:
|
||||||
return result_;
|
return result_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
||||||
push(id);
|
push(id);
|
||||||
|
|
@ -169,6 +171,8 @@ public:
|
||||||
return result_;
|
return result_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char * /*id*/, V &/*x*/, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char * /*id*/, V &/*x*/, const utils::primary_key_attribute& /*attr*/) {
|
||||||
result_.emplace_back(utils::_);
|
result_.emplace_back(utils::_);
|
||||||
|
|
@ -227,6 +231,8 @@ public:
|
||||||
return std::move(result_);
|
return std::move(result_);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char *id, V &x, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *id, V &x, const utils::primary_key_attribute& /*attr*/) {
|
||||||
push_back(id, x);
|
push_back(id, x);
|
||||||
|
|
|
||||||
|
|
@ -23,6 +23,8 @@ class has_many_linker {
|
||||||
public:
|
public:
|
||||||
has_many_linker(const object::object_ptr<ObjectType> &ptr, std::string join_column)
|
has_many_linker(const object::object_ptr<ObjectType> &ptr, std::string join_column)
|
||||||
: ptr_(ptr), join_column_(std::move(join_column)) {}
|
: ptr_(ptr), join_column_(std::move(join_column)) {}
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class PrimaryKeyType >
|
template < class PrimaryKeyType >
|
||||||
static void on_primary_key(const char * /*id*/, PrimaryKeyType &, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, PrimaryKeyType &, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
@ -64,6 +66,7 @@ struct insert_step {
|
||||||
std::function<void(const sql::record &)> apply_returning{};
|
std::function<void(const sql::record &)> apply_returning{};
|
||||||
std::function<void(const utils::identifier &)> apply_primary_key{};
|
std::function<void(const utils::identifier &)> apply_primary_key{};
|
||||||
std::function<void(sql::statement &)> bind_object{};
|
std::function<void(sql::statement &)> bind_object{};
|
||||||
|
std::function<void()> make_object_persistent{};
|
||||||
};
|
};
|
||||||
|
|
||||||
template<class ObjectType>
|
template<class ObjectType>
|
||||||
|
|
@ -139,23 +142,30 @@ public:
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (processing_many_to_many_relations_.find(id) != processing_many_to_many_relations_.end()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
const auto it = schema_.find(std::string{id});
|
const auto it = schema_.find(std::string{id});
|
||||||
if (it == schema_.end()) {
|
if (it == schema_.end()) {
|
||||||
throw query_builder_exception(query_build_error::UnknownType);
|
throw query_builder_exception(query_build_error::UnknownType);
|
||||||
}
|
}
|
||||||
|
|
||||||
using relation_value_type = object::many_to_many_relation<ObjectType, ForeignType>;
|
using relation_value_type = object::many_to_many_relation<ForeignType, ObjectType>;
|
||||||
|
|
||||||
if (std::type_index(typeid(relation_value_type)) != it->second.node().info().type_index()) {
|
if (std::type_index(typeid(relation_value_type)) != it->second.node().info().type_index()) {
|
||||||
throw query_builder_exception(query_build_error::InvalidRelationType);
|
throw query_builder_exception(query_build_error::InvalidRelationType);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto &obj : objects) {
|
const auto cit = contexts_by_type_.find(it->second.node().info().type_index());
|
||||||
if (!obj) {
|
if (cit == contexts_by_type_.end()) {
|
||||||
continue;
|
throw query_builder_exception(query_build_error::UnknownType);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (obj.is_persistent()) {
|
const auto rel_it = processing_many_to_many_relations_.insert(id);
|
||||||
|
std::vector<insert_step> rel_steps;
|
||||||
|
for (auto &obj : objects) {
|
||||||
|
if (!obj) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -164,24 +174,32 @@ public:
|
||||||
build_for(obj, relation_steps_);
|
build_for(obj, relation_steps_);
|
||||||
}
|
}
|
||||||
|
|
||||||
auto rel = object::make_object<relation_value_type>(join_column, inverse_join_column, ptr_, obj);
|
auto rel = object::make_object<relation_value_type>(join_column, inverse_join_column, obj, ptr_);
|
||||||
|
|
||||||
// Extract FK value from the foreign object
|
access::process(*this, *rel);
|
||||||
insert_step rel_step{};
|
|
||||||
// const auto pk = rel_step.pk_accessor.get(*obj);
|
|
||||||
// if (pk.is_valid()) {
|
|
||||||
// continue;
|
|
||||||
// }
|
|
||||||
|
|
||||||
relation_steps_.push_back(std::move(rel_step));
|
insert_step step{};
|
||||||
|
step.pk_generator = utils::generator_type::None;
|
||||||
|
step.ctx = cit->second.insert;
|
||||||
|
step.bind_object = [rel](sql::statement &stmt) { stmt.bind(*rel); };
|
||||||
|
step.make_object_persistent = [] {};
|
||||||
|
|
||||||
|
rel_steps.push_back(std::move(step));
|
||||||
}
|
}
|
||||||
|
relation_steps_.insert(relation_steps_.end(), rel_steps.begin(), rel_steps.end());
|
||||||
|
processing_many_to_many_relations_.erase(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class ForeignType>
|
template<class ForeignType>
|
||||||
void on_has_many_to_many(const char *id, object::collection<object::object_ptr<ForeignType>> &objects, const utils::foreign_attributes &attr) {
|
void on_has_many_to_many(const char *id, object::collection<object::object_ptr<ForeignType>> &objects, const utils::foreign_attributes &attr) {
|
||||||
if (!utils::is_cascade_type_set(attr.cascade(), utils::cascade_type::Insert)) {
|
if (!utils::is_cascade_type_set(attr.cascade(), utils::cascade_type::Insert)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (processing_many_to_many_relations_.find(id) != processing_many_to_many_relations_.end()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
object::join_columns_collector collector;
|
object::join_columns_collector collector;
|
||||||
auto join_columns = collector.collect<ForeignType>();
|
auto join_columns = collector.collect<ForeignType>();
|
||||||
|
|
||||||
|
|
@ -196,12 +214,15 @@ public:
|
||||||
throw query_builder_exception(query_build_error::InvalidRelationType);
|
throw query_builder_exception(query_build_error::InvalidRelationType);
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto &obj : objects) {
|
const auto cit = contexts_by_type_.find(it->second.node().info().type_index());
|
||||||
if (!obj) {
|
if (cit == contexts_by_type_.end()) {
|
||||||
continue;
|
throw query_builder_exception(query_build_error::UnknownType);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (obj.is_persistent()) {
|
const auto rel_it = processing_many_to_many_relations_.insert(id);
|
||||||
|
std::vector<insert_step> rel_steps;
|
||||||
|
for (auto &obj : objects) {
|
||||||
|
if (!obj) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -212,23 +233,20 @@ public:
|
||||||
|
|
||||||
auto rel = object::make_object<relation_value_type>(join_columns.inverse_join_column, join_columns.join_column, obj, ptr_);
|
auto rel = object::make_object<relation_value_type>(join_columns.inverse_join_column, join_columns.join_column, obj, ptr_);
|
||||||
|
|
||||||
// Extract FK value from the foreign object
|
access::process(*this, *rel);
|
||||||
insert_step rel_step{};
|
|
||||||
// const auto pk = rel_step.pk_accessor.get(*obj);
|
|
||||||
// if (pk.is_valid()) {
|
|
||||||
// continue;
|
|
||||||
// }
|
|
||||||
|
|
||||||
relation_steps_.push_back(std::move(rel_step));
|
insert_step step{};
|
||||||
|
step.pk_generator = utils::generator_type::None;
|
||||||
|
step.ctx = cit->second.insert;
|
||||||
|
step.bind_object = [rel](sql::statement &stmt) { stmt.bind(*rel); };
|
||||||
|
step.make_object_persistent = [] {};
|
||||||
|
|
||||||
|
rel_steps.push_back(std::move(step));
|
||||||
}
|
}
|
||||||
|
relation_steps_.insert(relation_steps_.end(), rel_steps.begin(), rel_steps.end());
|
||||||
|
processing_many_to_many_relations_.erase(id);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class CollectionType>
|
|
||||||
void process_has_many_to_many(const char *id, CollectionType &objects, const char *join_column, const char *inverse_join_column) {
|
|
||||||
if (id == nullptr || join_column == nullptr || inverse_join_column == nullptr) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
private:
|
private:
|
||||||
template<class EntityType>
|
template<class EntityType>
|
||||||
static std::pair<std::type_index, const void *> make_visit_key(const object::object_ptr<EntityType> &ptr) {
|
static std::pair<std::type_index, const void *> make_visit_key(const object::object_ptr<EntityType> &ptr) {
|
||||||
|
|
@ -292,6 +310,7 @@ private:
|
||||||
step.pk_accessor.set(*ptr, id);
|
step.pk_accessor.set(*ptr, id);
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
step.make_object_persistent = [ptr] { ptr.change_state(object::object_state::Persistent); };
|
||||||
steps.push_back(std::move(step));
|
steps.push_back(std::move(step));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -318,6 +337,7 @@ private:
|
||||||
std::vector<insert_step> steps_;
|
std::vector<insert_step> steps_;
|
||||||
std::vector<insert_step> relation_steps_;
|
std::vector<insert_step> relation_steps_;
|
||||||
std::unordered_set<std::pair<std::type_index, const void *>, visit_key_hash> visited_;
|
std::unordered_set<std::pair<std::type_index, const void *>, visit_key_hash> visited_;
|
||||||
|
std::unordered_set<std::string> processing_many_to_many_relations_;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
#endif //MATADOR_INSERT_QUERY_BUILDER_HPP
|
#endif //MATADOR_INSERT_QUERY_BUILDER_HPP
|
||||||
|
|
@ -26,6 +26,8 @@ public:
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char *id, V &x, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *id, V &x, const utils::primary_key_attribute& /*attr*/) {
|
||||||
result_.emplace_back(id, x);
|
result_.emplace_back(id, x);
|
||||||
|
|
|
||||||
|
|
@ -60,6 +60,8 @@ public:
|
||||||
, root_type_(root_type)
|
, root_type_(root_type)
|
||||||
{}
|
{}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
static void on_primary_key(const char * /*id*/, ValueType &/*value*/, const utils::primary_key_attribute& /*attr*/) {}
|
static void on_primary_key(const char * /*id*/, ValueType &/*value*/, const utils::primary_key_attribute& /*attr*/) {}
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
|
||||||
|
|
@ -89,6 +89,9 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
|
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
||||||
push(id);
|
push(id);
|
||||||
|
|
|
||||||
|
|
@ -25,6 +25,8 @@ public:
|
||||||
return values;
|
return values;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *, ValueType &x, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *, ValueType &x, const utils::primary_key_attribute& attr) {
|
||||||
utils::data_type_traits<ValueType>::bind_value(*this, 0, x, attr.size());
|
utils::data_type_traits<ValueType>::bind_value(*this, 0, x, attr.size());
|
||||||
|
|
|
||||||
|
|
@ -44,6 +44,8 @@ public:
|
||||||
return columns;
|
return columns;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class V >
|
template < class V >
|
||||||
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
void on_primary_key(const char *id, V &, const utils::primary_key_attribute& /*attr*/) {
|
||||||
if (has_many_to_many_) {
|
if (has_many_to_many_) {
|
||||||
|
|
|
||||||
|
|
@ -22,6 +22,8 @@ public:
|
||||||
return identifier_;
|
return identifier_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr) {
|
||||||
utils::data_type_traits<ValueType>::read_value(reader_, id, column_index_, value, attr.size());
|
utils::data_type_traits<ValueType>::read_value(reader_, id, column_index_, value, attr.size());
|
||||||
|
|
|
||||||
|
|
@ -27,6 +27,8 @@ public:
|
||||||
binder_ = nullptr;
|
binder_ = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
||||||
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
static void on_revision(const char * /*id*/, uint64_t &/*rev*/) {}
|
||||||
|
|
@ -73,6 +75,8 @@ public:
|
||||||
|
|
||||||
void reset();
|
void reset();
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class Type >
|
template < class Type >
|
||||||
void on_primary_key(const char *id, Type &val, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *id, Type &val, const utils::primary_key_attribute& attr) {
|
||||||
utils::data_type_traits<Type>::read_value(*binder_, id, index_++, val, attr.size());
|
utils::data_type_traits<Type>::read_value(*binder_, id, index_++, val, attr.size());
|
||||||
|
|
|
||||||
|
|
@ -14,6 +14,8 @@ public:
|
||||||
access::process(*this, obj);
|
access::process(*this, obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
||||||
void on_revision(const char * /*id*/, uint64_t &/*rev*/) {
|
void on_revision(const char * /*id*/, uint64_t &/*rev*/) {
|
||||||
|
|
|
||||||
|
|
@ -40,6 +40,8 @@ public:
|
||||||
const std::type_index& result_type,
|
const std::type_index& result_type,
|
||||||
size_t column_index = 0);
|
size_t column_index = 0);
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr) {
|
||||||
utils::data_type_traits<ValueType>::read_value(*reader_, id, column_index_++, value, attr.size());
|
utils::data_type_traits<ValueType>::read_value(*reader_, id, column_index_++, value, attr.size());
|
||||||
|
|
|
||||||
|
|
@ -27,6 +27,8 @@ public:
|
||||||
return pk_;
|
return pk_;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &/*value*/, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char *id, ValueType &/*value*/, const utils::primary_key_attribute& attr) {
|
||||||
if (!type_stack_.empty()) {
|
if (!type_stack_.empty()) {
|
||||||
|
|
|
||||||
|
|
@ -17,6 +17,8 @@ public:
|
||||||
void reset(size_t start_index);
|
void reset(size_t start_index);
|
||||||
[[nodiscard]] size_t current_index() const;
|
[[nodiscard]] size_t current_index() const;
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template < class Type >
|
template < class Type >
|
||||||
void on_primary_key(const char * /*id*/, Type &val, const utils::primary_key_attribute& attr) {
|
void on_primary_key(const char * /*id*/, Type &val, const utils::primary_key_attribute& attr) {
|
||||||
utils::data_type_traits<Type>::bind_value(*binder_, index_++, val, attr.size());
|
utils::data_type_traits<Type>::bind_value(*binder_, index_++, val, attr.size());
|
||||||
|
|
|
||||||
|
|
@ -19,6 +19,8 @@ public:
|
||||||
binder_ = nullptr;
|
binder_ = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename ValueType>
|
template<typename ValueType>
|
||||||
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
void on_primary_key(const char *id, ValueType &value, const utils::primary_key_attribute& attr);
|
||||||
static void on_revision(const char * /*id*/, unsigned long long &/*rev*/) {}
|
static void on_revision(const char * /*id*/, unsigned long long &/*rev*/) {}
|
||||||
|
|
|
||||||
|
|
@ -53,12 +53,12 @@ void revision(Operator &op, const char *id, uint64_t &value) {
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class Operator, class Type>
|
template<class Operator, class Type>
|
||||||
void attribute(Operator &op, const char *id, Type &value, const utils::field_attributes &attr = utils::NullAttributes) {
|
void attribute(Operator &op, const char *id, Type &value, const utils::field_attributes &attr = NullAttributes) {
|
||||||
op.on_attribute(id, value, attr);
|
op.on_attribute(id, value, attr);
|
||||||
}
|
}
|
||||||
|
|
||||||
template<class Operator, class Type>
|
template<class Operator, class Type>
|
||||||
void attribute(Operator &op, const char *id, std::optional<Type> &value, const utils::field_attributes &attr = utils::NullAttributes) {
|
void attribute(Operator &op, const char *id, std::optional<Type> &value, const utils::field_attributes &attr = NullAttributes) {
|
||||||
op.on_attribute(id, value, attr);
|
op.on_attribute(id, value, attr);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -73,8 +73,31 @@ private:
|
||||||
size_t size_ = 0;
|
size_t size_ = 0;
|
||||||
constraints options_ = constraints::None;
|
constraints options_ = constraints::None;
|
||||||
};
|
};
|
||||||
|
|
||||||
const field_attributes NullAttributes {};
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
namespace matador {
|
||||||
|
const utils::field_attributes NullAttributes {};
|
||||||
|
const utils::field_attributes VarChar63 {63};
|
||||||
|
const utils::field_attributes VarChar127 {127};
|
||||||
|
const utils::field_attributes VarChar255 {255};
|
||||||
|
const utils::field_attributes VarChar511 {511};
|
||||||
|
const utils::field_attributes VarChar1023 {1023};
|
||||||
|
const utils::field_attributes VarChar2047 {2047};
|
||||||
|
const utils::field_attributes VarChar4095 {4095};
|
||||||
|
const utils::field_attributes UniqueVarChar63 {63, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar127 {127, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar255 {255, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar511 {511, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar1023 {1023, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar2047 {2047, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes UniqueVarChar4095 {4095, utils::constraints::Unique};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar63 {63, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar127 {127, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar255 {255, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar511 {511, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar1023 {1023, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar2047 {2047, utils::constraints::PrimaryKey};
|
||||||
|
const utils::field_attributes PrimaryKeyVarChar4095 {4095, utils::constraints::PrimaryKey};
|
||||||
|
}
|
||||||
|
|
||||||
#endif //MATADOR_FIELD_ATTRIBUTES_HPP
|
#endif //MATADOR_FIELD_ATTRIBUTES_HPP
|
||||||
|
|
|
||||||
|
|
@ -21,6 +21,8 @@ public:
|
||||||
access::process(*this, obj);
|
access::process(*this, obj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<typename PrimaryKeyType>
|
template<typename PrimaryKeyType>
|
||||||
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
||||||
const auto value = pk_.as<PrimaryKeyType>();
|
const auto value = pk_.as<PrimaryKeyType>();
|
||||||
|
|
@ -51,6 +53,8 @@ private:
|
||||||
struct pk_unset_checker {
|
struct pk_unset_checker {
|
||||||
bool unset{true};
|
bool unset{true};
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class PrimaryKeyType>
|
template<class PrimaryKeyType>
|
||||||
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
||||||
unset = !identifier_type_traits<PrimaryKeyType>::is_valid(pk);
|
unset = !identifier_type_traits<PrimaryKeyType>::is_valid(pk);
|
||||||
|
|
@ -73,6 +77,8 @@ struct pk_unset_checker {
|
||||||
struct primary_key_getter {
|
struct primary_key_getter {
|
||||||
std::uint64_t value{0};
|
std::uint64_t value{0};
|
||||||
|
|
||||||
|
template<typename BaseType>
|
||||||
|
static void on_base(const BaseType&) {}
|
||||||
template<class PrimaryKeyType>
|
template<class PrimaryKeyType>
|
||||||
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
void on_primary_key(const char * /*id*/, PrimaryKeyType &pk, const primary_key_attribute & = DefaultPkAttributes) {
|
||||||
pk_ = pk;
|
pk_ = pk;
|
||||||
|
|
|
||||||
|
|
@ -48,6 +48,14 @@ private:
|
||||||
};
|
};
|
||||||
|
|
||||||
const primary_key_attribute DefaultPkAttributes {};
|
const primary_key_attribute DefaultPkAttributes {};
|
||||||
|
const primary_key_attribute Identity {generator_type::Identity};
|
||||||
|
const primary_key_attribute ManualVarChar63 {63};
|
||||||
|
const primary_key_attribute ManualVarChar127 {127};
|
||||||
|
const primary_key_attribute ManualVarChar255 {255};
|
||||||
|
const primary_key_attribute ManualVarChar511 {511};
|
||||||
|
const primary_key_attribute ManualVarChar1023 {1023};
|
||||||
|
const primary_key_attribute ManualVarChar2047 {2047};
|
||||||
|
const primary_key_attribute ManualVarChar4095 {4095};
|
||||||
|
|
||||||
}
|
}
|
||||||
#endif //PRIMARY_KEY_ATTRIBUTE_HPP
|
#endif //PRIMARY_KEY_ATTRIBUTE_HPP
|
||||||
|
|
|
||||||
|
|
@ -3,6 +3,7 @@
|
||||||
|
|
||||||
namespace matador::utils {
|
namespace matador::utils {
|
||||||
enum class generator_type {
|
enum class generator_type {
|
||||||
|
None = 0, /**< No generator type set. */
|
||||||
Manual, /**< User sets the primary key value manually. */
|
Manual, /**< User sets the primary key value manually. */
|
||||||
Auto, /**< Matador chooses the best generator type depending on the underlying dbms. */
|
Auto, /**< Matador chooses the best generator type depending on the underlying dbms. */
|
||||||
Identity, /**< DBMS automatically generates the primary key value. */
|
Identity, /**< DBMS automatically generates the primary key value. */
|
||||||
|
|
|
||||||
|
|
@ -56,66 +56,6 @@ session::session(session_context&& ctx, const query::schema &scm)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
utils::result<void, utils::error> session::drop_table(const std::string &table_name) const {
|
|
||||||
auto result = query::drop()
|
|
||||||
.table(table_name)
|
|
||||||
.execute(*this);
|
|
||||||
if (result.is_error()) {
|
|
||||||
return utils::failure(result.err());
|
|
||||||
}
|
|
||||||
|
|
||||||
return utils::ok<void>();
|
|
||||||
}
|
|
||||||
|
|
||||||
utils::result<sql::query_result<sql::record>, utils::error> session::fetch_all(const sql::query_context &q) const {
|
|
||||||
auto c = cache_.pool().acquire();
|
|
||||||
if (!c.valid()) {
|
|
||||||
return utils::failure(make_error(error_code::NoConnectionAvailable, "Failed to acquire connection."));
|
|
||||||
}
|
|
||||||
auto it = prototypes_.find(q.table_name);
|
|
||||||
if (it == prototypes_.end()) {
|
|
||||||
auto result = c->describe(q.table_name);
|
|
||||||
if (!result) {
|
|
||||||
return utils::failure(result.err());
|
|
||||||
}
|
|
||||||
it = prototypes_.emplace(q.table_name, *result).first;
|
|
||||||
}
|
|
||||||
// adjust columns from given query
|
|
||||||
for (auto &col: q.prototype) {
|
|
||||||
if (const auto rit = std::find_if(it->second.begin(), it->second.end(), [&col](const auto &value) {
|
|
||||||
return value.name() == col.name();
|
|
||||||
}); rit != it->second.end()) {
|
|
||||||
const_cast<object::attribute &>(col).change_type(rit->type());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
auto res = fetch(q);
|
|
||||||
if (!res) {
|
|
||||||
return utils::failure(res.err());
|
|
||||||
}
|
|
||||||
const auto prototype = res.value()->prototype();
|
|
||||||
return utils::ok(sql::query_result<sql::record>{std::move(*res), prototype});
|
|
||||||
}
|
|
||||||
|
|
||||||
utils::result<sql::execute_result, utils::error> session::execute(const std::string &sql) const {
|
|
||||||
return execute(sql::query_context{sql});
|
|
||||||
}
|
|
||||||
|
|
||||||
std::vector<object::attribute> session::describe_table(const std::string &table_name) const {
|
|
||||||
const auto c = cache_.pool().acquire();
|
|
||||||
if (!c.valid()) {
|
|
||||||
throw std::logic_error("no database connection available");
|
|
||||||
}
|
|
||||||
return c->describe(table_name).release();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool session::table_exists(const std::string &table_name) const {
|
|
||||||
const auto c = cache_.pool().acquire();
|
|
||||||
if (!c.valid()) {
|
|
||||||
throw std::logic_error("no database connection available");
|
|
||||||
}
|
|
||||||
return c->exists(dialect_.default_schema_name(), table_name);
|
|
||||||
}
|
|
||||||
|
|
||||||
const class sql::dialect &session::dialect() const {
|
const class sql::dialect &session::dialect() const {
|
||||||
return dialect_;
|
return dialect_;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -281,7 +281,7 @@ TEST_CASE_METHOD(QueryFixture, "Test describe table", "[query][describe][table]"
|
||||||
"val_char", "val_float", "val_double", "val_short",
|
"val_char", "val_float", "val_double", "val_short",
|
||||||
"val_int", "val_long_long", "val_unsigned_char",
|
"val_int", "val_long_long", "val_unsigned_char",
|
||||||
"val_unsigned_short", "val_unsigned_int", "val_unsigned_long_long",
|
"val_unsigned_short", "val_unsigned_int", "val_unsigned_long_long",
|
||||||
"val_bool", /*"val_cstr", */"val_string", "val_varchar",
|
"val_bool", "val_string", "val_varchar",
|
||||||
// "val_date", "val_time",
|
// "val_date", "val_time",
|
||||||
"val_binary"};
|
"val_binary"};
|
||||||
const std::vector<std::function<bool (const attribute&)>> type_check = {
|
const std::vector<std::function<bool (const attribute&)>> type_check = {
|
||||||
|
|
@ -295,11 +295,8 @@ TEST_CASE_METHOD(QueryFixture, "Test describe table", "[query][describe][table]"
|
||||||
[](const attribute &cf) { return cf.is_integer(); },
|
[](const attribute &cf) { return cf.is_integer(); },
|
||||||
[](const attribute &cf) { return cf.is_integer(); },
|
[](const attribute &cf) { return cf.is_integer(); },
|
||||||
[](const attribute &cf) { return cf.is_integer(); },
|
[](const attribute &cf) { return cf.is_integer(); },
|
||||||
// [](const attribute_definition &cf) { return cf.is_integer(); },
|
|
||||||
// [](const attribute_definition &cf) { return cf.is_integer(); },
|
|
||||||
[](const attribute &cf) { return cf.is_integer(); },
|
[](const attribute &cf) { return cf.is_integer(); },
|
||||||
[](const attribute &cf) { return cf.is_bool(); },
|
[](const attribute &cf) { return cf.is_bool(); },
|
||||||
// [](const attribute_definition &cf) { return cf.is_varchar(); },
|
|
||||||
[](const attribute &cf) { return cf.is_string(); },
|
[](const attribute &cf) { return cf.is_string(); },
|
||||||
[](const attribute &cf) { return cf.is_varchar(); },
|
[](const attribute &cf) { return cf.is_varchar(); },
|
||||||
// [](const attribute_definition &cf) { return cf.is_date(); },
|
// [](const attribute_definition &cf) { return cf.is_date(); },
|
||||||
|
|
@ -329,7 +326,7 @@ struct pk {
|
||||||
template<class Operator>
|
template<class Operator>
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
access::primary_key(op, "id", id);
|
access::primary_key(op, "id", id);
|
||||||
access::attribute(op, "name", name, 255);
|
access::attribute(op, "name", name, VarChar255);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t id{};
|
uint32_t id{};
|
||||||
|
|
|
||||||
|
|
@ -11,6 +11,47 @@ using namespace matador;
|
||||||
using namespace matador::object;
|
using namespace matador::object;
|
||||||
using namespace matador::test;
|
using namespace matador::test;
|
||||||
|
|
||||||
|
namespace matador::test {
|
||||||
|
struct book_identity;
|
||||||
|
struct author_identity {
|
||||||
|
unsigned int id{};
|
||||||
|
std::string name;
|
||||||
|
collection<object_ptr<book_identity> > books;
|
||||||
|
|
||||||
|
author_identity() = default;
|
||||||
|
explicit author_identity(std::string name)
|
||||||
|
: name(std::move(name)) {}
|
||||||
|
|
||||||
|
template<typename Operator>
|
||||||
|
void process(Operator &op) {
|
||||||
|
namespace field = matador::access;
|
||||||
|
field::primary_key(op, "id", id, utils::Identity);
|
||||||
|
field::attribute(op, "first_name", name, VarChar63);
|
||||||
|
field::has_many(op, "books", books, "author_id", utils::CascadeAllFetchLazy);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
struct book_identity {
|
||||||
|
unsigned int id{};
|
||||||
|
std::string title;
|
||||||
|
object_ptr<author_identity> book_author;
|
||||||
|
unsigned short published_in{};
|
||||||
|
|
||||||
|
book_identity() = default;
|
||||||
|
book_identity(std::string title, object_ptr<author_identity> author, const unsigned short published_in)
|
||||||
|
: title(std::move(title)), book_author(std::move(author)), published_in(published_in) {}
|
||||||
|
|
||||||
|
template<typename Operator>
|
||||||
|
void process(Operator &op) {
|
||||||
|
namespace field = matador::access;
|
||||||
|
field::primary_key(op, "id", id, utils::Identity);
|
||||||
|
field::attribute(op, "title", title, VarChar511);
|
||||||
|
field::belongs_to(op, "author_id", book_author, utils::CascadeAllFetchEager);
|
||||||
|
field::attribute(op, "published_in", published_in);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
TEST_CASE_METHOD(SessionFixture, "Test insert object with has many relation", "[session][insert][has_many]") {
|
TEST_CASE_METHOD(SessionFixture, "Test insert object with has many relation", "[session][insert][has_many]") {
|
||||||
const auto result = schema.attach<book>("books")
|
const auto result = schema.attach<book>("books")
|
||||||
.and_then( [this] { return schema.attach<author>("authors"); } )
|
.and_then( [this] { return schema.attach<author>("authors"); } )
|
||||||
|
|
@ -22,11 +63,32 @@ TEST_CASE_METHOD(SessionFixture, "Test insert object with has many relation", "[
|
||||||
|
|
||||||
auto s_king = make_object<author>(1, "Steven", "King", "21.9.1947", 1956, false);
|
auto s_king = make_object<author>(1, "Steven", "King", "21.9.1947", 1956, false);
|
||||||
|
|
||||||
s_king->books.push_back(make_object<book>(2, "Carrie", object_ptr<author>{}, 1974));
|
s_king->books.push_back(make_object<book>(2, "Carrie", nullobj, 1974));
|
||||||
s_king->books.push_back(make_object<book>(3, "The Shining", object_ptr<author>{}, 1977));
|
s_king->books.push_back(make_object<book>(3, "The Shining", nullobj, 1977));
|
||||||
s_king->books.push_back(make_object<book>(4, "It", object_ptr<author>{}, 1986));
|
s_king->books.push_back(make_object<book>(4, "It", nullobj, 1986));
|
||||||
s_king->books.push_back(make_object<book>(5, "Misery", object_ptr<author>{}, 1987));
|
s_king->books.push_back(make_object<book>(5, "Misery", nullobj, 1987));
|
||||||
s_king->books.push_back(make_object<book>(6, "The Dark Tower: The Gunslinger", object_ptr<author>{}, 1982));
|
s_king->books.push_back(make_object<book>(6, "The Dark Tower: The Gunslinger", nullobj, 1982));
|
||||||
|
|
||||||
|
auto res = ses.insert(s_king);
|
||||||
|
REQUIRE(res.is_ok());
|
||||||
|
}
|
||||||
|
|
||||||
|
TEST_CASE_METHOD(SessionFixture, "Test insert object with has many relation with identity", "[session][insert][has_many][identity]") {
|
||||||
|
const auto result = schema.attach<book_identity>("books")
|
||||||
|
.and_then( [this] { return schema.attach<author_identity>("authors"); } )
|
||||||
|
.and_then([this] { return schema.create(db); } );
|
||||||
|
REQUIRE(result.is_ok());
|
||||||
|
|
||||||
|
orm::session ses({bus, connection::dns, 4}, schema);
|
||||||
|
schema.initialize(ses);
|
||||||
|
|
||||||
|
auto s_king = make_object<author_identity>("Steven King");
|
||||||
|
|
||||||
|
s_king->books.push_back(make_object<book_identity>("Carrie", nullobj, 1974));
|
||||||
|
s_king->books.push_back(make_object<book_identity>("The Shining", nullobj, 1977));
|
||||||
|
s_king->books.push_back(make_object<book_identity>("It", nullobj, 1986));
|
||||||
|
s_king->books.push_back(make_object<book_identity>("Misery", nullobj, 1987));
|
||||||
|
s_king->books.push_back(make_object<book_identity>("The Dark Tower: The Gunslinger", nullobj, 1982));
|
||||||
|
|
||||||
auto res = ses.insert(s_king);
|
auto res = ses.insert(s_king);
|
||||||
REQUIRE(res.is_ok());
|
REQUIRE(res.is_ok());
|
||||||
|
|
|
||||||
|
|
@ -5,10 +5,12 @@
|
||||||
#include "connection.hpp"
|
#include "connection.hpp"
|
||||||
|
|
||||||
#include "models/recipe.hpp"
|
#include "models/recipe.hpp"
|
||||||
|
#include "models/model_metas.hpp"
|
||||||
|
|
||||||
using namespace matador;
|
using namespace matador;
|
||||||
using namespace matador::object;
|
using namespace matador::object;
|
||||||
using namespace matador::test;
|
using namespace matador::test;
|
||||||
|
using namespace matador::query::meta;
|
||||||
|
|
||||||
TEST_CASE_METHOD(SessionFixture, "Test insert object with has many to many relation", "[session][insert][has_many_to_many]") {
|
TEST_CASE_METHOD(SessionFixture, "Test insert object with has many to many relation", "[session][insert][has_many_to_many]") {
|
||||||
auto result = schema.attach<recipe>("recipes")
|
auto result = schema.attach<recipe>("recipes")
|
||||||
|
|
@ -16,6 +18,7 @@ TEST_CASE_METHOD(SessionFixture, "Test insert object with has many to many relat
|
||||||
.and_then([this] { return schema.create(db); } );
|
.and_then([this] { return schema.create(db); } );
|
||||||
|
|
||||||
orm::session ses({bus, connection::dns, 4}, schema);
|
orm::session ses({bus, connection::dns, 4}, schema);
|
||||||
|
schema.initialize(ses);
|
||||||
|
|
||||||
std::vector ingredients {
|
std::vector ingredients {
|
||||||
make_object<ingredient>(1, "Apple"),
|
make_object<ingredient>(1, "Apple"),
|
||||||
|
|
@ -37,4 +40,16 @@ TEST_CASE_METHOD(SessionFixture, "Test insert object with has many to many relat
|
||||||
auto res = ses.insert(r);
|
auto res = ses.insert(r);
|
||||||
REQUIRE(res.is_ok());
|
REQUIRE(res.is_ok());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
auto recipe_result = ses.find<recipe>(1);
|
||||||
|
// auto recipe_result = ses.find<recipe>(RECIPE.id == 1);
|
||||||
|
REQUIRE(recipe_result.is_ok());
|
||||||
|
|
||||||
|
// auto r = *recipe_result->begin();
|
||||||
|
auto r = *recipe_result;
|
||||||
|
std::cout << r->name << " (ingredients: " << r->ingredients.size() << ")" << std::endl;
|
||||||
|
// REQUIRE(r->name != "");
|
||||||
|
for (const auto &ingr: r->ingredients) {
|
||||||
|
std::cout << " " << ingr->name << std::endl;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -24,8 +24,8 @@ struct airplane {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "brand", brand, 255);
|
field::attribute(op, "brand", brand, UniqueVarChar255);
|
||||||
field::attribute(op, "model", model, 255);
|
field::attribute(op, "model", model, UniqueVarChar255);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
@ -36,8 +36,8 @@ struct airplane {
|
||||||
// namespace field = matador::access;
|
// namespace field = matador::access;
|
||||||
// using namespace matador::utils;
|
// using namespace matador::utils;
|
||||||
// field::primary_key(op, "id", object.id);
|
// field::primary_key(op, "id", object.id);
|
||||||
// field::attribute(op, "brand", object.brand, 255);
|
// field::attribute(op, "brand", object.brand, UniqueVarChar255);
|
||||||
// field::attribute(op, "model", object.model, 255);
|
// field::attribute(op, "model", object.model, UniqueVarChar255);
|
||||||
// }
|
// }
|
||||||
// template<class Operator>
|
// template<class Operator>
|
||||||
// void process(Operator &op, const matador::test::airplane &object) {
|
// void process(Operator &op, const matador::test::airplane &object) {
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@
|
||||||
#define QUERY_AUTHOR_HPP
|
#define QUERY_AUTHOR_HPP
|
||||||
|
|
||||||
#include "matador/utils/access.hpp"
|
#include "matador/utils/access.hpp"
|
||||||
|
#include "matador/utils/field_attributes.hpp"
|
||||||
|
|
||||||
#include "matador/object/object_ptr.hpp"
|
#include "matador/object/object_ptr.hpp"
|
||||||
#include "matador/object/collection.hpp"
|
#include "matador/object/collection.hpp"
|
||||||
|
|
@ -32,9 +33,9 @@ struct author {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "first_name", first_name, 63);
|
field::attribute(op, "first_name", first_name, VarChar63);
|
||||||
field::attribute(op, "last_name", last_name, 63);
|
field::attribute(op, "last_name", last_name, VarChar63);
|
||||||
field::attribute(op, "date_of_birth", date_of_birth, 31);
|
field::attribute(op, "date_of_birth", date_of_birth, VarChar63);
|
||||||
field::attribute(op, "year_of_birth", year_of_birth);
|
field::attribute(op, "year_of_birth", year_of_birth);
|
||||||
field::attribute(op, "distinguished", distinguished);
|
field::attribute(op, "distinguished", distinguished);
|
||||||
field::has_many(op, "books", books, "author_id", utils::CascadeAllFetchLazy);
|
field::has_many(op, "books", books, "author_id", utils::CascadeAllFetchLazy);
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@
|
||||||
#include "matador/object/object_ptr.hpp"
|
#include "matador/object/object_ptr.hpp"
|
||||||
|
|
||||||
#include "matador/utils/access.hpp"
|
#include "matador/utils/access.hpp"
|
||||||
|
#include "matador/utils/field_attributes.hpp"
|
||||||
#include "matador/utils/foreign_attributes.hpp"
|
#include "matador/utils/foreign_attributes.hpp"
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
@ -13,7 +14,7 @@ struct author;
|
||||||
|
|
||||||
struct book {
|
struct book {
|
||||||
book() = default;
|
book() = default;
|
||||||
book(const unsigned int id, std::string title, object::object_ptr<author> author, unsigned short published_in)
|
book(const unsigned int id, std::string title, object::object_ptr<author> author, const unsigned short published_in)
|
||||||
: id(id), title(std::move(title)), book_author(std::move(author)), published_in(published_in) {}
|
: id(id), title(std::move(title)), book_author(std::move(author)), published_in(published_in) {}
|
||||||
unsigned int id{};
|
unsigned int id{};
|
||||||
std::string title;
|
std::string title;
|
||||||
|
|
@ -24,7 +25,7 @@ struct book {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "title", title, 511);
|
field::attribute(op, "title", title, VarChar511);
|
||||||
field::belongs_to(op, "author_id", book_author, utils::CascadeAllFetchEager);
|
field::belongs_to(op, "author_id", book_author, utils::CascadeAllFetchEager);
|
||||||
field::attribute(op, "published_in", published_in);
|
field::attribute(op, "published_in", published_in);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,6 +2,7 @@
|
||||||
#define QUERY_CATEGORY_HPP
|
#define QUERY_CATEGORY_HPP
|
||||||
|
|
||||||
#include "matador/utils/access.hpp"
|
#include "matador/utils/access.hpp"
|
||||||
|
#include "matador/utils/field_attributes.hpp"
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
|
@ -15,7 +16,7 @@ struct category {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -14,7 +14,7 @@ struct coordinate {
|
||||||
|
|
||||||
namespace matador::access {
|
namespace matador::access {
|
||||||
template<class Operator>
|
template<class Operator>
|
||||||
void attribute(Operator &op, const char *id, test::coordinate &value, const utils::field_attributes &attr = utils::NullAttributes) {
|
void attribute(Operator &op, const char *id, test::coordinate &value, const utils::field_attributes &attr = NullAttributes) {
|
||||||
attribute(op, (std::string(id) + "_x").c_str(), value.x, attr);
|
attribute(op, (std::string(id) + "_x").c_str(), value.x, attr);
|
||||||
attribute(op, (std::string(id) + "_y").c_str(), value.y, attr);
|
attribute(op, (std::string(id) + "_y").c_str(), value.y, attr);
|
||||||
attribute(op, (std::string(id) + "_z").c_str(), value.z, attr);
|
attribute(op, (std::string(id) + "_z").c_str(), value.z, attr);
|
||||||
|
|
|
||||||
|
|
@ -24,7 +24,7 @@ struct department {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 63);
|
field::attribute(op, "name", name, UniqueVarChar63);
|
||||||
field::has_many(op, "employees", employees, "dep_id", utils::CascadeAllFetchEager);
|
field::has_many(op, "employees", employees, "dep_id", utils::CascadeAllFetchEager);
|
||||||
// field::belongs_to(op, "manager_id", manager, utils::fetch_type::EAGER);
|
// field::belongs_to(op, "manager_id", manager, utils::fetch_type::EAGER);
|
||||||
}
|
}
|
||||||
|
|
@ -43,8 +43,8 @@ struct employee {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "first_name", first_name, 63);
|
field::attribute(op, "first_name", first_name, VarChar63);
|
||||||
field::attribute(op, "last_name", last_name, 63);
|
field::attribute(op, "last_name", last_name, VarChar63);
|
||||||
field::belongs_to(op, "dep_id", dep, utils::CascadeAllFetchLazy);
|
field::belongs_to(op, "dep_id", dep, utils::CascadeAllFetchLazy);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -30,7 +30,7 @@ struct flight {
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::belongs_to(op, "airplane_id", plane, {utils::cascade_type::All, fetch_type::Eager});
|
field::belongs_to(op, "airplane_id", plane, {utils::cascade_type::All, fetch_type::Eager});
|
||||||
field::attribute(op, "pilot_name", pilot_name, 255);
|
field::attribute(op, "pilot_name", pilot_name, VarChar255);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -22,7 +22,7 @@ struct location {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar63);
|
||||||
field::attribute(op, "coordinate", coord);
|
field::attribute(op, "coordinate", coord);
|
||||||
field::attribute(op, "color", color);
|
field::attribute(op, "color", color);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -18,7 +18,7 @@ struct optional {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, VarChar255);
|
||||||
field::attribute(op, "age", age);
|
field::attribute(op, "age", age);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -28,17 +28,17 @@ struct order {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "order_id", order_id);
|
field::primary_key(op, "order_id", order_id);
|
||||||
field::attribute(op, "order_date", order_date, 255);
|
field::attribute(op, "order_date", order_date, VarChar255);
|
||||||
field::attribute(op, "required_date", required_date, 255);
|
field::attribute(op, "required_date", required_date, VarChar255);
|
||||||
field::attribute(op, "shipped_date", shipped_date, 255);
|
field::attribute(op, "shipped_date", shipped_date, VarChar255);
|
||||||
field::attribute(op, "ship_via", ship_via);
|
field::attribute(op, "ship_via", ship_via);
|
||||||
field::attribute(op, "freight", freight);
|
field::attribute(op, "freight", freight);
|
||||||
field::attribute(op, "ship_name", ship_name, 255);
|
field::attribute(op, "ship_name", ship_name, VarChar255);
|
||||||
field::attribute(op, "ship_address", ship_address, 255);
|
field::attribute(op, "ship_address", ship_address, VarChar255);
|
||||||
field::attribute(op, "ship_city", ship_city, 255);
|
field::attribute(op, "ship_city", ship_city, VarChar255);
|
||||||
field::attribute(op, "ship_region", ship_region, 255);
|
field::attribute(op, "ship_region", ship_region, VarChar255);
|
||||||
field::attribute(op, "ship_postal_code", ship_postal_code, 255);
|
field::attribute(op, "ship_postal_code", ship_postal_code, VarChar255);
|
||||||
field::attribute(op, "ship_country", ship_country, 255);
|
field::attribute(op, "ship_country", ship_country, VarChar255);
|
||||||
field::has_many(op, "order_details", order_details_, "order_id", utils::fetch_type::Eager);
|
field::has_many(op, "order_details", order_details_, "order_id", utils::fetch_type::Eager);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ struct person {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
field::attribute(op, "age", age);
|
field::attribute(op, "age", age);
|
||||||
field::attribute(op, "image", image);
|
field::attribute(op, "image", image);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,10 +26,10 @@ struct product {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "product_name", product_name, 255);
|
field::primary_key(op, "product_name", product_name, ManualVarChar511);
|
||||||
field::belongs_to(op, "supplier_id", seller, CascadeAllFetchLazy);
|
field::belongs_to(op, "supplier_id", seller, CascadeAllFetchLazy);
|
||||||
field::belongs_to(op, "category_id", type, CascadeAllFetchLazy);
|
field::belongs_to(op, "category_id", type, CascadeAllFetchLazy);
|
||||||
field::attribute(op, "quantity_per_unit", quantity_per_unit, 255);
|
field::attribute(op, "quantity_per_unit", quantity_per_unit, VarChar255);
|
||||||
field::attribute(op, "unit_price", unit_price);
|
field::attribute(op, "unit_price", unit_price);
|
||||||
field::attribute(op, "units_in_stock", units_in_stock);
|
field::attribute(op, "units_in_stock", units_in_stock);
|
||||||
field::attribute(op, "units_in_order", units_in_order);
|
field::attribute(op, "units_in_order", units_in_order);
|
||||||
|
|
|
||||||
|
|
@ -29,7 +29,7 @@ struct ingredient {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
field::has_many_to_many(op, "recipe_ingredients", recipes, "ingredient_id", "recipe_id", utils::CascadeAllFetchEager);
|
field::has_many_to_many(op, "recipe_ingredients", recipes, "ingredient_id", "recipe_id", utils::CascadeAllFetchEager);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
@ -53,15 +53,10 @@ struct recipe {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
field::has_many_to_many(op, "recipe_ingredients", ingredients, utils::CascadeAllFetchLazy);
|
field::has_many_to_many(op, "recipe_ingredients", ingredients, utils::CascadeAllFetchLazy);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// class recipe_ingredient : public object::many_to_many_relation<recipe, ingredient> {
|
|
||||||
// public:
|
|
||||||
// recipe_ingredient() : many_to_many_relation("recipe_id", "ingredient_id") {}
|
|
||||||
// };
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif //QUERY_RECIPE_HPP
|
#endif //QUERY_RECIPE_HPP
|
||||||
|
|
|
||||||
|
|
@ -25,7 +25,7 @@ struct shipment {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "tracking_number", tracking_number, 255);
|
field::attribute(op, "tracking_number", tracking_number, UniqueVarChar255);
|
||||||
field::has_many(op, "packages", packages, "shipment_id", utils::CascadeAllFetchEager);
|
field::has_many(op, "packages", packages, "shipment_id", utils::CascadeAllFetchEager);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -2,11 +2,11 @@
|
||||||
#define QUERY_STUDENT_HPP
|
#define QUERY_STUDENT_HPP
|
||||||
|
|
||||||
#include "matador/utils/access.hpp"
|
#include "matador/utils/access.hpp"
|
||||||
|
#include "matador/utils/field_attributes.hpp"
|
||||||
#include "matador/utils/foreign_attributes.hpp"
|
#include "matador/utils/foreign_attributes.hpp"
|
||||||
|
|
||||||
#include "matador/object/object_ptr.hpp"
|
#include "matador/object/object_ptr.hpp"
|
||||||
#include "matador/object/collection.hpp"
|
#include "matador/object/collection.hpp"
|
||||||
#include "matador/object/many_to_many_relation.hpp"
|
|
||||||
|
|
||||||
#include <utility>
|
#include <utility>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
@ -30,7 +30,7 @@ struct student {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
field::has_many_to_many(op, "student_courses", courses, "student_id", "course_id", utils::CascadeAllFetchLazy);
|
field::has_many_to_many(op, "student_courses", courses, "student_id", "course_id", utils::CascadeAllFetchLazy);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
@ -51,15 +51,9 @@ struct course {
|
||||||
void process(Operator &op) {
|
void process(Operator &op) {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "title", title, 255);
|
field::attribute(op, "title", title, UniqueVarChar255);
|
||||||
field::has_many_to_many(op, "student_courses", students, utils::CascadeAllFetchEager);
|
field::has_many_to_many(op, "student_courses", students, utils::CascadeAllFetchEager);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
class student_course : public object::many_to_many_relation<student, course> {
|
|
||||||
public:
|
|
||||||
student_course() : many_to_many_relation("student_id", "course_id") {
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
#endif //QUERY_STUDENT_HPP
|
#endif //QUERY_STUDENT_HPP
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ struct supplier {
|
||||||
namespace field = matador::access;
|
namespace field = matador::access;
|
||||||
using namespace matador::utils;
|
using namespace matador::utils;
|
||||||
field::primary_key(op, "id", id);
|
field::primary_key(op, "id", id);
|
||||||
field::attribute(op, "name", name, 255);
|
field::attribute(op, "name", name, UniqueVarChar255);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -6,8 +6,6 @@
|
||||||
|
|
||||||
namespace matador::test {
|
namespace matador::test {
|
||||||
struct types {
|
struct types {
|
||||||
// enum { CSTR_LEN=255 };
|
|
||||||
|
|
||||||
unsigned int id_ = 0;
|
unsigned int id_ = 0;
|
||||||
int8_t char_ = 'c';
|
int8_t char_ = 'c';
|
||||||
short short_ = -127;
|
short short_ = -127;
|
||||||
|
|
@ -20,7 +18,6 @@ struct types {
|
||||||
float float_ = 3.1415f;
|
float float_ = 3.1415f;
|
||||||
double double_ = 1.1414;
|
double double_ = 1.1414;
|
||||||
bool bool_ = true;
|
bool bool_ = true;
|
||||||
// char cstr_[CSTR_LEN]{};
|
|
||||||
std::string string_ = "Welt";
|
std::string string_ = "Welt";
|
||||||
std::string varchar_ = "Erde";
|
std::string varchar_ = "Erde";
|
||||||
// matador::date date_;
|
// matador::date date_;
|
||||||
|
|
@ -43,9 +40,8 @@ struct types {
|
||||||
field::attribute(op, "val_unsigned_int", unsigned_int_);
|
field::attribute(op, "val_unsigned_int", unsigned_int_);
|
||||||
field::attribute(op, "val_unsigned_long_long", unsigned_long64_);
|
field::attribute(op, "val_unsigned_long_long", unsigned_long64_);
|
||||||
field::attribute(op, "val_bool", bool_);
|
field::attribute(op, "val_bool", bool_);
|
||||||
// field::attribute(op, "val_cstr", cstr_, CSTR_LEN);
|
|
||||||
field::attribute(op, "val_string", string_);
|
field::attribute(op, "val_string", string_);
|
||||||
field::attribute(op, "val_varchar", varchar_, 63);
|
field::attribute(op, "val_varchar", varchar_, VarChar63);
|
||||||
// field::attribute(op, "val_date", date_);
|
// field::attribute(op, "val_date", date_);
|
||||||
// field::attribute(op, "val_time", time_);
|
// field::attribute(op, "val_time", time_);
|
||||||
field::attribute(op, "val_binary", binary_);
|
field::attribute(op, "val_binary", binary_);
|
||||||
|
|
|
||||||
|
|
@ -18,6 +18,7 @@
|
||||||
#include "../../models/book.hpp"
|
#include "../../models/book.hpp"
|
||||||
#include "../../models/airplane.hpp"
|
#include "../../models/airplane.hpp"
|
||||||
#include "../../models/flight.hpp"
|
#include "../../models/flight.hpp"
|
||||||
|
#include "../../models/recipe.hpp"
|
||||||
|
|
||||||
using namespace matador::object;
|
using namespace matador::object;
|
||||||
using namespace matador::sql;
|
using namespace matador::sql;
|
||||||
|
|
@ -113,3 +114,40 @@ TEST_CASE("Test insert builder has many", "[query][insert_query_builder][has_man
|
||||||
REQUIRE_FALSE(stmts.empty());
|
REQUIRE_FALSE(stmts.empty());
|
||||||
REQUIRE(stmts.size() == 6);
|
REQUIRE(stmts.size() == 6);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST_CASE("Test insert builder has many to many", "[query][insert_query_builder][many_to_many]") {
|
||||||
|
using namespace matador::test;
|
||||||
|
backend_provider::instance().register_backend("noop", std::make_unique<orm::test_backend_service>());
|
||||||
|
connection db("noop://noop.db");
|
||||||
|
|
||||||
|
schema scm;
|
||||||
|
const auto result = scm.attach<recipe>("recipes")
|
||||||
|
.and_then( [&scm] { return scm.attach<ingredient>("ingredients"); } );
|
||||||
|
REQUIRE(result.is_ok());
|
||||||
|
|
||||||
|
const std::vector ingredients {
|
||||||
|
make_object<ingredient>(1, "Apple"),
|
||||||
|
make_object<ingredient>(2, "Strawberry"),
|
||||||
|
make_object<ingredient>(3, "Pineapple"),
|
||||||
|
make_object<ingredient>(4, "Sugar"),
|
||||||
|
make_object<ingredient>(5, "Flour"),
|
||||||
|
make_object<ingredient>(6, "Butter"),
|
||||||
|
make_object<ingredient>(7, "Beans")
|
||||||
|
};
|
||||||
|
|
||||||
|
std::vector recipes {
|
||||||
|
make_object<recipe>(1, "Apple Pie", std::vector{ingredients[0], ingredients[3], ingredients[4]}),
|
||||||
|
make_object<recipe>(2, "Strawberry Cake", std::vector{ingredients[5], ingredients[6]}),
|
||||||
|
make_object<recipe>(3, "Pineapple Pie", std::vector{ingredients[0], ingredients[1], ingredients[2]})
|
||||||
|
};
|
||||||
|
|
||||||
|
const auto contexts_by_type = to_contexts_by_name(scm, db.dialect());
|
||||||
|
insert_query_builder<recipe> iqb(scm, contexts_by_type);
|
||||||
|
|
||||||
|
auto build_result = iqb.build(recipes[0]);
|
||||||
|
REQUIRE(build_result.is_ok());
|
||||||
|
|
||||||
|
const auto& stmts = *build_result;
|
||||||
|
REQUIRE_FALSE(stmts.empty());
|
||||||
|
REQUIRE(stmts.size() == 7);
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue