Skip to content

Commit

Permalink
#tables and #table_exists? and returns only tables and not views
Browse files Browse the repository at this point in the history
  • Loading branch information
rafaelfranca committed Dec 29, 2016
1 parent d5be101 commit 5973a98
Show file tree
Hide file tree
Showing 19 changed files with 131 additions and 166 deletions.
6 changes: 6 additions & 0 deletions activerecord/CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,9 @@
* `#tables` and `#table_exists?` and returns only tables and not views.

All the deprecations on those methods were removed.

*Rafael Mendonça França*

* Remove deprecated `name` argument from `#tables`.

*Rafael Mendonça França*
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -311,38 +311,35 @@ def collation
end

def tables # :nodoc:
ActiveSupport::Deprecation.warn(<<-MSG.squish)
#tables currently returns both tables and views.
This behavior is deprecated and will be changed with Rails 5.1 to only return tables.
Use #data_sources instead.
MSG
sql = "SELECT table_name FROM information_schema.tables WHERE table_type = 'BASE TABLE'"
sql << " AND table_schema = #{quote(@config[:database])}"

data_sources
select_values(sql, "SCHEMA")
end

def views # :nodoc:
select_values("SHOW FULL TABLES WHERE table_type = 'VIEW'", "SCHEMA")
end

def data_sources
def data_sources # :nodoc:
sql = "SELECT table_name FROM information_schema.tables "
sql << "WHERE table_schema = #{quote(@config[:database])}"

select_values(sql, "SCHEMA")
end

def truncate(table_name, name = nil)
execute "TRUNCATE TABLE #{quote_table_name(table_name)}", name
end
def table_exists?(table_name) # :nodoc:
return false unless table_name.present?

def table_exists?(table_name)
# Update lib/active_record/internal_metadata.rb when this gets removed
ActiveSupport::Deprecation.warn(<<-MSG.squish)
#table_exists? currently checks both tables and views.
This behavior is deprecated and will be changed with Rails 5.1 to only check tables.
Use #data_source_exists? instead.
MSG
schema, name = extract_schema_qualified_name(table_name)

data_source_exists?(table_name)
sql = "SELECT table_name FROM information_schema.tables WHERE table_type = 'BASE TABLE'"
sql << " AND table_schema = #{quote(schema)} AND table_name = #{quote(name)}"

select_values(sql, "SCHEMA").any?
end

def data_source_exists?(table_name)
def data_source_exists?(table_name) # :nodoc:
return false unless table_name.present?

schema, name = extract_schema_qualified_name(table_name)
Expand All @@ -353,10 +350,6 @@ def data_source_exists?(table_name)
select_values(sql, "SCHEMA").any?
end

def views # :nodoc:
select_values("SHOW FULL TABLES WHERE table_type = 'VIEW'", "SCHEMA")
end

def view_exists?(view_name) # :nodoc:
return false unless view_name.present?

Expand All @@ -368,6 +361,10 @@ def view_exists?(view_name) # :nodoc:
select_values(sql, "SCHEMA").any?
end

def truncate(table_name, name = nil)
execute "TRUNCATE TABLE #{quote_table_name(table_name)}", name
end

# Returns an array of indexes for the given table.
def indexes(table_name, name = nil) #:nodoc:
indexes = []
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -85,40 +85,42 @@ def data_sources # :nodoc
SQL
end

def views # :nodoc:
select_values(<<-SQL, "SCHEMA")
SELECT c.relname
FROM pg_class c
LEFT JOIN pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('v','m') -- (v)iew, (m)aterialized view
AND n.nspname = ANY (current_schemas(false))
SQL
end

# Returns true if table exists.
# If the schema is not specified as part of +name+ then it will only find tables within
# the current schema search path (regardless of permissions to access tables in other schemas)
def table_exists?(name)
ActiveSupport::Deprecation.warn(<<-MSG.squish)
#table_exists? currently checks both tables and views.
This behavior is deprecated and will be changed with Rails 5.1 to only check tables.
Use #data_source_exists? instead.
MSG

data_source_exists?(name)
end

def data_source_exists?(name)
name = Utils.extract_schema_qualified_name(name.to_s)
return false unless name.identifier

select_values(<<-SQL, "SCHEMA").any?
SELECT c.relname
FROM pg_class c
LEFT JOIN pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('r','v','m') -- (r)elation/table, (v)iew, (m)aterialized view
AND c.relname = #{quote(name.identifier)}
AND n.nspname = #{name.schema ? quote(name.schema) : "ANY (current_schemas(false))"}
SELECT tablename
FROM pg_tables
WHERE tablename = #{quote(name.identifier)}
AND schemaname = #{name.schema ? quote(name.schema) : "ANY (current_schemas(false))"}
SQL
end

