Skip to content

Commit

Permalink
Raise nicely when data dictionary is needed but missing
Browse files Browse the repository at this point in the history
  • Loading branch information
jeremycole committed Nov 6, 2024
1 parent ebb904f commit a8c585b
Show file tree
Hide file tree
Showing 4 changed files with 39 additions and 14 deletions.
9 changes: 9 additions & 0 deletions lib/innodb/data_dictionary.rb
Original file line number Diff line number Diff line change
Expand Up @@ -235,7 +235,14 @@ def data_dictionary_indexes
system_space.data_dictionary_page.data_dictionary_header[:indexes]
end

# Check if the data dictionary indexes are all available.
def found?
data_dictionary_indexes.values.map(&:values).flatten.none?(&:zero?)
end

def data_dictionary_index_ids
raise "Data Dictionary not found; is the MySQL version supported?" unless found?

return @data_dictionary_index_ids if @data_dictionary_index_ids

# TODO: This could probably be done a lot more Ruby-like.
Expand Down Expand Up @@ -275,6 +282,8 @@ def data_dictionary_index_describer(table_name, index_name)
# internal data dictionary index with an appropriate
# record describer so that records can be recursed.
def data_dictionary_index(table_name, index_name)
raise "Data Dictionary not found; is the MySQL version supported?" unless found?

table_entry = data_dictionary_indexes[table_name]
raise "Unknown data dictionary table #{table_name}" unless table_entry

Expand Down
26 changes: 16 additions & 10 deletions lib/innodb/page/index.rb
Original file line number Diff line number Diff line change
Expand Up @@ -546,7 +546,7 @@ def supremum
end

def make_record_describer
if space&.innodb_system && index_id
if space&.innodb_system&.data_dictionary&.found? && index_id && !ibuf_index?
@record_describer = space.innodb_system.data_dictionary.record_describer_by_index_id(index_id)
elsif space
@record_describer = space.record_describer
Expand Down Expand Up @@ -1096,17 +1096,23 @@ def dump
pp supremum.record
puts

puts "garbage records:"
each_garbage_record do |rec|
pp rec.record
if ibuf_index?
puts "(records not dumped due to this being an insert buffer index)"
elsif !record_describer
puts "(records not dumped due to missing record describer or data dictionary)"
else
puts "garbage records:"
each_garbage_record do |rec|
pp rec.record
puts
end
puts
end
puts

puts "records:"
each_record do |rec|
pp rec.record
puts
puts "records:"
each_record do |rec|
pp rec.record
puts
end
end
puts
end
Expand Down
14 changes: 12 additions & 2 deletions lib/innodb/space.rb
Original file line number Diff line number Diff line change
Expand Up @@ -276,14 +276,22 @@ def space_id
fsp[:space_id]
end

def checked_page_class!(page, expected_class)
return page if page.instance_of?(expected_class)

raise "Page #{page.offset} is not the correct type, found: #{page.class}, expected: #{expected_class}"
end

# Return the page number for the space's TRX_SYS page.
def page_trx_sys
5
end

# Get the Innodb::Page::TrxSys page for a system space.
def trx_sys
page(page_trx_sys) if system_space?
raise "Transaction System is only available in system spaces" unless system_space?

checked_page_class!(page(page_trx_sys), Innodb::Page::TrxSys)
end

def rseg_page?(page_number)
Expand All @@ -299,7 +307,9 @@ def page_sys_data_dictionary

# Get the Innodb::Page::SysDataDictionaryHeader page for a system space.
def data_dictionary_page
page(page_sys_data_dictionary) if system_space?
raise "Data Dictionary is only available in system spaces" unless system_space?

checked_page_class!(page(page_sys_data_dictionary), Innodb::Page::SysDataDictionaryHeader)
end

# Get an Innodb::List object for a specific list by list name.
Expand Down
4 changes: 2 additions & 2 deletions spec/innodb/space_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@
end

it "should return nil for a non-system space" do
@space_ibd.trx_sys.should eql nil
expect { @space_ibd.trx_sys }.to raise_error(RuntimeError)
end
end

Expand All @@ -118,7 +118,7 @@
end

it "should return nil for a non-system space" do
@space_ibd.data_dictionary_page.should eql nil
expect { @space_ibd.data_dictionary_page }.to raise_error(RuntimeError)
end
end

Expand Down

0 comments on commit a8c585b

Please sign in to comment.