Class: VersionedStore::Stores::Schema

Inherits:
Object
  • Object
show all
Defined in:
lib/versioned_store/stores/schema.rb

Defined Under Namespace

Classes: Migration, Record, RecordContext

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initializeSchema

Returns a new instance of Schema.



43
44
45
46
47
48
49
50
# File 'lib/versioned_store/stores/schema.rb', line 43

def initialize
  @migrations = []
  @records = {}
  @migration_counter = 1
  @migrated_tables = Set.new
  @schema_blocks = {}
  @post_init_hooks = []
end

Instance Attribute Details

#migrated_tablesObject (readonly)

Returns the value of attribute migrated_tables.



42
43
44
# File 'lib/versioned_store/stores/schema.rb', line 42

def migrated_tables
  @migrated_tables
end

#migrationsObject (readonly)

Returns the value of attribute migrations.



42
43
44
# File 'lib/versioned_store/stores/schema.rb', line 42

def migrations
  @migrations
end

#post_init_hooksObject (readonly)

Returns the value of attribute post_init_hooks.



42
43
44
# File 'lib/versioned_store/stores/schema.rb', line 42

def post_init_hooks
  @post_init_hooks
end

#recordsObject (readonly)

Returns the value of attribute records.



42
43
44
# File 'lib/versioned_store/stores/schema.rb', line 42

def records
  @records
end

#schema_blocksObject (readonly)

Returns the value of attribute schema_blocks.



42
43
44
# File 'lib/versioned_store/stores/schema.rb', line 42

def schema_blocks
  @schema_blocks
end

Class Method Details

.call(&block) ⇒ Object



119
120
121
122
123
124
# File 'lib/versioned_store/stores/schema.rb', line 119

def self.call(&block)
  schema = new
  schema.instance_exec(&block) if block
  schema.add_table_migrations!
  schema
end

Instance Method Details

#add_table_migrations!Object

Add a migration for each table with collected schema blocks (called after all record blocks)



104
105
106
107
108
109
110
111
112
113
114
115
116
117
# File 'lib/versioned_store/stores/schema.rb', line 104

def add_table_migrations!
  schema_blocks.each do |table_name, blocks|
    next if migrated_tables.include?(table_name) || table_name.nil?
    blocks_to_eval = blocks.dup
    migration_block = Proc.new do
      create_table(table_name) do |t|
        blocks_to_eval.each { |blk| blk.call(t) }
      end
    end
    version = "table_#{table_name}"
    prepend_migration(version, &migration_block)
    migrated_tables.add(table_name)
  end
end

#dir(path = nil) ⇒ Object



64
65
66
67
# File 'lib/versioned_store/stores/schema.rb', line 64

def dir(path = nil)
  @dir = path if path
  @dir
end

#dupObject



52
53
54
55
56
57
58
59
60
61
62
# File 'lib/versioned_store/stores/schema.rb', line 52

def dup
  new_schema = Schema.new
  new_schema.instance_variable_set(:@migrations, @migrations.dup)
  new_schema.instance_variable_set(:@records, @records.dup)
  new_schema.instance_variable_set(:@migration_counter, @migration_counter)
  new_schema.instance_variable_set(:@migrated_tables, @migrated_tables.dup)
  new_schema.instance_variable_set(:@schema_blocks, @schema_blocks.dup)
  new_schema.instance_variable_set(:@post_init_hooks, @post_init_hooks.dup)
  new_schema.instance_variable_set(:@dir, @dir)
  new_schema
end

#migrate(version = @migration_counter += 1, &block) ⇒ Object



69
70
71
# File 'lib/versioned_store/stores/schema.rb', line 69

def migrate(version = @migration_counter += 1, &block)
  migrations << Migration.new(version: version, block: block)
end

#prepend_migration(version, &block) ⇒ Object



73
74
75
# File 'lib/versioned_store/stores/schema.rb', line 73

def prepend_migration(version, &block)
  migrations.unshift(Migration.new(version: version, block: block))
end

#record(name, table: nil, &block) ⇒ Object



77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/versioned_store/stores/schema.rb', line 77

def record(name, table: nil, &block)
  # If block is given, execute it in RecordContext to extract schema calls
  extracted_table = table
  if block
    context = RecordContext.new(self, name)
    context.instance_exec(&block)
    extracted_table ||= context.table_name
  end

  prev = records[name]
  blocks = prev ? prev.blocks.dup : []
  blocks << block if block
  # Prefer the first non-nil table name, otherwise default to name + "s"
  table_name = prev&.table || extracted_table
  if table_name.nil?
    name_str = name.to_s
    table_name = (name_str.end_with?('s') ? name_str : "#{name_str}s").to_sym
  end

  records[name] = Record.new(
    name: name,
    table: table_name,
    blocks: blocks
  )
end