def views # :nodoc:
select_values(<<-SQL, "SCHEMA")
def data_source_exists?(name) # :nodoc:
name = Utils.extract_schema_qualified_name(name.to_s)
return false unless name.identifier

select_values(<<-SQL, "SCHEMA").any?
SELECT c.relname
FROM pg_class c
LEFT JOIN pg_namespace n ON n.oid = c.relnamespace
WHERE c.relkind IN ('v','m') -- (v)iew, (m)aterialized view
AND n.nspname = ANY (current_schemas(false))
WHERE c.relkind IN ('r','v','m') -- (r)elation/table, (v)iew, (m)aterialized view
AND c.relname = #{quote(name.identifier)}
AND n.nspname = #{name.schema ? quote(name.schema) : "ANY (current_schemas(false))"}
SQL
end

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,8 +48,6 @@ def data_source_exists?(name)

@data_sources[name] = connection.data_source_exists?(name)
end
alias table_exists? data_source_exists?
deprecate table_exists?: "use #data_source_exists? instead"

# Add internal cache for table with +table_name+.
def add(table_name)
Expand All @@ -63,8 +61,6 @@ def add(table_name)
def data_sources(name)
@data_sources[name]
end
alias tables data_sources
deprecate tables: "use #data_sources instead"

# Get the columns for a table
def columns(table_name)
Expand Down Expand Up @@ -99,8 +95,6 @@ def clear_data_source_cache!(name)
@primary_keys.delete name
@data_sources.delete name
end
alias clear_table_cache! clear_data_source_cache!
deprecate clear_table_cache!: "use #clear_data_source_cache! instead"

def marshal_dump
# if we get current version during initialization, it happens stack over flow.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -260,40 +260,33 @@ def exec_rollback_db_transaction #:nodoc:
# SCHEMA STATEMENTS ========================================

def tables # :nodoc:
ActiveSupport::Deprecation.warn(<<-MSG.squish)
#tables currently returns both tables and views.
This behavior is deprecated and will be changed with Rails 5.1 to only return tables.
Use #data_sources instead.
MSG

data_sources
select_values("SELECT name FROM sqlite_master WHERE type = 'table' AND name <> 'sqlite_sequence'", "SCHEMA")
end

def data_sources
def data_sources # :nodoc:
select_values("SELECT name FROM sqlite_master WHERE type IN ('table','view') AND name <> 'sqlite_sequence'", "SCHEMA")
end

def table_exists?(table_name)
ActiveSupport::Deprecation.warn(<<-MSG.squish)
#table_exists? currently checks both tables and views.
This behavior is deprecated and will be changed with Rails 5.1 to only check tables.
Use #data_source_exists? instead.
MSG

data_source_exists?(table_name)
def views # :nodoc:
select_values("SELECT name FROM sqlite_master WHERE type = 'view' AND name <> 'sqlite_sequence'", "SCHEMA")
end

def data_source_exists?(table_name)
def table_exists?(table_name) # :nodoc:
return false unless table_name.present?

sql = "SELECT name FROM sqlite_master WHERE type IN ('table','view') AND name <> 'sqlite_sequence'"
sql = "SELECT name FROM sqlite_master WHERE type = 'table' AND name <> 'sqlite_sequence'"
sql << " AND name = #{quote(table_name)}"

select_values(sql, "SCHEMA").any?
end

def views # :nodoc:
select_values("SELECT name FROM sqlite_master WHERE type = 'view' AND name <> 'sqlite_sequence'", "SCHEMA")
def data_source_exists?(table_name) # :nodoc:
return false unless table_name.present?

sql = "SELECT name FROM sqlite_master WHERE type IN ('table','view') AND name <> 'sqlite_sequence'"
sql << " AND name = #{quote(table_name)}"

select_values(sql, "SCHEMA").any?
end

def view_exists?(view_name) # :nodoc:
Expand Down
2 changes: 1 addition & 1 deletion activerecord/lib/active_record/internal_metadata.rb
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ def [](key)
end

def table_exists?
ActiveSupport::Deprecation.silence { connection.table_exists?(table_name) }
connection.table_exists?(table_name)
end

# Creates an internal metadata table with columns +key+ and +value+
Expand Down
10 changes: 4 additions & 6 deletions activerecord/lib/active_record/migration.rb
Original file line number Diff line number Diff line change
Expand Up @@ -1026,12 +1026,10 @@ def schema_migrations_table_name
end

