lib/partitioned/partitioned_base.rb in partitioned-1.0.1 vs lib/partitioned/partitioned_base.rb in partitioned-1.1.0
- old
+ new
@@ -59,11 +59,11 @@
# define the key value(s) for the constraint check.
#
# @return [String] the fully qualified name of the database table, ie: foos_partitions.p17
def partition_table_name
symbolized_attributes = attributes.symbolize_keys
- return self.class.partition_name(*self.class.partition_keys.map{|attribute_name| symbolized_attributes[attribute_name]})
+ return self.class.partition_table_name(*self.class.partition_keys.map{|attribute_name| symbolized_attributes[attribute_name]})
end
#
# Normalize the value to be used for partitioning. This allows, for instance, a class that partitions on
# a time field to group the times by month. An integer field might be grouped by every 10mil values, A
@@ -117,11 +117,11 @@
@arel_tables ||= {}
key_values = self.partition_key_values(values)
new_arel_table = @arel_tables[key_values]
arel_engine_hash = {:engine => self.arel_engine}
arel_engine_hash[:as] = as unless as.blank?
- new_arel_table = Arel::Table.new(self.partition_name(*key_values), arel_engine_hash)
+ new_arel_table = Arel::Table.new(self.partition_table_name(*key_values), arel_engine_hash)
return new_arel_table
end
#
# Used by our active record hacks to supply an Arel::Table given this active record's
@@ -133,55 +133,31 @@
symbolized_attributes = attributes.symbolize_keys
key_values = Hash[*self.class.partition_keys.map{|name| [name,symbolized_attributes[name]]}.flatten]
return self.class.dynamic_arel_table(key_values, as)
end
- # :from_partition_scope is generally not used directly,
- # use helper self.from_partition so that the derived class
- # can be passed into :from_partition_scope
#
- # @return [Hash] the from scoping
- scope :from_partition_scope, lambda { |target_class, *partition_field|
- {
- :from => "#{target_class.partition_name(*partition_field)} AS #{target_class.table_name}"
- }
- }
-
- #
- # Real scope (uses #from_partition_scope). This scope is used to target the
+ # This scoping is used to target the
# active record find() to a specific child table and alias it to the name of the
# parent table (so activerecord can generally work with it)
#
# Use as:
#
# Foo.from_partition(KEY).find(:first)
#
# where KEY is the key value(s) used as the check constraint on Foo's table.
#
- # Because the scope is specific to a class (a class method) but unlike
- # class methods is not inherited, one must use this form (#from_partition) instead
- # of #from_partition_scope to get the most derived classes specific active record scope.
- #
# @param [*Array<Object>] partition_field the field values to partition on
# @return [Hash] the scoping
def self.from_partition(*partition_field)
- from_partition_scope(self, *partition_field)
+ table_alias_name = partition_table_alias_name(*partition_field)
+ from("#{partition_table_name(*partition_field)} AS #{table_alias_name}").
+ tap{|relation| relation.table.table_alias = table_alias_name}
end
- # :from_partitioned_without_alias_scope is generally not used directly,
- # use helper self.from_partitioned_without_alias so that the derived class
- # can be passed into :from_partitioned_without_alias_scope
#
- # @return [Hash] the from scoping
- scope :from_partitioned_without_alias_scope, lambda { |target_class, *partition_field|
- {
- :from => target_class.partition_name(*partition_field)
- }
- }
-
- #
- # Real scope (uses #from_partitioned_without_alias_scope). This scope is used to target the
+ # This scope is used to target the
# active record find() to a specific child table. Is probably best used in advanced
# activerecord queries when a number of tables are involved in the query.
#
# Use as:
#
@@ -203,11 +179,13 @@
# of #from_partitioned_without_alias_scope to get the most derived classes specific active record scope.
#
# @param [*Array<Object>] partition_field the field values to partition on
# @return [Hash] the scoping
def self.from_partitioned_without_alias(*partition_field)
- from_partitioned_without_alias_scope(self, *partition_field)
+ table_alias_name = partition_table_name(*partition_field)
+ from(table_alias_name).
+ tap{|relation| relation.table.table_alias = table_alias_name}
end
#
# Return a object used to read configurator information.
#
@@ -250,12 +228,28 @@
#
# By default this will be the table name of the parent class with a suffix "_partitions".
#
# For a parent table name foos, that would be foos_partitions
#
+ # N.B.: if the parent table is not in the default schema ("public") the name of the
+ # partition schema is prefixed by the schema name of the parent table and an
+ # underscore. That is, if a parent table schema/table name is "other.foos"
+ # the schema for its partitions will be "other_foos_partitions"
+ #
partition.schema_name lambda {|model|
- return model.table_name + '_partitions'
+ schema_parts = []
+ table_parts = model.table_name.split('.')
+ # table_parts should be either ["table_name"] or ["schema_name", "table_name"]
+ if table_parts.length == 2
+ # XXX should we find the schema_path here and accept anything in the path as "public"
+ unless table_parts.first == "public"
+ schema_parts << table_parts.first
+ end
+ end
+ schema_parts << table_parts.last
+ schema_parts << 'partitions'
+ return schema_parts.join('_')
}
#
# The table name of the table who is the direct ancestor of a child table.
# The child table is defined by the partition key values passed in.
@@ -270,11 +264,13 @@
#
# The schema name of the table who is the direct ancestor of a child table.
# The child table is defined by the partition key values passed in.
#
partition.parent_table_schema_name lambda {|model, *partition_key_values|
- # this should be a connection_adapter thing
+ table_parts = model.table_name.split('.')
+ # table_parts should be either ["table_name"] or ["schema_name", "table_name"]
+ return table_parts.first if table_parts.length == 2
return "public"
}
#
# The prefix for a child table's name. This is typically a letter ('p') so that
@@ -307,10 +303,17 @@
configurator = model.configurator
return "#{configurator.schema_name}.#{configurator.part_name(*partition_key_values)}"
}
#
+ # A reasonable alias for this table
+ #
+ partition.table_alias_name lambda {|model, *partition_key_values|
+ return model.configurator.parent_table_name(*partition_key_values).gsub('.', '_')
+ }
+
+ #
# The name of the child table without a schema name or prefix. this is used to
# build child table names for multi-level partitions.
#
# For a table named foos_partitions.p42, this would be "42"
#
@@ -365,10 +368,17 @@
def self.add_parent_table_rules(*partition_key_values)
partition_manager.add_parent_table_rules(*partition_key_values)
end
##
+ # :method: archive_old_partitions
+ # delegated to Partitioned::PartitionedBase::PartitionManager#archive_old_partitions
+ def self.archive_old_partitions
+ partition_manager.archive_old_partitions
+ end
+
+ ##
# :method: drop_old_partitions
# delegated to Partitioned::PartitionedBase::PartitionManager#drop_old_partitions
def self.drop_old_partitions
partition_manager.drop_old_partitions
end
@@ -379,10 +389,17 @@
def self.create_new_partitions
partition_manager.create_new_partitions
end
##
+ # :method: archive_old_partition
+ # delegated to Partitioned::PartitionedBase::PartitionManager#archive_old_partition
+ def self.archive_old_partition(*partition_key_values)
+ partition_manager.archive_old_partition(*partition_key_values)
+ end
+
+ ##
# :method: drop_old_partition
# delegated to Partitioned::PartitionedBase::PartitionManager#drop_old_partition
def self.drop_old_partition(*partition_key_values)
partition_manager.drop_old_partition(*partition_key_values)
end
@@ -418,8 +435,15 @@
##
# :method: partition_name
# delegated to Partitioned::PartitionedBase::PartitionManager#partition_table_name
def self.partition_name(*partition_key_values)
return partition_manager.partition_table_name(*partition_key_values)
+ end
+
+ ##
+ # :method: partition_table_alias_name
+ # delegated to Partitioned::PartitionedBase::PartitionManager#partition_table_alias_name
+ def self.partition_table_alias_name(*partition_key_values)
+ return partition_manager.partition_table_alias_name(*partition_key_values)
end
end
end