diff options
-rw-r--r-- | odb/relational/model.hxx | 7 | ||||
-rw-r--r-- | odb/relational/mssql/schema.cxx | 14 | ||||
-rw-r--r-- | odb/relational/mysql/schema.cxx | 14 | ||||
-rw-r--r-- | odb/relational/oracle/schema.cxx | 20 | ||||
-rw-r--r-- | odb/relational/pgsql/schema.cxx | 8 | ||||
-rw-r--r-- | odb/relational/schema.cxx | 17 | ||||
-rw-r--r-- | odb/relational/schema.hxx | 205 | ||||
-rw-r--r-- | odb/relational/sqlite/schema.cxx | 20 | ||||
-rw-r--r-- | odb/semantics/relational/elements.hxx | 8 | ||||
-rw-r--r-- | odb/semantics/relational/foreign-key.hxx | 4 | ||||
-rw-r--r-- | odb/semantics/relational/index.hxx | 19 | ||||
-rw-r--r-- | odb/semantics/relational/key.hxx | 4 | ||||
-rw-r--r-- | odb/semantics/relational/primary-key.hxx | 7 |
13 files changed, 164 insertions, 183 deletions
diff --git a/odb/relational/model.hxx b/odb/relational/model.hxx index d41b701..b95425e 100644 --- a/odb/relational/model.hxx +++ b/odb/relational/model.hxx @@ -471,9 +471,7 @@ namespace relational id_name += '_'; model_.new_edge<sema_rel::unames> (t, fk, id_name + "fk"); - - model_.new_edge<sema_rel::qnames> ( - model_, in, name + "_" + id_name + "i"); + model_.new_edge<sema_rel::unames> (t, in, id_name + "i"); } // index (simple value) @@ -492,8 +490,7 @@ namespace relational model_.new_edge<sema_rel::contains> ( in, dynamic_cast<column&> (t.find (col_name)->nameable ())); - model_.new_edge<sema_rel::qnames> ( - model_, in, name + "_" + col_name + "_i"); + model_.new_edge<sema_rel::unames> (t, in, col_name + "_i"); } // key diff --git a/odb/relational/mssql/schema.cxx b/odb/relational/mssql/schema.cxx index ebbda2c..47cb250 100644 --- a/odb/relational/mssql/schema.cxx +++ b/odb/relational/mssql/schema.cxx @@ -288,20 +288,6 @@ namespace relational trav_rel::unames n (fk); names (t, n); } - - struct create_index: relational::create_index, context - { - create_index (base const& x): base (x) {} - - virtual string - name (sema_rel::index& in) - { - // In SQL Server indexes cannot have a schema. - // - return quote_id (in.name ().uname ()); - } - }; - entry<create_index> create_index_; } } } diff --git a/odb/relational/mysql/schema.cxx b/odb/relational/mysql/schema.cxx index 6db30ad..4050d70 100644 --- a/odb/relational/mysql/schema.cxx +++ b/odb/relational/mysql/schema.cxx @@ -125,20 +125,6 @@ namespace relational } }; entry<create_table> create_table_; - - struct create_index: relational::create_index, context - { - create_index (base const& x): base (x) {} - - virtual string - name (sema_rel::index& in) - { - // In MySQL an index cannot be qualified with the database name. - // - return quote_id (in.name ().uname ()); - } - }; - entry<create_index> create_index_; } } } diff --git a/odb/relational/oracle/schema.cxx b/odb/relational/oracle/schema.cxx index ce2c470..29c1130 100644 --- a/odb/relational/oracle/schema.cxx +++ b/odb/relational/oracle/schema.cxx @@ -302,6 +302,26 @@ namespace relational trav_rel::unames n (fk); names (t, n); } + + struct create_index: relational::create_index, context + { + create_index (base const& x): base (x) {} + + virtual string + name (sema_rel::index& in) + { + // In Oracle, index names are database-global. Make them unique + // by prefixing the index name with table name (preserving the + // schema). + // + sema_rel::qname n ( + static_cast<sema_rel::table&> (in.scope ()).name ()); + + n.uname () += "_" + in.name (); + return quote_id (n); + } + }; + entry<create_index> create_index_; } } } diff --git a/odb/relational/pgsql/schema.cxx b/odb/relational/pgsql/schema.cxx index c774561..2113894 100644 --- a/odb/relational/pgsql/schema.cxx +++ b/odb/relational/pgsql/schema.cxx @@ -173,9 +173,13 @@ namespace relational virtual string name (sema_rel::index& in) { - // In PostgreSQL indexes cannot have a schema. + // In PostgreSQL, index names are database-global. Make them unique + // by prefixing the index name with table name. Note, however, that + // they cannot be qualified with the schema name. // - return quote_id (in.name ().uname ()); + return quote_id ( + static_cast<sema_rel::table&> (in.scope ()).name ().uname () + + "_" + in.name ()); } }; entry<create_index> create_index_; diff --git a/odb/relational/schema.cxx b/odb/relational/schema.cxx index ea9083d..3dd8507 100644 --- a/odb/relational/schema.cxx +++ b/odb/relational/schema.cxx @@ -45,15 +45,11 @@ namespace relational // Drop. // { - instance<drop_model> model (*em, emos, f); - trav_rel::qnames names; instance<drop_table> table (*em, emos, f); - instance<drop_index> index (*em, emos, f); + trav_rel::qnames names; - model >> names; - names >> table; - names >> index; + model >> names >> table; // Pass 1 and 2. // @@ -61,7 +57,6 @@ namespace relational { model->pass (pass); table->pass (pass); - index->pass (pass); model->traverse (*ctx.model); } @@ -73,13 +68,10 @@ namespace relational // { instance<create_model> model (*em, emos, f); - trav_rel::qnames names; instance<create_table> table (*em, emos, f); - instance<create_index> index (*em, emos, f); + trav_rel::qnames names; - model >> names; - names >> table; - names >> index; + model >> names >> table; // Pass 1 and 2. // @@ -87,7 +79,6 @@ namespace relational { model->pass (pass); table->pass (pass); - index->pass (pass); model->traverse (*ctx.model); } diff --git a/odb/relational/schema.hxx b/odb/relational/schema.hxx index 4f31dca..6551119 100644 --- a/odb/relational/schema.hxx +++ b/odb/relational/schema.hxx @@ -58,65 +58,65 @@ namespace relational // Drop. // - struct drop_table: trav_rel::table, common + struct drop_index: trav_rel::index, common { - typedef drop_table base; + typedef drop_index base; - drop_table (emitter_type& e, ostream& os, schema_format f) + drop_index (emitter_type& e, ostream& os, schema_format f) : common (e, os), format_ (f) { } - virtual void - drop (sema_rel::qname const& table) + virtual string + name (sema_rel::index& in) { - os << "DROP TABLE IF EXISTS " << quote_id (table) << endl; + return quote_id (in.name ()); + } + + virtual string + table_name (sema_rel::index& in) + { + return quote_id (static_cast<sema_rel::table&> (in.scope ()).name ()); } virtual void - traverse (sema_rel::table& t) + drop (string const& /*name*/, string const& /*table*/) { - // By default we do everything in a single pass. But some - // databases may require the second pass. + // Most database systems drop indexes together with the table. // - if (pass_ > 1) - return; - - pre_statement (); - drop (t.name ()); - post_statement (); + // os << "DROP INDEX IF EXISTS " << quote_id (name) << " ON " << + // table << endl; } - void - pass (unsigned short p) + virtual void + traverse (sema_rel::index& in) { - pass_ = p; + pre_statement (); + drop (name (in), table_name (in)); + post_statement (); } protected: schema_format format_; - unsigned short pass_; }; - struct drop_index: trav_rel::index, common + struct drop_table: trav_rel::table, common { - typedef drop_index base; + typedef drop_table base; - drop_index (emitter_type& e, ostream& os, schema_format f) + drop_table (emitter_type& e, ostream& os, schema_format f) : common (e, os), format_ (f) { } virtual void - drop (sema_rel::qname const& /*index*/) + drop (sema_rel::qname const& table) { - // Most database systems drop indexes together with the table. - // - //os << "DROP INDEX IF EXISTS " << quote_id (index); + os << "DROP TABLE IF EXISTS " << quote_id (table) << endl; } virtual void - traverse (sema_rel::index& in) + traverse (sema_rel::table& t) { // By default we do everything in a single pass. But some // databases may require the second pass. @@ -124,8 +124,16 @@ namespace relational if (pass_ > 1) return; + // Drop indexes. + // + { + instance<drop_index> in (emitter (), stream (), format_); + trav_rel::unames n (*in); + names (t, n); + } + pre_statement (); - drop (in.name ()); + drop (t.name ()); post_statement (); } @@ -456,65 +464,6 @@ namespace relational create_table& create_table_; }; - struct create_table: trav_rel::table, common - { - typedef create_table base; - - create_table (emitter_type& e, ostream& os, schema_format f) - : common (e, os), format_ (f) - { - } - - virtual void - create_pre (sema_rel::qname const& table) - { - os << "CREATE TABLE " << quote_id (table) << " (" << endl; - } - - virtual void - create_post () - { - os << ")" << endl; - } - - virtual void - traverse (sema_rel::table& t) - { - // By default we do everything in a single pass. But some - // databases may require the second pass. - // - if (pass_ > 1) - return; - - pre_statement (); - create_pre (t.name ()); - - instance<create_column> c (format_, *this); - instance<create_primary_key> pk (format_, *this); - instance<create_foreign_key> fk (format_, *this); - trav_rel::unames n; - - n >> c; - n >> pk; - n >> fk; - - names (t, n); - - create_post (); - post_statement (); - } - - void - pass (unsigned short p) - { - pass_ = p; - } - - protected: - schema_format format_; - unsigned short pass_; - }; - struct create_index: trav_rel::index, common { typedef create_index base; @@ -527,12 +476,6 @@ namespace relational virtual void traverse (sema_rel::index& in) { - // By default we do everything in a single pass. But some - // databases may require the second pass. - // - if (pass_ > 1) - return; - pre_statement (); create (in); post_statement (); @@ -547,7 +490,7 @@ namespace relational virtual string table_name (sema_rel::index& in) { - return quote_id (in.table ().name ()); + return quote_id (static_cast<sema_rel::table&> (in.scope ()).name ()); } virtual void @@ -577,6 +520,66 @@ namespace relational os << ")" << endl; } + protected: + schema_format format_; + }; + + struct create_table: trav_rel::table, common + { + typedef create_table base; + + create_table (emitter_type& e, ostream& os, schema_format f) + : common (e, os), format_ (f) + { + } + + virtual void + create_pre (sema_rel::qname const& table) + { + os << "CREATE TABLE " << quote_id (table) << " (" << endl; + } + + virtual void + create_post () + { + os << ")" << endl; + } + + virtual void + traverse (sema_rel::table& t) + { + // By default we do everything in a single pass. But some + // databases may require the second pass. + // + if (pass_ > 1) + return; + + pre_statement (); + create_pre (t.name ()); + + instance<create_column> c (format_, *this); + instance<create_primary_key> pk (format_, *this); + instance<create_foreign_key> fk (format_, *this); + trav_rel::unames n; + + n >> c; + n >> pk; + n >> fk; + + names (t, n); + + create_post (); + post_statement (); + + // Create indexes. + // + { + instance<create_index> in (emitter (), stream (), format_); + trav_rel::unames n (*in); + names (t, n); + } + } + void pass (unsigned short p) { @@ -799,10 +802,8 @@ namespace relational : stream_ (*emitter_), drop_model_ (*emitter_, stream_, format_embedded), drop_table_ (*emitter_, stream_, format_embedded), - drop_index_ (*emitter_, stream_, format_embedded), create_model_ (*emitter_, stream_, format_embedded), - create_table_ (*emitter_, stream_, format_embedded), - create_index_ (*emitter_, stream_, format_embedded) + create_table_ (*emitter_, stream_, format_embedded) { init (); } @@ -813,10 +814,8 @@ namespace relational stream_ (*emitter_), drop_model_ (*emitter_, stream_, format_embedded), drop_table_ (*emitter_, stream_, format_embedded), - drop_index_ (*emitter_, stream_, format_embedded), create_model_ (*emitter_, stream_, format_embedded), - create_table_ (*emitter_, stream_, format_embedded), - create_index_ (*emitter_, stream_, format_embedded) + create_table_ (*emitter_, stream_, format_embedded) { init (); } @@ -826,11 +825,9 @@ namespace relational { drop_model_ >> drop_names_; drop_names_ >> drop_table_; - drop_names_ >> drop_index_; create_model_ >> create_names_; create_names_ >> create_table_; - create_names_ >> create_index_; } void @@ -872,7 +869,6 @@ namespace relational emitter_->pass (pass); drop_model_->pass (pass); drop_table_->pass (pass); - drop_index_->pass (pass); drop_model_->traverse (begin, end); @@ -900,7 +896,6 @@ namespace relational emitter_->pass (pass); create_model_->pass (pass); create_table_->pass (pass); - create_index_->pass (pass); create_model_->traverse (begin, end); @@ -932,12 +927,10 @@ namespace relational trav_rel::qnames drop_names_; instance<drop_model> drop_model_; instance<drop_table> drop_table_; - instance<drop_index> drop_index_; trav_rel::qnames create_names_; instance<create_model> create_model_; instance<create_table> create_table_; - instance<create_index> create_index_; }; } } diff --git a/odb/relational/sqlite/schema.cxx b/odb/relational/sqlite/schema.cxx index b20c7da..8efef66 100644 --- a/odb/relational/sqlite/schema.cxx +++ b/odb/relational/sqlite/schema.cxx @@ -54,13 +54,29 @@ namespace relational create_index (base const& x): base (x) {} virtual string + name (sema_rel::index& in) + { + // In SQLite, index names are database-global. Make them unique + // by prefixing the index name with table name (preserving the + // database). + // + sema_rel::qname n ( + static_cast<sema_rel::table&> (in.scope ()).name ()); + + n.uname () += "_" + in.name (); + return quote_id (n); + } + + virtual string table_name (sema_rel::index& in) { // In SQLite, the index table cannot be qualified with the - // database name (it has to be in the same database anyway). + // database name (it has to be in the same database). // - return quote_id (in.table ().name ().uname ()); + return quote_id ( + static_cast<sema_rel::table&> (in.scope ()).name ().uname ()); } + }; entry<create_index> create_index_; } diff --git a/odb/semantics/relational/elements.hxx b/odb/semantics/relational/elements.hxx index 6b4964e..8eb695a 100644 --- a/odb/semantics/relational/elements.hxx +++ b/odb/semantics/relational/elements.hxx @@ -174,10 +174,10 @@ namespace semantics public: // Id identifies the C++ node (e.g., a class or a data member) that // this model node corresponds to. The ids are not necessarily unique - // (e.g., there can be a table and an index with the same id that - // correspond to a container member). However, in any given scope, - // the {id,typeid} must be unique. This becomes important when we - // try to find correspondance between nodes during model diff'ing. + // (e.g., there can be a foreign key and an index with the same id that + // correspond to a container member). However, in any given scope, the + // {id,typeid} must be unique. This becomes important when we try to + // find correspondance between nodes during model diff'ing. // nameable (string const& id): id_ (id), named_ (0) {} diff --git a/odb/semantics/relational/foreign-key.hxx b/odb/semantics/relational/foreign-key.hxx index 83b7071..871c036 100644 --- a/odb/semantics/relational/foreign-key.hxx +++ b/odb/semantics/relational/foreign-key.hxx @@ -12,7 +12,7 @@ namespace semantics { namespace relational { - class foreign_key: public unameable, public key + class foreign_key: public key { public: enum action @@ -25,7 +25,7 @@ namespace semantics qname const& referenced_table, bool deferred, action on_delete = no_action) - : unameable (id), + : key (id), referenced_table_ (referenced_table), deferred_ (deferred), on_delete_ (on_delete) diff --git a/odb/semantics/relational/index.hxx b/odb/semantics/relational/index.hxx index dcb8e6e..af90b12 100644 --- a/odb/semantics/relational/index.hxx +++ b/odb/semantics/relational/index.hxx @@ -6,31 +6,18 @@ #define ODB_SEMANTICS_RELATIONAL_INDEX_HXX #include <odb/semantics/relational/elements.hxx> -#include <odb/semantics/relational/column.hxx> #include <odb/semantics/relational/key.hxx> -#include <odb/semantics/relational/table.hxx> namespace semantics { namespace relational { - // Note that unlike other keys, indexes are defined in the model - // scope, not table scope. + // Note that in our model indexes are defined in the table scope. // - class index: public qnameable, public key + class index: public key { public: - relational::table& - table () const - { - return contains_begin ()->column ().table (); - } - - public: - index (string const& id) - : qnameable (id) - { - } + index (string const& id): key (id) {} virtual string kind () const diff --git a/odb/semantics/relational/key.hxx b/odb/semantics/relational/key.hxx index f5184be..40e7499 100644 --- a/odb/semantics/relational/key.hxx +++ b/odb/semantics/relational/key.hxx @@ -50,7 +50,7 @@ namespace semantics column_type* column_; }; - class key: public virtual node + class key: public unameable { typedef std::vector<contains*> contains_list; @@ -78,6 +78,8 @@ namespace semantics } public: + key (std::string const& id): unameable (id) {} + void add_edge_left (contains& e) { diff --git a/odb/semantics/relational/primary-key.hxx b/odb/semantics/relational/primary-key.hxx index e35b00f..0aec038 100644 --- a/odb/semantics/relational/primary-key.hxx +++ b/odb/semantics/relational/primary-key.hxx @@ -12,7 +12,7 @@ namespace semantics { namespace relational { - class primary_key: public unameable, public key + class primary_key: public key { public: bool @@ -23,9 +23,8 @@ namespace semantics public: primary_key (bool auto_) - // Primary key has the implicit empty id. - // - : unameable (""), auto__ (auto_) + : key (""), // Primary key has the implicit empty id. + auto__ (auto_) { } |