def get_all_versions(connection = Base.connection)
ActiveSupport::Deprecation.silence do
if connection.table_exists?(schema_migrations_table_name)
SchemaMigration.all.map { |x| x.version.to_i }.sort
else
[]
end
if connection.table_exists?(schema_migrations_table_name)
SchemaMigration.all.map { |x| x.version.to_i }.sort
else
[]
end
end

Expand Down
2 changes: 1 addition & 1 deletion activerecord/lib/active_record/schema_migration.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ def table_name
end

def table_exists?
ActiveSupport::Deprecation.silence { connection.table_exists?(table_name) }
connection.table_exists?(table_name)
end

def create_table
Expand Down
24 changes: 6 additions & 18 deletions activerecord/test/cases/adapter_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -32,25 +32,19 @@ def test_create_record_with_pk_as_zero

def test_tables
tables = nil
ActiveSupport::Deprecation.silence { tables = @connection.tables }
tables = @connection.tables
assert_includes tables, "accounts"
assert_includes tables, "authors"
assert_includes tables, "tasks"
assert_includes tables, "topics"
end

def test_table_exists?
ActiveSupport::Deprecation.silence do
assert @connection.table_exists?("accounts")
assert @connection.table_exists?(:accounts)
assert_not @connection.table_exists?("nonexistingtable")
assert_not @connection.table_exists?("'")
assert_not @connection.table_exists?(nil)
end
end

def test_table_exists_checking_both_tables_and_views_is_deprecated
assert_deprecated { @connection.table_exists?("accounts") }
assert @connection.table_exists?("accounts")
assert @connection.table_exists?(:accounts)
assert_not @connection.table_exists?("nonexistingtable")
assert_not @connection.table_exists?("'")
assert_not @connection.table_exists?(nil)
end

def test_data_sources
Expand Down Expand Up @@ -294,12 +288,6 @@ def test_log_invalid_encoding
assert_not_nil error.message
end
end

if current_adapter?(:Mysql2Adapter, :SQLite3Adapter)
def test_tables_returning_both_tables_and_views_is_deprecated
assert_deprecated { @connection.tables }
end
end
end

class AdapterTestWithoutTransaction < ActiveRecord::TestCase
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ def test_indexes_logs_name
end

def test_table_exists_logs_name
ActiveSupport::Deprecation.silence { @connection.table_exists?("items") }
@connection.table_exists?("items")
assert_equal "SCHEMA", @subscriber.logged[0][1]
end

Expand Down
12 changes: 5 additions & 7 deletions activerecord/test/cases/adapters/sqlite3/sqlite3_adapter_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -267,17 +267,17 @@ def test_transaction

def test_tables
with_example_table do
ActiveSupport::Deprecation.silence { assert_equal %w{ ex }, @conn.tables }
assert_equal %w{ ex }, @conn.tables
with_example_table "id integer PRIMARY KEY AUTOINCREMENT, number integer", "people" do
ActiveSupport::Deprecation.silence { assert_equal %w{ ex people }.sort, @conn.tables.sort }
assert_equal %w{ ex people }.sort, @conn.tables.sort
end
end
end

def test_tables_logs_name
sql = <<-SQL
SELECT name FROM sqlite_master
WHERE type IN ('table','view') AND name <> 'sqlite_sequence'
WHERE type = 'table' AND name <> 'sqlite_sequence'
SQL
assert_logged [[sql.squish, "SCHEMA", []]] do
@conn.tables
Expand All @@ -296,12 +296,10 @@ def test_table_exists_logs_name
with_example_table do
sql = <<-SQL
SELECT name FROM sqlite_master
WHERE type IN ('table','view') AND name <> 'sqlite_sequence' AND name = 'ex'
WHERE type = 'table' AND name <> 'sqlite_sequence' AND name = 'ex'
SQL
assert_logged [[sql.squish, "SCHEMA", []]] do
ActiveSupport::Deprecation.silence do
assert @conn.table_exists?("ex")
end
assert @conn.table_exists?("ex")
end
end
end
Expand Down
11 changes: 7 additions & 4 deletions activerecord/test/cases/connection_adapters/schema_cache_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -80,10 +80,13 @@ def test_dump_and_load
end
end

def test_table_methods_deprecation
assert_deprecated { assert @cache.table_exists?("posts") }
assert_deprecated { assert @cache.tables("posts") }
assert_deprecated { @cache.clear_table_cache!("posts") }
def test_data_source_exist
assert @cache.data_source_exists?("posts")
assert_not @cache.data_source_exists?("foo")
end

def test_clear_data_source_cache
@cache.clear_data_source_cache!("posts")
end

private
Expand Down
Loading

0 comments on commit 5973a98

Please sign in to comment.