From fd3532204c7302ec80a245c72852a11288ec38b5 Mon Sep 17 00:00:00 2001 From: Guilherme Mansur Date: Tue, 14 May 2019 15:13:29 -0400 Subject: [PATCH] Better error message for calling columns_hash When a record does not have a table name, as in the case for a record with `self.abstract_class = true` and no `self.table_name` set the error message raises a cryptic: "ActiveRecord::StatementInvalid: Could not find table ''" this patch now raises a new `TableNotSpecified Error` Fixes: #36274 Co-Authored-By: Eugene Kenny --- activerecord/CHANGELOG.md | 4 ++++ activerecord/lib/active_record/errors.rb | 4 ++++ activerecord/lib/active_record/model_schema.rb | 3 +++ activerecord/test/cases/base_test.rb | 8 ++++++++ 4 files changed, 19 insertions(+) diff --git a/activerecord/CHANGELOG.md b/activerecord/CHANGELOG.md index 8d4b01e995..8642227a2b 100644 --- a/activerecord/CHANGELOG.md +++ b/activerecord/CHANGELOG.md @@ -1,3 +1,7 @@ +* Loading the schema for a model that has no `table_name` raises a `TableNotSpecified` error. + + *Guilherme Mansur*, *Eugene Kenny* + * PostgreSQL: Fix GROUP BY with ORDER BY virtual count attribute. Fixes #36022. diff --git a/activerecord/lib/active_record/errors.rb b/activerecord/lib/active_record/errors.rb index 60cf9818c1..c8c06375a3 100644 --- a/activerecord/lib/active_record/errors.rb +++ b/activerecord/lib/active_record/errors.rb @@ -38,6 +38,10 @@ module ActiveRecord class AdapterNotSpecified < ActiveRecordError end + # Raised when a model makes a query but it has not specified an associated table. + class TableNotSpecified < ActiveRecordError + end + # Raised when Active Record cannot find database adapter specified in # +config/database.yml+ or programmatically. class AdapterNotFound < ActiveRecordError diff --git a/activerecord/lib/active_record/model_schema.rb b/activerecord/lib/active_record/model_schema.rb index 2a45f63d64..18f19af6be 100644 --- a/activerecord/lib/active_record/model_schema.rb +++ b/activerecord/lib/active_record/model_schema.rb @@ -482,6 +482,9 @@ module ActiveRecord end def load_schema! + unless table_name + raise ActiveRecord::TableNotSpecified, "#{self} has no table configured. Set one with #{self}.table_name=" + end @columns_hash = connection.schema_cache.columns_hash(table_name).except(*ignored_columns) @columns_hash.each do |name, column| define_attribute( diff --git a/activerecord/test/cases/base_test.rb b/activerecord/test/cases/base_test.rb index 983a46a2d0..1324bdf9b8 100644 --- a/activerecord/test/cases/base_test.rb +++ b/activerecord/test/cases/base_test.rb @@ -1415,6 +1415,14 @@ class BasicsTest < ActiveRecord::TestCase assert_not_includes SymbolIgnoredDeveloper.columns_hash.keys, "first_name" end + test ".columns_hash raises an error if the record has an empty table name" do + expected_message = "FirstAbstractClass has no table configured. Set one with FirstAbstractClass.table_name=" + exception = assert_raises(ActiveRecord::TableNotSpecified) do + FirstAbstractClass.columns_hash + end + assert_equal expected_message, exception.message + end + test "ignored columns have no attribute methods" do assert_not_respond_to Developer.new, :first_name assert_not_respond_to Developer.new, :first_name=