|
- #include <cpphibernate/driver/mariadb/classes/fields/field.h>
- #include <cpphibernate/driver/mariadb/classes/tables/table.h>
- #include <cpphibernate/driver/mariadb/context/create_update_context.inl>
-
- using namespace ::cpphibernate;
- using namespace ::cpphibernate::mariadb;
-
- static std::string build_foreign_one_delete_query(const field_t& field, bool key_known);
-
- void field_t::foreign_one_delete(
- const create_update_context& context,
- const std::string& primary_key,
- const value_t& foreign_key) const
- {
- /* get statement */
- auto& statement = foreign_key.has_value()
- ? get_statement_foreign_one_delete_key_known()
- : get_statement_foreign_one_delete_key_unknown();
-
- /* update statement values */
- statement.set(0, primary_key);
- if (foreign_key.has_value())
- statement.set(1, *foreign_key);
-
- /* execute query */
- auto& connection = context.connection;
- cpphibernate_log_debug("execute DELETE old foreign one query: " << std::endl << statement.query(connection) << std::endl);
- connection.execute(statement);
-
- /* cleanup tables */
- assert(referenced_table);
- table_t::table_set processed;
- referenced_table->cleanup(context, processed, true, true);
- }
-
-
- ::cppmariadb::statement& field_t::get_statement_foreign_one_delete_key_known() const
- {
- if (!_statement_foreign_one_delete_key_known)
- {
- auto query = build_foreign_one_delete_query(*this, true);
- _statement_foreign_one_delete_key_known.reset(new ::cppmariadb::statement(std::move(query)));
- }
- return *_statement_foreign_one_delete_key_known;
- }
-
- cppmariadb::statement& field_t::get_statement_foreign_one_delete_key_unknown() const
- {
- if (!_statement_foreign_one_delete_key_unknown)
- {
- auto query = build_foreign_one_delete_query(*this, false);
- _statement_foreign_one_delete_key_unknown.reset(new ::cppmariadb::statement(std::move(query)));
- }
- return *_statement_foreign_one_delete_key_unknown;
- }
-
- std::string build_foreign_one_delete_query(const field_t& field, bool key_known)
- {
- assert(field.table.primary_key_field);
- assert(field.referenced_table);
- assert(field.referenced_table->primary_key_field);
-
- if (key_known)
- {
- auto& ref_table = *field.referenced_table;
- auto& key_info = *field.table.primary_key_field;
- auto& ref_key_info = *ref_table.primary_key_field;
-
- std::ostringstream os;
- os << "WHERE `"
- << ref_key_info.name
- << "` IN (SELECT `"
- << ref_key_info.table.name
- << "_id_"
- << field.name
- << "` FROM `"
- << key_info.table.name
- << "` WHERE `"
- << key_info.name
- << "`="
- << key_info.convert_to_open
- << "?\?"
- << key_info.convert_to_close
- << " AND `"
- << ref_key_info.table.name
- << "_id_"
- << field.name
- << "`!="
- << ref_key_info.convert_to_open
- << "?\?"
- << ref_key_info.convert_to_close
- << ")";
-
- auto where = os.str();
- auto query = ref_table.build_delete_query(&where);
- return query;
- }
- else
- {
- auto& ref_table = *field.referenced_table;
- auto& key_info = *field.table.primary_key_field;
- auto& ref_key_info = *ref_table.primary_key_field;
-
- std::ostringstream os;
- os << "WHERE `"
- << ref_key_info.name
- << "` IN (SELECT `"
- << ref_key_info.table.name
- << "_id_"
- << field.name
- << "` FROM `"
- << key_info.table.name
- << "` WHERE `"
- << key_info.name
- << "`="
- << key_info.convert_to_open
- << "?\?"
- << key_info.convert_to_close
- << ")";
-
- auto where = os.str();
- auto query = ref_table.build_delete_query(&where);
- return query;
- }
- }
|